实现内容:按照城市(程序内列出部分主要城市,可自行在程序中更改)抓取拉勾网的特定职位信息,默认30页
程序运行方法:python3 lagou_JobSearch.py 索索岗位名称(中文/英文)
爬虫结果文件自动保存到 city_搜索名称.tsv文件中
第一层:导入模块和程序
requests:网页请求模块
time:主要是等待一段时间,避免频繁访问网页而被禁止访问请求
sys:参数传递模块
urllib:对中文进行编码置于url中
外层函数传入参数都main函数,main函数是爬虫的主函数
import requests
import time
import random
import sys
from urllib import parse
#定义一个表示爬去数量的全局变量,每爬到一条职位信息就打印出当前爬取状态
n = 0
if __name__ == '__main__':
key_word = sys.argv[1]
out_file = 'city_{}.tsv'.format(key_word)
main(key_word,out_file)
第二层:main函数
实现内容:按照城市分别进行爬取,对每个城市分页(1~30)进行访问,对具体的抓取过程放在get_json()函数中,
其返回抓取的页面职位数据列表,在main()函数中保存数据到文件
def main(key_word,out_file):
out_hd = open(out_file,'w')
head_list = ['职位','公司简称','学历要求','工作经验','工资','城市','县区','位置','创建时间', '工作性质','经营范围','公司规模','公司
全称','福利待遇','公司优势','类型1','类型2','类型3']
out_hd.write('\t'.join(head_list)+'\n')
city_name_list = ['北京','上海','深圳','广州','杭州','成都','南京','武汉','长沙']
for k in range(len(city_name_list)):
n = 0
city_name = parse.quote(city_name_list[k])
page = 1
while page<31:
t = random.uniform(5,15)
time.sleep(t)
result = get_json(page,key_word,city_name)
for each in result:
each_info = '\t'.join(each)
out_hd.write(each_info+'\n')
out_hd.flush()
page += 1
out_hd.close()
第三层:get_json()函数具体爬取过程
定义headers信息,定义data上传数据,定义Myparams参数
首先访问主页面保存cookie信息,然后再访问AJAX请求得到数据,最后解析json并提取数据
def get_json(page,key_word,city):
key_word_raw = key_word
key_word = parse.quote(key_word)
MyParams = {'labelWords':'','fromSearch':'true','suginput':''}
headers['Referer'] = 'https://www.lagou.com/jobs/list_{}?px=default&city={}'.format(key_word,city)
url_start = 'https://www.lagou.com/jobs/list_{}?px=default&city={}#filterBox'.format(key_word,city)
s = requests.Session()
s.get(url_start,headers=headers,params=MyParams,timeout=3)
time.sleep(random.uniform(5,15))
cookie = s.cookies
data = {'first':'true','pn':str(page),'kd':key_word_raw}
MyParams = {'px':'default','city':city,'needAddtionalResult':'false'}
url = 'https://www.lagou.com/jobs/positionAjax.json?px=default&city={}&needAddtionalResult=false'.format(city)
r = s.post(url, data=data, headers=headers,cookies=cookie, timeout=3)
print('\n状态码{}'.format(str(r.status_code)))
json = r.json()
time.sleep(random.uniform(5,15))
list_con = json['content']['positionResult']['result']
info_list = []
global n
m = 0
for i in list_con:
n += 1
m += 1
info = []
info.append(i.get('positionName','no'))
info.append(i.get('companyShortName','no'))
info.append(i.get('education','no'))
info.append(i.get('workYear','no'))
info.append(i.get('salary','no'))
info.append(i.get('city','no'))
info.append(i.get('district','no'))
info.append(i.get('createTime','no'))
info.append(i.get('stationname','no'))
info.append(i.get('jobNature','no'))
info.append(i.get('industryField','no'))
info.append(i.get('companySize','no'))
info.append(i.get('companyFullName','no'))
info.append(';'.join(i.get('companyLabelList','no')))
info.append(i.get('positionAdvantage','no'))
info.append(i.get('firstType','no'))
info.append(i.get('secondType','no'))
info.append(i.get('thirdType','no'))
for i in range(len(info)):
if info[i] is None:
info[i] = 'no'
print('城市:{}; 总共第{}条数据; 第{}页 第{}条数据'.format(info[5],str(n),str(page),str(m)))
info_list.append(info)
return info_list
当然,还要定义headers信息
headers = {
'Accept': 'application/json, text/javascript, */*; q=0.01',
'Accept-Encoding': 'gzip, deflate, br',
'Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8',
'Connection': 'keep-alive',
'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8',
'Host': 'www.lagou.com',
'Origin': 'https://www.lagou.com',
'Sec-Fetch-Mode': 'cors',
'Sec-Fetch-Site': 'same-origin',
'User-Agent': 'Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.132 Mobile Safari/537.36',
'X-Anit-Forge-Code': '0',
'X-Anit-Forge-Token': None,
'X-Requested-With': 'XMLHttpRequest',
#'Content-Length': '23', #这个不固定,加上后反而不能连接网站
}
爬取结果:
参考: