⌈ 传知代码 ⌋ 利用scrapy框架练习爬虫

news2025/1/6 19:28:03

💛前情提要💛

本文是传知代码平台中的相关前沿知识与技术的分享~

接下来我们即将进入一个全新的空间,对技术有一个全新的视角~

本文所涉及所有资源均在传知代码平台可获取

以下的内容一定会让你对AI 赋能时代有一个颠覆性的认识哦!!!

以下内容干货满满,跟上步伐吧~


📌导航小助手📌

  • 💡本章重点
  • 🍞一. 概述
  • 🍞二. 演示效果
  • 🍞三.核心逻辑
  • 🫓总结


💡本章重点

  • 利用scrapy框架练习爬虫

🍞一. 概述

运用Python语言编程知识及实现网络数据采集的各种Python第三方库、Scrapy框架等实现技术爬取网页信息,要求爬取的网页信息至少包括两种类型:标题列表页(该页要包括分页功能)和详情页。

在这里插入图片描述


🍞二. 演示效果

整体框架

在这里插入图片描述

文件导出

在这里插入图片描述

数据库导出

在这里插入图片描述


🍞三.核心逻辑

编写对应蜘蛛程序

    def start_requests(self):
        # 爬列表页 只爬1页
        for page in range(1, 2):
            yield Request(url="https://jobs.51job.com/beijing/p{}".format(page), callback=self.parse)

    def parse(self, response: HtmlResponse, **kwargs):
        # time.sleep(3)
        # 查看网页内容
        # print(response.text)
        sel = Selector(response)
        # 浏览器F12 选中目标,鼠标右击copy selector
        # 得到原始css选择器 body > div.maincenter > div.mcon > div.left > div.detlist.gbox > div:nth-child(7)
        title_text = sel.css('title::text').extract_first()
        # title_text = sel.xpath('//title/text()').extract_first()
        # 测试一下标题能不能获取到,如果不能,几乎可以肯定有问题
        print("title_text:", title_text)

        list_items = sel.css('div.detlist.gbox > div')

        for list_item in list_items:
            job_item = JobItem()
            job_id = list_item.css('input::attr(value)').extract_first()
            title = list_item.css('p.info > span.title > a::text').extract_first()
            location = list_item.css('p.info > span.location.name::text').extract_first()
            salary = list_item.css('p.info > span.location:not(.name)::text').extract_first()
            # 得到的是 '学历要求:本科' , 需要处理一下得到 '本科'
            degree = list_item.css('p.order::text').extract_first().split(':')[1].strip()
            # 详情页面
            detail_url = list_item.css('p.info > span.title > a::attr(href)').extract_first()
            print("test:", job_id, title, location, salary, degree, detail_url)

            job_item['job_id'] = job_id
            job_item['title'] = title
            job_item['location'] = location
            job_item['salary'] = salary
            job_item['degree'] = degree
            yield Request(url=detail_url,
                          callback=parse_detail,
                          cb_kwargs={'item': job_item})


def parse_detail(response: HtmlResponse, **kwargs):
    job_item = kwargs['item']
    sel = Selector(response)
    # 原始css选择器 div.tCompany_main > div.tBorderTop_box> div.tmsg.inbox
    company_detail = sel.css('div.tmsg.inbox::text').extract_first()
    print('company_detail:', company_detail)
    job_item['company_detail'] = company_detail
    yield job_item

构造Items

class JobItem(scrapy.Item):
    job_id = scrapy.Field()
    title = scrapy.Field()
    location = scrapy.Field()
    salary = scrapy.Field()
    degree = scrapy.Field()
    company_detail = scrapy.Field()

编写文件管道(Excel)

class ExcelPipeline:
    def __init__(self):
        self.wb = openpyxl.Workbook()
        self.ws = self.wb.active
        self.ws.title = 'Jobs'
        self.ws.append(['职位ID', '职位',
                        '工作地点', '薪资范围',
                        '学历要求', '公司详情'])

    def open_spider(self, spider):
        pass

    def close_spider(self, spider):
        self.wb.save('51jobs.xlsx')

    def process_item(self, item, spider):
        company_detail, degree, job_id, location, salary, title = get_infos(item)
        # self.ws.append([job_id, title, location, salary, degree, company_detail])
        self.ws.append((job_id, title, location, salary, degree, company_detail))
        return item

编写数据库管道及建表

class DbPipeline:
    def __init__(self):
        self.conn = pymysql.connect(host='localhost', port=3306, user='root', password='root',
                                    db='spyder', charset='utf8mb4')
        self.cursor = self.conn.cursor()

    def close_spider(self, spider):
        print('commit------------------------------')
        self.conn.commit()
        self.conn.close()

    def process_item(self, item, spider):
        company_detail, degree, job_id, location, salary, title = get_infos(item)
        self.cursor.execute('insert into tb_51job_items (job_id, title, location, salary, degree, company_detail) '
                            'values (%s,%s,%s,%s,%s,%s)',
                            (job_id, title, location, salary, degree, company_detail))
        return item
CREATE TABLE spyder.tb_51job_items (
	job_id varchar(100) NULL COMMENT '职位ID',
	title varchar(100) NULL COMMENT '职位',
	location varchar(100) NULL COMMENT '工作地点',
	salary varchar(100) NULL COMMENT '薪资范围',
	`degree` varchar(100) NULL COMMENT '学历要求',
	company_detail varchar(2000) NULL COMMENT '公司详情'
)
ENGINE=InnoDB
DEFAULT CHARSET=utf8mb4
COLLATE=utf8mb4_0900_ai_ci;

配置管道及优先级

ITEM_PIPELINES = {
   "spider51job.pipelines.ExcelPipeline": 300,
   "spider51job.pipelines.DbPipeline": 400
}

编写中间件代码

    def __init__(self):
        self.browser = create_chrome_driver(headless=False)
        self.browser.get('https://jobs.51job.com')
        # 初始化时, 先访问主页, 得到cookie信息
        cookie_file = '51job_cookies.json'
        # 这边也可以先人工运行test_generate_cookies.py提前生成好cookies信息,下面直接add_cookies使用就可以了
        generate_cookies(self.browser, cookie_file)
        add_cookies(self.browser, cookie_file)

    def __del__(self):
        # 爬完关闭浏览器
        self.browser.close()

    def process_request(self, request, spider):
        # Called for each request that goes through the downloader
        # middleware.

        # Must either:
        # - return None: continue processing this request
        # - or return a Response object
        # - or return a Request object
        # - or raise IgnoreRequest: process_exception() methods of
        #   installed downloader middleware will be called
        self.browser.get(request.url)
        # time.sleep(5)
        if request.url.startswith('https://jobs.51job.com/beijing/p'):
            wait_obj = WebDriverWait(self.browser, 10)
            wait_obj.until(expected_conditions.presence_of_element_located((By.CSS_SELECTOR, '#searchForm')))
            print('爬的时候可能也被反爬,需要人工滑块!')
        # page_source这个可以获取到动态页面的源代码
        return HtmlResponse(url=request.url, body=self.browser.page_source,
                            encoding='utf-8', request=request)

🫓总结

综上,我们基本了解了“一项全新的技术啦” 🍭 ~~

恭喜你的内功又双叒叕得到了提高!!!

感谢你们的阅读😆

后续还会继续更新💓,欢迎持续关注📌哟~

💫如果有错误❌,欢迎指正呀💫

✨如果觉得收获满满,可以点点赞👍支持一下哟~✨

【传知科技 – 了解更多新知识】

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1960263.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

56_Redis简单命令

一、引言 1.1 数据库压力过大 由于用户量增大,请求数量也随之增大,数据压力过大 一个请求的url 背后可能有有4-5个 sql的操作 每秒钟 qps(并发数) 1000 背后的sql操作 4000-5000mysql 单机并发量读写 8000-10000 &#x…

素数提升运算时间得算法

我们在计算素数的一种简便算法&#xff0c;用到另一个库math.h之后给大家详细的解释原理 #include<stdio.h> #include<math.h> int main() {int i 0;for (i 101; i < 200; i 2){int flag 1;int j 0;for (j 2; j < sqrt(i); j){if (i % j 0){flag 0;b…

ITSS四级认证费用是多少?

信息技术服务标准&#xff08;ITSS&#xff09;认证是评估一个企业在信息技术服务领域能力的标准之一&#xff0c;它涵盖了从基础标准、支撑标准到基于业务的需求侧和供给侧标准的全面内容。 具体条件 独立法人地位&#xff1a;申请单位需要具备独立法人地位&#xff0c;这是四…

如何使用rdma-core来实现RDMA操作

rdma-core 是一个开源项目&#xff0c;为远程直接内存访问&#xff08;RDMA&#xff09;提供用户空间的支持。它包括 RDMA 设备的驱动程序、库和工具&#xff0c;旨在简化 RDMA 应用的开发和部署。 基础知识参考博文&#xff1a; 一文带你了解什么是RDMA RDMA 高性能架构基本…

day07 项目启动以及git

spring框架 spring 负责整合各种框架&#xff0c;把new对象的部分交给spring去做&#xff0c;对象new不出来&#xff0c;项目就启动不起来&#xff0c;这样可以有效保证所需要的对象都在容器中存在&#xff0c;后续的部分都可以顺利执行控制反转&#xff1a;业务对象创建依赖资…

零基础入门转录组数据分析——机器学习算法之lasso

零基础入门转录组数据分析——机器学习算法之lasso 目录 零基础入门转录组数据分析——机器学习算法之lasso1. Lasso基础知识2. Lasso&#xff08;Rstudio&#xff09;——代码实操2. 1 数据处理2. 2 构建Lasso模型2. 3 提取Lasso关键基因2. 4 Lasso结果简单可视化 1. Lasso基础…

高度偏斜特征处理:log(x)、sqrt(x)、box-cox、Yeo-Johnson

一、概念 高度偏斜的特征 &#xff1a; 数据分布不均匀、不对称的特征 处理之后&#xff1a;使其分布更接近正态分布或至少减少偏斜程度 二、处理方法 1、对数变换&#xff1a;log(x) 适用于右偏数据压缩大值&#xff0c;拉伸小值 2、平方根变换&#xff1a;sqrt(x) 对右…

臂式血压计电子方案ocba设计与开发

臂式血压计是运用电子技术与血压间接测量原理进行血压测量的医疗设备。臂式血压计有臂式、腕式、手表式之分&#xff1b;其电子技术已经历了最原始的第一代&#xff08;机械式定速排气阀&#xff09;、第二代&#xff08;电子伺服阀&#xff09;、第三代&#xff08;加压同步测…

学习测试12-车(略)

系统讲解&#xff0c;可以在懂车帝网站去了解汽车结构

商用密码测评之对HTTPS(TLS)协议中各个参数解释

1、TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 是一个广泛使用的TLS&#xff08;传输层安全协议&#xff09;加密套件&#xff0c;它结合了多种技术和算法来确保网络通信的安全。下面是对该加密套件中各个参数的详细解释&#xff1a; 1. TLS 定义&#xff1a;TLS&#xff08;传…

【文件解析漏洞】实战详解!

漏洞描述&#xff1a; 文件解析漏洞是由于中间件错误的将任意格式的文件解析成网页可执行文件&#xff0c;配合文件上传漏洞进行GetShell的漏洞! IIS解析漏洞&#xff1a; IIS6.X&#xff1a; 方式一:目录解析 在网站下建立文件夹的名字为.asp/.asa 的文件夹&#xff0c;其目…

【前端 · 面试 】JavaScript 之你不一定会的基础题(一)

最近我在做前端面试题总结系列&#xff0c;感兴趣的朋友可以添加关注&#xff0c;欢迎指正、交流。 争取每个知识点能够多总结一些&#xff0c;至少要做到在面试时&#xff0c;针对每个知识点都可以侃起来&#xff0c;不至于哑火。 JavaScript 之你不一定会的基础题 前言 面试往…

python中list的深拷贝和浅拷贝

其实这还是涉及到python中的可变对象和不可变对象的概念。 https://www.cnblogs.com/poloyy/p/15073168.html # -*- coding: utf-8 -*-person [name, [savings, 100.00]] hubby person[:] # slice copy wifey list(person) # fac func copy a [id(x) for x in person] b …

【Vue3】watch 监视多种类型数据

【Vue3】watch 监视多种类型数据 背景简介开发环境开发步骤及源码 背景 随着年龄的增长&#xff0c;很多曾经烂熟于心的技术原理已被岁月摩擦得愈发模糊起来&#xff0c;技术出身的人总是很难放下一些执念&#xff0c;遂将这些知识整理成文&#xff0c;以纪念曾经努力学习奋斗…

新闻稿的写作格式,干货分享

随着互联网的发展&#xff0c;新闻稿在互联网上的地位非常高&#xff0c;新闻稿对比一般软文来说内容质量偏高而且还具备&#xff1a;严谨、时效、可观的特点。 撰写新闻稿主要就是突出最新鲜、最重要的事实&#xff0c;同时&#xff0c;新闻稿也是文字简洁&#xff0c;并且时效…

【nginx、apache】网站只有首页可以正常打开,其他页面都实现404

【nginx、apache】网站只有首页可以正常打开&#xff0c;其他页面都实现404 1、检查伪静态规则&#xff08;中枪&#xff09;

【剑指offer】

剑指offer 面试题67&#xff1a;字符串转成整数面试题1&#xff1a;赋值运算符函数面试题3&#xff1a;数组中重复的数字 面试题67&#xff1a;字符串转成整数 LeedCode&#xff1a;LCR 192. 把字符串转换成整数 (atoi) 测试atoi的功能和异常效果 #include <iostream> #…

【Linux】全志Tina配置屏幕时钟的方法

一、文件位置 V:\f1c100s\Evenurs\f1c100s\tina\device\config\chips\c200s\configs\F1C200s\sys_config.fex 二、文件内容 三、介绍 在此处可以修改屏幕的频率&#xff0c;当前为21MHz。 四、总结 注意选择对应的屏幕的参数&#xff0c;sdk所支持的屏幕信息都在此文件夹中…

嵌入式C++、STM32、Flask框架、SQL、ROS系统和MQTT协议通讯:智能药盒及物联网数据监测设计思路(代码示例)

目录 项目概述 系统设计 硬件设计 软件设计 系统架构图 代码实现 1. 开发环境 2. STM32 微控制器代码示例 3. ROS 节点代码示例 4. 后端服务器代码示例&#xff08;Flask&#xff09; 数据库部分 3.4 删除药物记录 项目概述 随着老龄化社会的加剧&#xff0c;患者…

钢琴模拟器

文章目录 钢琴模拟器代码结构HTML结构CSS样式JavaScript功能 源码效果图 钢琴模拟器 代码结构 HTML结构 <html>: HTML文档的根元素。 <head>: 包含文档的元数据。 <base>: 指定相对URL的基准。 <title>: 指定页面的标题。 <style>: 包含嵌入的…