VB.net 2010 视频教程 VB.net 2010 视频教程 python基础视频教程
SQL Server 2008 视频教程 c#入门经典教程 Visual Basic从门到精通视频教程
当前位置:
首页 > temp > c#教程 >
  • Python爬取大厂找招聘数据,看看大家的差别在哪里

本文的文字及图片来源于网络,仅供学习、交流使用,不具有任何商业用途,如有问题请及时联系我们以作处理。

以下文章来源于菜J学Python ,作者小小明

Python爬虫、数据分析、网站开发等案例教程视频免费在线观看

https://www.xin3721.com/eschool/pythonxin3721/

前言

今天我们打算爬取一下字节跳动的招聘信息:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

我们打开开发者工具并访问:

https://jobs.bytedance.com/experienced/position?keywords=&category=&location=&project=&type=&job_hot_flag=¤t=1&limit=10

 

这次访问监控到的数据很多,其中这个posts接口才有我们需要的json数据:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

观察响应头发现一个重要参数csrf:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

说明字节跳动的网站具备csrf校验的功能,后文将再介绍如何获取到这个csrf的token。

查看请求参数:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

参数包装函数

为了正常爬取时的方便,我们需要先将上面需要的参数,组织成python能够识别的字典形式。直接复制粘贴有很多需要加双引号的地方,但我们可以编程解决这个问题。

首先,定义一个处理函数:

复制代码
import re


def warp_heareder(s):
    print("{")
    lines = s.splitlines()
    for i, line in enumerate(lines):
        k, v = line.split(": ")
        if re.search("[a-zA-Z]", k):
            k = f'"{k}"'
        if re.search("[a-zA-Z]", v):
            v = f'"{v}"'
        print(f"    {k}: {v},")
    print("}")
复制代码

 

处理请求头:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

处理post请求数据:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

csrf校验值获取

首先,清空cookie:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

然后刷新页面,查看网络请求的抓包情况:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

找啊找,终于找到了一个set-cookie的响应头,而且这个设置cookie参数包括了csrf的设置。那么这个接口我们就可以用来作为获取csrf校验值的接口。

使用session保存响应头设置的cookie:

复制代码
import requests

session = requests.session()
headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36',
    'Origin': 'https://jobs.bytedance.com',
    'Referer': f'https://jobs.bytedance.com/experienced/position?keywords=&category=&location=&project=&type=&job_hot_flag=¤t=1&limit=10'
}
data = {
    "portal_entrance": 1
}
url = "https://jobs.bytedance.com/api/v1/csrf/token"
r = session.post(url, headers=headers, data=data)
r
复制代码

 

结果:

<Response [200]>

 

查看获取到的cookie:

cookies = session.cookies.get_dict()
cookies

 

结果:

{'atsx-csrf-token': 'RDTEznQqdr3O3h9PjRdWjfkSRW79K_G16g85FrXNxm0%3D'}

 

显然这个token相对真实需要的存在url编码,现在对它进行url解码:

from urllib.parse import unquote

unquote(cookies['atsx-csrf-token'])

 

结果:

'RDTEznQqdr3O3h9PjRdWjfkSRW79K_G16g85FrXNxm0='

 

 

开始爬取第一页的数据

有了token我们就可以顺利的直接访问接口了:

复制代码
import requests
import json

headers = {
    "Accept": "application/json, text/plain, */*",
    "Host": "jobs.bytedance.com",
    "Origin": "https://jobs.bytedance.com",
    "Referer": "https://jobs.bytedance.com/experienced/position?keywords=&category=&location=&project=&type=&job_hot_flag=¤t=1&limit=10",
    "User-Agent": "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36",
    "x-csrf-token": unquote(cookies['atsx-csrf-token']),
}
data = {
    "job_category_id_list": [],
    "keyword": "",
    "limit": 10,
    "location_code_list": [],
    "offset": 0,
    "portal_entrance": 1,
    "portal_type": 2,
    "recruitment_id_list": [],
    "subject_id_list": []
}
url = "https://jobs.bytedance.com/api/v1/search/job/posts"
r = session.post(url, headers=headers, data=json.dumps(data))
r
复制代码

 

结果:

<Response [200]>

 

响应码是200,说明已经顺利通过了校验,现在查看一下数据结构:

r.json()

 

结果:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

使用Pandas对json数据进行处理

import pandas as pd

df = pd.DataFrame(r.json()['data']['job_post_list'])
df.head(3)

 

结果:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

然后我们对各列提取出我们需要的数据:

复制代码
df.city_info = df.city_info.str['name']
df.recruit_type = df.recruit_type.str['parent'].str['name']
tmp = []
for x in df.job_category.values:
    if x['parent']:
        tmp.append(f"{x['parent']['name']}-{x['name']}")
    else:
        tmp.append(x['name'])
df.job_category = tmp
df.publish_time = df.publish_time.apply(lambda x: pd.Timestamp(x, unit="ms"))
df.head(2)
复制代码

 

结果:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

再删除一些,明显没有任何用的列:

df.drop(columns=['sub_title', 'job_hot_flag', 'job_subject'], inplace=True)
df.head()

 

结果:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

爬取字节跳动全部职位信息

有了上面的测试基础,我们就可以组织一下完整的爬取代码:

复制代码
import requests
from urllib.parse import unquote
import pandas as pd
import time
import os

session = requests.session()
page = 1500
headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36',
    'Origin': 'https://jobs.bytedance.com',
    'Referer': f'https://jobs.bytedance.com/experienced/position?keywords=&category=&location=&project=&type=&job_hot_flag=¤t=1&limit={page}'
}
data = {
    "portal_entrance": 1
}
url = "https://jobs.bytedance.com/api/v1/csrf/token"
r = session.post(url, headers=headers, data=data)
cookies = session.cookies.get_dict()

url = "https://jobs.bytedance.com/api/v1/search/job/posts"
headers["x-csrf-token"] = unquote(cookies["atsx-csrf-token"])
data = {
    "job_category_id_list": [],
    "keyword": "",
    "limit": page,
    "location_code_list": [],
    "offset": 0,
    "portal_entrance": 1,
    "portal_type": 2,
    "recruitment_id_list": [],
    "subject_id_list": []
}
for i in range(11):
    print(f"准备爬取第{i}页")
    data["offset"] = i*page
    r = None
    whilenot r:
        try:
            r = session.post(url, headers=headers,
                             data=json.dumps(data), timeout=3)
        except Exception as e:
            print("访问超时!等待5s", e)
            time.sleep(5)
    df = pd.DataFrame(r.json()['data']['job_post_list'])
    if df.shape[0] == 0:
        print("爬取完毕!!!")
        break
    df.city_info = df.city_info.str['name']
    df.recruit_type = df.recruit_type.str['parent'].str['name']
    tmp = []
    for x in df.job_category.values:
        if x['parent']:
            tmp.append(f"{x['parent']['name']}-{x['name']}")
        else:
            tmp.append(x['name'])
    df.job_category = tmp
    df.publish_time = df.publish_time.apply(
        lambda x: pd.Timestamp(x, unit="ms"))
    df.drop(columns=['sub_title', 'job_hot_flag', 'job_subject'], inplace=True)
    df.to_csv("bytedance_jobs.csv", mode="a", header=not os.path.exists("bytedance_jobs.csv"), index=False)
    print(",".join(df.title.head(10)))
# 对结果去重
df = pd.read_csv("bytedance_jobs.csv")
df.drop_duplicates(inplace=True)
df.to_csv("bytedance_jobs.csv", index=False)
print("共爬取", df.shape[0], "行无重复数据")
复制代码

 

结果:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

仅7.3秒爬完了字节跳动1W+以上的职位信息。

可以读取看看:

import pandas as pd

df = pd.read_csv("bytedance_jobs.csv")
df

 

结果:

Python爬取大厂找招聘数据,看看大家的差别在哪里

 

有1万个以上的职位信息。


相关教程