scrapy的一個簡單小項目


使用scrapy抓取目標url下所有的課程名和價格,並將數據保存為json格式url=http://www.tanzhouedu.com/mall/course/initAllCourse

觀察網頁並分析該網頁:

是一個ajax加載的頁面,每次數據變化,但是url不變化,
通過查看headers中的信息,得到每次點擊下一頁時真正請求的鏈接url
觀察發現每次翻頁,請求變化的是offset的數值和時間戳

1.創建項目

使用命令:scrapy startproject 'project_name'得到對象的項目文件夾,里面包含scrapy的一些必要組件

如下:

具體文件含義,參見鏈接:http://www.cnblogs.com/pythoner6833/p/9012292.html

2.明確抓取目標。

編輯items.py文件,定義好需要抓取的數據字段名

代碼如下:

# -*- coding: utf-8 -*-

# Define here the models for your scraped items
#
# See documentation in:
# https://doc.scrapy.org/en/latest/topics/items.html

import scrapy


class TanzhouItem(scrapy.Item):
    # define the fields for your item here like:
    # name = scrapy.Field()
    """
    定義爬取的目標,本案例中只爬取標題和價格兩個內容
    所以定義兩個字段
    """
    # 課程金額
    money = scrapy.Field()
    # 課程名稱
    title = scrapy.Field()

 

3.編輯爬蟲。

進入spiders文件夾下,創建爬蟲文件,命令:scrapy  genspider  'spider_name'  "start_url"

就會得到一個以spider_name命名的文件,在里面編寫爬蟲的邏輯

# -*- coding: utf-8 -*-
"""
抓取:http://www.tanzhouedu.com/mall/course/initAllCourse
下的所有課程名稱和價格,並保存為json格式

網頁分析:
是一個ajax加載的頁面,每次數據變化,但是url不變化,
通過查看headers中的信息,得到每次點擊下一頁時真正請求的鏈接url
觀察發現每次翻頁,請求變化的是offset的數值和時間戳


1.首先創建一個爬蟲項目。
    使用命令:scrapy startproject 'pro_name'  # pro_name是項目名稱
    輸入命令后,會自動出現一個用pro_name的項目文件夾,
    里面包含一個scrapy項目所必要的文件

2.明確爬取目標,編輯items.py文件,定義需要爬取的字段。

3.編輯爬蟲。進入spiders文件夾下,創建爬蟲文件。
    使用命令:scrapy genspider 'spider_name' 'start_url'
    生成一個爬蟲,名字為spider_name,初始爬取url為start_url
    會在spiders文件夾下生成一個spider_name.py的文件,
    里面包含一個name=‘spider_name’, name是不同爬蟲的唯一標識,不能重復
    start_url是爬蟲的第一個爬取鏈接(可修改),並返回一個response
    解析response中的其他可用鏈接和數據

4.將爬取到的數據通過yield,丟給pipelines.py文件保存,
在pipelines.py文件中編寫保存文件的邏輯

5.運行爬蟲,使用命令:scrapy crawl "spider_name"

注:在配置文件中打開頭信息和管道
"""

import scrapy

# 從items文件中導入已經寫好的待爬取目標(money和title)
from tanzhou.items import TanzhouItem
import time

class TzSpider(scrapy.Spider):
    name = 'tz'  # 爬蟲名稱。區別於其他爬蟲的唯一ID。
    allowed_domains = ['tanzhouedu.com']  # 允許域名

    # 爬蟲的第一個爬取鏈接,啟動爬蟲就執行,並返回一個response交給parse函數
    start_urls = ['http://www.tanzhouedu.com/mall/course/initAllCourse']
    offset = 0

    def parse(self, response):
        item = TanzhouItem()  # 實例化。實例一個爬取字段的實例對象。

        # 通過xpath解析response,並從中提取數據,得到xpath對象
        node_list = response.xpath('//div[@id="newCourse"]/div/div/ul/li')
        for node in node_list:
            # extract_first() 是取對象的值,得到一個字符串
            item['money'] = node.xpath('./div/span/text()').extract_first()
            item['title'] = node.xpath('./a/@title').extract_first()

            yield item
            # yield將item返回,scrapy_engine通過管道,將item交給pipelines
            # pipelines.py文件用於爬取結果的保存

        if node_list == []:
            """
            下一頁到最后時,xpath匹配到的是一個空列表
            此時已沒有可爬取頁面,return結束程序。
            """
            return

        self.offset += 20  # 構造變化的offset,每次翻頁增加20

        # yield將新的請求丟給調度器,然后交給下載器,繼續下載頁面,得到response
        # callback回調parse函數,實現循環抓取
        yield scrapy.Request(url="http://www.tanzhouedu.com/mall/course/initAllCourse?params.offset="
            + str(self.offset) +"&params.num=20&keyword=&_=" + str(int(time.time() * 1000)), callback=self.parse)

 

4.編寫保存數據的邏輯。

在pipelines.py文件中編寫保存數據的邏輯

# -*- coding: utf-8 -*-

# Define your item pipelines here
#
# Don't forget to add your pipeline to the ITEM_PIPELINES setting
# See: https://doc.scrapy.org/en/latest/topics/item-pipeline.html

import json

class TanzhouPipeline(object):
    """
    編寫爬取到的數據保存的邏輯
    """
    def __init__(self):
        """
        可選擇實現,對參數做一些初始化的處理
        """
        pass

    def open_spider(self, spider):
        """
        重寫open_spider函數,該函數在爬蟲啟動時就自動執行
        :param spider:
        :return:
        """
        self.file = open("tz.json", 'w', encoding='utf-8')

    def process_item(self, item, spider):
        """
        將yield丟過來的數據進行一定的處理並保存
        :param item:
        :param spider:
        :return:
        """
        # 管道傳過來的數據item是一個對象,將它轉化為字典,然后存儲
        content = json.dumps(dict(item), ensure_ascii=False) + '\n'
        self.file.write(content)
        return item

    def close_spider(self, spider):
        """
        重寫該函數,爬蟲執行完畢后執行該函數
        :param spider:
        :return:
        """
        self.file.close()

 

5.運行爬蟲。

使用命令:scrapy crawl  "spider_name"

 運行結果:

得到一個保存有抓取結果的json文件

 完整代碼

參見:https://github.com/zInPython/tanzhou


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM