【问题标题】:How to get the url or filename being downloaded now?如何获取现在正在下载的 url 或文件名?
【发布时间】:2019-10-25 21:26:22
【问题描述】:

点击按钮后,如何知道下载地址(带文件名),或者

如何知道正在下载的文件名(包含扩展名)?一个问题是,例如下载的文件有些有.csv 扩展名,有些没有。

例如我想统一重命名它。 (请不要去 D/L DIR,找到文件并重命名)

from selenium import webdriver
from selenium.webdriver.firefox.options import Options 
...
profile.set_preference('browser.helperApps.neverAsk.saveToDisk', 'text/csv')
...
driver = webdriver.Firefox(profile, options=opts, executable_path=FIREFOX_GOCKO_DRIVER_PATH)

driver.get(url)
driver.find_element_by_id(Button).click()

print("The file being downloaded is... ", ??? )
print("File is being downloaded from...", ?url?)

【问题讨论】:

    标签: python selenium firefox


    【解决方案1】:

    这里是获取最新下载的文件名和url的简单解决方案。

    注意:考虑到文件下载已完成,然后再运行以下代码。

    如果您希望脚本等到下载完成,请检查答案末尾的 getDownLoadedFileName 方法。

    # open a new tab
    driver.execute_script("window.open()")
    # switch to new tab
    driver.switch_to.window(driver.window_handles[-1])
    # navigate to chrome downloads
    driver.get('chrome://downloads')
    # get the latest downloaded file name
    fileName = driver.execute_script("return document.querySelector('downloads-manager').shadowRoot.querySelector('#downloadsList downloads-item').shadowRoot.querySelector('div#content  #file-link').text")
    # get the latest downloaded file url
    sourceURL = driver.execute_script("return document.querySelector('downloads-manager').shadowRoot.querySelector('#downloadsList downloads-item').shadowRoot.querySelector('div#content  #file-link').href")
    # print the details
    print(fileName)
    print (sourceURL)
    # close the downloads tab2
    driver.close()
    # switch back to main window
    driver.switch_to.window(driver.window_handles[0])
    

    如果您愿意,您可以将其作为一种方法并在需要的地方调用。

    编辑:如果您必须等到下载完成,请不要担心

    您可以中继 chrome 下载状态,检查以下方法。

    在获取文件名时只需在代码中调用以下方法

    def getDownLoadedFileName(waitTime):
        downloadsList = driver.execute_script("return document.querySelector('downloads-manager').shadowRoot")
        endTime = time.time()+waitTime
        while True:
            try:
                fileName = driver.execute_script("return document.querySelector('downloads-manager').shadowRoot.querySelector('#downloadsList downloads-item').shadowRoot.querySelector('div#content  #file-link').text")
                if fileName:
                    return fileName
            except:
                pass
            time.sleep(1)
            if time.time() > endTime:
                break
    

    您可以如下调用该方法。

    # wait until the download completes and get the file name
    fileName = getDownLoadedFileName(180)
    print(fileName)
    

    火狐: 火狐使用下面的方法。

    def getDownLoadedFileName(waitTime):
        driver.execute_script("window.open()")
        WebDriverWait(driver,10).until(EC.new_window_is_opened)
        driver.switch_to.window(driver.window_handles[-1])
        driver.get("about:downloads")
    
        endTime = time.time()+waitTime
        while True:
            try:
                fileName = driver.execute_script("return document.querySelector('#contentAreaDownloadsView .downloadMainArea .downloadContainer description:nth-of-type(1)').value")
                if fileName:
                    return fileName
            except:
                pass
            time.sleep(1)
            if time.time() > endTime:
                break
    

    Java + Chrome:如果您正在寻找 java 实现。

    这是java中的方法。

    public String waitUntilDonwloadCompleted(WebDriver driver) throws InterruptedException {
          // Store the current window handle
          String mainWindow = driver.getWindowHandle();
    
          // open a new tab
          JavascriptExecutor js = (JavascriptExecutor)driver;
          js.executeScript("window.open()");
         // switch to new tab
        // Switch to new window opened
          for(String winHandle : driver.getWindowHandles()){
              driver.switchTo().window(winHandle);
          }
         // navigate to chrome downloads
          driver.get("chrome://downloads");
    
          JavascriptExecutor js1 = (JavascriptExecutor)driver;
          // wait until the file is downloaded
          Long percentage = (long) 0;
          while ( percentage!= 100) {
              try {
                  percentage = (Long) js1.executeScript("return document.querySelector('downloads-manager').shadowRoot.querySelector('#downloadsList downloads-item').shadowRoot.querySelector('#progress').value");
                  //System.out.println(percentage);
              }catch (Exception e) {
                // Nothing to do just wait
            }
              Thread.sleep(1000);
          }
         // get the latest downloaded file name
          String fileName = (String) js1.executeScript("return document.querySelector('downloads-manager').shadowRoot.querySelector('#downloadsList downloads-item').shadowRoot.querySelector('div#content #file-link').text");
         // get the latest downloaded file url
          String sourceURL = (String) js1.executeScript("return document.querySelector('downloads-manager').shadowRoot.querySelector('#downloadsList downloads-item').shadowRoot.querySelector('div#content #file-link').href");
          // file downloaded location
          String donwloadedAt = (String) js1.executeScript("return document.querySelector('downloads-manager').shadowRoot.querySelector('#downloadsList downloads-item').shadowRoot.querySelector('div.is-active.focus-row-active #file-icon-wrapper img').src");
          System.out.println("Download deatils");
          System.out.println("File Name :-" + fileName);
          System.out.println("Donwloaded path :- " + donwloadedAt);
          System.out.println("Downloaded from url :- " + sourceURL);
         // print the details
          System.out.println(fileName);
          System.out.println(sourceURL);
         // close the downloads tab2
          driver.close();
         // switch back to main window
          driver.switchTo().window(mainWindow);
          return fileName;
      }
    

    这是在您的 java 脚本中调用它的方法。

    // download triggering step 
    downloadExe.click();
    // now waituntil download finish and then get file name
    System.out.println(waitUntilDonwloadCompleted(driver));
    

    【讨论】:

    • 检查getDownLoadedFileName 方法,以确保在获取名称之前完成下载。您可以通过秒数来完成下载。例如:我在上面的答案中的getDownLoadedFileName(180) 方法调用中提到它为180 秒。
    • 谢谢!我在 click() 之后直接添加您的代码,它一直到“fileName = driver.execute_script(”,然后出现错误“消息:javascript 错误:无法读取 null 的属性 'shadowRoot'(会话信息:headless chrome=74.0.3729.169) " ,我读了this link,shadowRoot 还是有问题?
    • 尝试使用fileName =getDownloadedFileName(180) 而不是fileName = driver.execute_script(,这样该方法将确保在获取文件名之前显示shadowroot。您可以在我的回答末尾看到def getDownloadedFileName 的实现。
    • 我把 def 子例程放在最上面,然后在 click() 之后调用它,仍然是同样的错误:>> 消息:javascript 错误:无法读取 null 的属性 'shadowRoot'(会话信息:chrome =74.0.3729.169) (驱动信息: chromedriver=74.0.3729.6 (255758eccf3d244491b8a1317aa76e1ce10d57e9-refs/branch-heads/3729@{#29}),platform=Mac OS X 10.13.6 x86_64) buggy > a lot here,但仍然没有固定在 headless 中,但可以 D/L all w/o headless。您介意按照 OP 的要求使用 Firefox 吗?谢谢!
    • 在无头模式下我得到selenium.common.exceptions.JavascriptException: Message: javascript error: Cannot read property 'shadowRoot' of null
    猜你喜欢
    • 2012-11-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-01-01
    • 1970-01-01
    • 2019-02-01
    相关资源
    最近更新 更多