Python爬虫 之Ajax请求

Ajax

当访问的页面是一个动态页面,就需要我们使用Ajax请求。

AJAX 是 Asynchronous JavaScript and XML(异步的 JavaScript 和 XML)的缩写。AJAX 通过使用原有的 web 标准组件,实现了在不重新加载整个页面的情况下,与服务器进行数据交互。例如在新浪微博中,你可以展开一条微博的评论,而不需要重新加载,或者打开一个新的页面。但是这些内容并不是一开始就在页面中的(这样页面就太大了),而是在你点击的时候被加载进来的。这就导致了你抓取这个页面的时候,并不能获得这些评论信息(因为你没有『展开』)。
AJAX 的一种常见用法是使用 AJAX 加载 JSON 数据,然后在浏览器端渲染。如果能直接抓取到 JSON 数据,会比 HTML 更容易解析。
AJAX 实际上也是通过 HTTP 传输数据的。

Python爬虫 之Ajax请求_第1张图片
AJAX 一般是通过 XMLHttpRequest 对象接口发送请求的,XMLHttpRequest 一般被缩写为 XHR。点击网络面板上漏斗形的过滤按钮,过滤出 XHR 请求。挨个查看每个请求,通过访问路径和预览,找到包含信息的请求。

如果页面是一个动态的json数据,就需要Ajax请求


实际案例

案例一:

需求:
实现输入一个单词,出现翻译结果,并储存到 json 文件中。

代码实现:

import requests
import json

if __name__ == '__main__':
    # 1.指定url
    url = 'https://fanyi.baidu.com/sug'
    # 2.进行UA伪装
    header = {
     
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.25 Safari/537.36 Core/1.70.3775.400 QQBrowser/10.6.4208.400'
    }
    # 3.参数处理
    # data相当于get请求中的params,表示请求所带的参数(也是一个字典类型数据)
    # post请求参数处理(和get请求一致)
    word = input('请输入要翻译的单词:')		# 这样翻译单词就变成动态的了
    data = {
     
        'kw':word
    }
    # 4.请求发送
    response = requests.post(url=url,data=data,headers=header)
    # 5.获取相应数据
    # json()方法返回的是一个对象
    # 如果确定相应数据是json类型的,才可以使用json()方法进行对象的返回
    dic_obj = response.json()
    print(dic_obj)
    print('数据打印结束!')

    # 5.进行持续化存储
    file_name = word + '.json'
    fp = open(file_name,'w',endcoding='utf-8')
    json.dump(dic_obj,fp=fp,ensure_ascii=False)
    print('数据存储结束!')

案例二:

需求:
实现读取豆瓣电影信息。

代码实现:

import requests
import json

if __name__ == '__main__':
    url = 'https://movie.douban.com/j/chart/top_list'
    param = {
     
        'type': '24',
        'interval_id': '100:90',
        'action': '',
        'start': '0',       # 从库中的第几个元素取
        'limit': '20',      # 一次取几个
    }
    header = {
     
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.105 Safari/537.36'
    }
    response = requests.get(url=url,params=param,headers=header)
    list_data = response.json()
    # 打印结果
    for i in list_data:
        print(i)
    # 也可以这样直接打印:
    # print(list_data)

案例三:

需求:
爬取肯德基餐厅查询,指定地点的餐厅数量。
网址:http://www.kfc.com.cn/kfccda/storelist/index.aspx

Python爬虫 之Ajax请求_第2张图片

代码实现:

# 爬取想要爬取城市的肯德基餐厅信息
import requests
import json

if __name__ == '__main__':
    # 指定url
    url = 'http://www.kfc.com.cn/kfccda/ashx/GetStoreList.ashx?op=keyword'
    # 动态输入查找的城市
    city = input('请输入您想要查找的城市:')
    # 参数处理
    param = {
     
        'cname': '',
        'pid': '',
        'keyword': city,        # 城市名称
        'pageIndex': '1',       # 页面
        'pageSize': '10',       # 一页显示多少数据
    }
    # 进行UA伪装
    header = {
     
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.105 Safari/537.36'
    }
    # 获取相应数据
    response = requests.post(url=url,data=param,headers=header)
    # 这个页面是一个text,不是json
    page_text = response.text
    print(page_text)
    print('数据爬取成功!')

案例四:

需求:
爬取国家药品监督管理局中化妆品生产许可信息管理系统服务平台,其中每个企业的详细信息。
网址:http://scxk.nmpa.gov.cn:81/xk/

思路:
我们可以发现这是一个json动态页面,需要我们使用Ajax请求抓取页面数据。但是我们需要打印每个公司的详细信息,我们点开不同公司的详细信息后发现,每个公司的网址前面的都是相同的(都是:http://scxk.nmpa.gov.cn:81/xk/itownet/portalAction.do?method=getXkzsById),唯一不同的是后面的id信息。而这个id可以从首页中抓取。
所有,我们只需要通过post方法抓取到首页信息,再将id信息存入名为id_list(自己定义的名字,任何名字都可以)的列表中即可。

Python爬虫 之Ajax请求_第3张图片

我们得到id_list列表信息后,就可再次用post方法抓取这个页面的企业详细信息。通过遍历id信息,来查找每个企业的详细信息,并且打印。
最后,我们发现这个网址有300多页,如果我们想把所有页的所有企业的详细信息都打印下来怎么办呢?我们发现参数param中的page是一个动态变量,其代表的就是页码数。我们只需要通过for循环将页码数变量,即可完成对所有(也可以是任意页,可以从第n页到第m页,只需要控制for循环内的参数即可)页码所有企业详细信息数据的抓取打印。

代码实现:

import requests
import json

if __name__ == '__main__':
    # 指定url,国家药品监督总局化妆品生产许可信息管理服务平台
    url = 'http://scxk.nmpa.gov.cn:81/xk/itownet/portalAction.do?method=getXkzsList'
    # 进行UA伪装
    header = {
     
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.105 Safari/537.36'
    }
    
    id_list = []        # 存贮id信息(需要定义在循环外,要不然就相当于每次循环都创建一个名为id_list的列表,会报错)

    # 从第一页到第六页信息(也可以是从第n页到第m页)
    # page为动态变量表示的是页码数
    for page in range(1,6):
        page = str(page)
        # 参数处理
        param = {
     
            'on': 'true',
            'page' : page,			# 页码数
            'pageSize' : '15',		# 一页只有15个企业
            'productName': '',
            'conditionType': '1',	# 从第一个企业开始
            'applyname': '',
            'applysn': ''
        }
        # 获取相应数据
        # 为了获取所有企业的id
        response = requests.post(url=url,data=param,headers=header)
        json_id = response.json()
        # print(json_id)

        # 将id信息存入列表中
        for dic in json_id['list']:
            id_list.append(dic['ID'])
        # print(id_list)
    # 获取企业详细信息
    # 每个企业的化妆品生产许可信息
    url1 = 'http://scxk.nmpa.gov.cn:81/xk/itownet/portalAction.do?method=getXkzsById'
    # 遍历列表中的id信息,用post方法抓取数据,打印企业详细信息
    for i in id_list:
        data = {
     
            'id': i
        }
        page_post = requests.post(url=url1,headers=header,data=data).json()
        print(page_post)

你可能感兴趣的:(Python,python,ajax,json)