Ajax可以对JS进行渲染,但有些直接通过JS来渲染,例如淘宝,许多图形是通过JavaScript计算之后形成的,里面的Ajax接口含有许多加密参数,无法找到规律,像Echarts
1. selenium
Selenium是一个 自动化测试工具,利用它可以驱动浏览器执行特定的动作,如点击、下拉等操作,同时还可以获取浏览器当前呈现的页面的源代码,做到可见即可爬
1 from selenium import webdriver 2 from selenium.webdriver.common.by import By 3 from selenium.webdriver.common.keys import Keys 4 from selenium.webdriver.support import expected_conditions as EC 5 from selenium.webdriver.support.wait import WebDriverWait 6 from selenium.common.exceptions import NoSuchElementException 7 from selenium.webdriver.support.ui import WebDriverWait 8 from selenium.webdriver import ActionChains 9 import time 10 11 browser = webdriver.Chrome() 12 13 ''' 14 #访问百度,并查询python 15 try: 16 browser.get('https://www.baidu.com') 17 input = browser.find_element_by_id('kw') 18 input.send_keys('Python') 19 input.send_keys(Keys.ENTER) 20 wait = WebDriverWait(browser, 10) 21 wait.until(EC.presence_of_element_located((By.ID, 'content_left'))) 22 print(browser.current_url) 23 print(browser.get_cookies()) 24 print(browser.page_source) 25 finally: 26 browser.close() 27 28 #访问淘宝 29 #单个节点 30 browser.get('http://www.taobao.com') 31 input_first = browser.find_element_by_id('q') 32 input_second = browser.find_element_by_css_selector('#q') 33 input_third = browser.find_element_by_xpath('//*[@id="q"]') 34 print(input_first, input_second, input_third) 35 #print(browser.page_source) 36 browser.close() 37 ''' 38 39 ''' 40 #多个节点 41 import time 42 browser = webdriver.Chrome() 43 browser.get('https://www.taobao.com') 44 input = browser.find_element_by_id('q') 45 input.send_keys('iPhone') 46 time.sleep(1) 47 input.clear() 48 input.send_keys('iPad') 49 button = browser.find_element_by_class_name('btn-search') 50 button.click() 51 ''' 52 53 ''' 54 #动作链 55 browser = webdriver.Chrome() 56 url = 'http://www.runoob.com/try/try.php?filename=jqueryui-api-droppable' 57 browser.get(url) 58 browser.switch_to_frame('iframeResult') 59 #source = browser.find_element_by_css_selector('#draggable') 60 #target = browser.find_element_by_css_selector('#droppable') 61 #actions =ActionChains(browser) 62 #actions.drag_and_drop(source, target) 63 #actions.perform() 64 65 #切换Frame 66 # Selenium打开页面后,它默认是在父级 Frame里面操作, 67 # 而此时如果页面中 还有子 Frame,它是不能获取到子 Frame里面的节点的 。 68 # 这时就需要使用 switch_to.frame()方法来切 换 Frame。 69 try: 70 logo = browser.find_element_by_class_name('logo') 71 except NoSuchElementException: 72 print('NO LOGO') 73 browser.switch_to.parent_frame() 74 logo = browser.find_element_by_class_name('logo') 75 print(logo) 76 print(logo.text) 77 ''' 78 79 ''' 80 #获取js 81 browser =webdriver.Chrome() 82 browser.get('http://www.zhihu.com/explore') 83 #browser.execute_script('window.scrollTo(0, ducument.body.scrollHeight)') 84 browser.execute_script('window.scrollTo(0, document.body.scrollHeight)') 85 browser.execute_script('alert("To Bottom")') 86 ''' 87 88 ''' 89 #获取节点信息 90 browser =webdriver.Chrome() 91 url = 'http://www.zhihu.com/explore' 92 browser.get(url) 93 logo = browser.find_element_by_id('zh-top-link-logo') 94 input = browser.find_element_by_class_name('zu-top-link-logo') 95 96 print(logo) 97 print(logo.get_attribute('class')) 98 print(input.text) 99 input = browser.find_element_by_class_name('zu-top-add-question') 100 print(input.id) 101 print(input.location) 102 print(input.tag_name) 103 print(input.size) 104 print(input.text) 105 ''' 106 107 ''' 108 #延时等待 109 #隐式等待 110 #使用隐式等待执行测试的时候, 111 #如果 Selenium没有在 DOM 中找到节点,将继续等待, 112 #超出设定时间后,则抛什1找不到节点的异常。 113 #browser = webdriver.Chrome() 114 #browser.implicitly_wait(10) 115 #browser.get('http://www.zhihu.com/explore') 116 #input = browser.find_element_by_class_name('zu-top-add-question') 117 #print(input) 118 #显式等待 119 #它指定要查找的节点,然后指定一个最长等待时间。 120 #如果 在规定时间内加载出来了这个节点,就返回查找的节点; 121 #如果到了规定时间依然没有加载出该节点,则抛阳超时异常。 122 browser = webdriver.Chrome() 123 browser.get('https://www.taobao.com/') 124 wait = WebDriverWait(browser, 10) 125 #until传入等待条件 126 #presence_of_element_located代表节点出现 127 input = wait.until(EC.presence_of_element_located((By.ID, 'q')))#节点定义为元组,所以是两对括号 128 button = wait.until(EC.element_to_be_clickable((By.CSS_SELECTOR, '.btn-search'))) 129 print(input, button) 130 ''' 131 132 ''' 133 #前进后退 134 browser.get('http://www.zhihu.com/explore') 135 browser.get('http://www.taobao.com') 136 browser.get('http://www.python.com') 137 browser.back() 138 time.sleep(1) 139 browser.forward() 140 browser.close() 141 ''' 142 143 #''' 144 #cookies 145 browser.get('http://www.zhihu.com/explore') 146 print(browser.get_cookies()) 147 print('--------------------------------------------------------------') 148 browser.add_cookie({ 149 'name': 'name', 150 'domain': 'www.zhihu.com', 151 'value': 'germey' 152 }) 153 print(browser.get_cookies()) 154 print('--------------------------------------------------------------') 155 browser.delete_all_cookies() 156 print(browser.get_cookies()) 157 #'''
2. splash:
Splash是一个 JavaScript渲染服务,是一个带有 HTTPAPI 的轻量级浏览器,同时它对接了 Python中的Twisted和QT库。 利用它,我们同样可以实现动态谊染页面的抓取。
- 异步方式处理多个网页渲染过程 ;
- 获取渲染后的页面的源代码或截图;
- 通过关闭图片渲染或者使用 Adblock规则来加快页面渲染速度;口 可执行特定的 JavaScript脚本;
- 可通过 Lua脚本来控制页面渲染过程;
- 获取渲染的详细过程并通过 HAR ( HTTP Archive )格式呈现。