I'm trying to automate the download of a CSV file from a Blob URL on a dynamic website using Selenium with Python. The CSV download is triggered by clicking a button, but the button click generates a Blob URL, which isn't directly accessible via traditional HTTP requests. I'm having trouble capturing and downloading the file from this Blob URL.
Here is the example of url: https://snapshot.org/#/aave.eth/proposal/0x70dfd865b78c4c391e2b0729b907d152e6e8a0da683416d617d8f84782036349
Here is the link looks like when I check from download history:
blob:https://snapshot.org/4b2f45e9-8ca3-4105-b142-e1877e420c84
I've checked this post as well Python: How to download a blob url video? which said that I could not download it and I think it does not make sense since when I open the webpage manually, I can click the download button and get the file.
This is the code that I've tried before
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.chrome.service import Service
from webdriver_manager.chrome import ChromeDriverManager
import time
# Setup ChromeDriver
driver = webdriver.Chrome(service=Service(ChromeDriverManager().install()))
# URL of the proposal page
url = 'https://snapshot.org/#/aave.eth/proposal/0x70dfd865b78c4c391e2b0729b907d152e6e8a0da683416d617d8f84782036349'
# Navigate to the page
driver.get(url)
try:
# Wait up to 20 seconds until the expected button is found using its attributes
wait = WebDriverWait(driver, 20)
download_button = wait.until(EC.element_to_be_clickable((By.XPATH, "//button[contains(.,'svg')]")))
download_button.click()
print("Download initiated.")
except Exception as e:
print(f"Error: {e}")
# Wait for the download to complete
time.sleep(5)
# Close the browser
driver.quit()
When I inspect the Download csv button here is what I got
<svg viewBox="0 0 24 24" width="1.2em" height="1.2em"><path fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 16v1a3 3 0 0 0 3 3h10a3 3 0 0 0 3-3v-1m-4-4l-4 4m0 0l-4-4m4 4V4"></path></svg>
I don't know what you tried to do (because you didn't show your code) but this works for me
driver.find_elements(By.XPATH, '//button')[10].click()
but it may need better method to find correct button (instead of [10]
).
Meanwhile I found this xpath: "//div[h4//span[contains(text(),'Votes')]]//button"
Full working code
from selenium import webdriver
from selenium.webdriver.common.by import By
#import undetected_chromedriver as uc
import time
# ---
import selenium
print('Selenium:', selenium.__version__) # Selenium: 4.19.0
# ---
url = 'https://snapshot.org/#/aave.eth/proposal/0x70dfd865b78c4c391e2b0729b907d152e6e8a0da683416d617d8f84782036349'
#driver = webdriver.Chrome() # the newest Selenium will automatically download driver - so it doesn't need `service=`
driver = webdriver.Firefox() # the newest Selenium will automatically download driver - so it doesn't need `service=`
#driver = uc.Chrome()
driver.get(url)
# ---
time.sleep(3)
#all_buttons = driver.find_elements(By.XPATH, '//button')
#all_buttons[10].click()
driver.find_element(By.XPATH, "//div[h4//span[contains(text(),'Votes')]]//button").click()
input('Press ENTER to exit')
driver.close()