分析京東網站結構


瀏覽器調試分析

商品列表url分析

打開京東網站,隨便輸入一個關鍵字,點開抓包工具(ctrl+F)

 看到不是動態加載的是不是有點激動?但是你拿到的並不是全數據,為什么這么說呢,往下看

當滑動滾輪時,出現了新數據

 查看請求url及參數

 

嘗試去掉不必要的參數,經過多次的嘗試發現,要獲取到數據只需要想它發送請求就可以拿到數據:

url:https://search.jd.com/s_new.php?keyword=電腦&page=1&s=30
# 注意page與s的關系,注意最大頁碼的值(商品頁面顯示頁碼為100,那么你在拼接url時,最大頁碼必須是100*2)
參數:   keyword:搜索的關鍵字   page:頁碼數   s:每一頁的數據條數

但是,你會發現他只能拿到三十幾條左右的數據,而正常是當滾輪滑動到底端時會有六十幾條數據,這時候不要慌,因為你會發現當url的page=2&s=60時,就會出現,原來滾輪滑動到底部后獲取的新數據

因此,當滾輪滑動到底部時,原來的1頁,展示了兩頁的數據

既然明白了他們的數據請求方式,那么拿到所有的商品列表就很簡單了

 拿到后發送請求獲取到response,進行xpath解析就可以了

詳情頁評論分析  

上面我們已經獲取了商品列表頁需要的數據,記得拿詳情頁的url

接下來繼續分析詳情頁數據接口的url:隨便點擊一個商品,抓包,全局搜索

 查看請求的url:

 分析url和參數:

將這里的請求url輸入瀏覽器地址欄,看能否拿到數據:

 很明顯,可以拿到數據,接着我們看攜帶的參數

url:https://club.jd.com/comment/productPageComments.action?callback=fetchJSON_comment98&productId=100006581268&score=0&sortType=5&page=0&pageSize=10&isShadowSku=0&fold=1

 參數:
        callback: fetchJSON_comment98  # 這是個回調函數
        productId: 100006581268           # 商品id
        score: 0                             # 不知道啥東西
        sortType: 5                        # 不知道啥東西
        page: 0                             # 評論的頁碼 
        pageSize: 10                      # 每頁顯示幾條數據 
        isShadowSku: 0        
        fold: 1

我們雖然拿到這些參數,但是,你會疑惑這些參數是不是通過js動態生成的?怎么獲取這些參數呢?

其實:對於這種情況來說,先不要老是想着找它的來源,因為有時候就單純的獲取數據來說,有些參數並不是必須要攜帶的

 這里,我們嘗試去掉一些不必要的參數

url:https://club.jd.com/comment/productPageComments.action?productId=100003383325&score=0&sortType=5&page=3&pageSize=10

參數:
    productId:商品id
    score:不知道啥東西,但這個必須帶
    sortType:同上
    page:評論的頁碼
    pageSize:每頁評論的條數

至此,我們的評論數據接口就搞定了

解決只能爬取70條左右的評論的問題

京東做了反扒機制,當你訪問評率過快或者使用單個ip訪問的時候只允許你拿70左右的數據,如何解決呢?

ip代理池+設置請求發送的間隔時間:以scrapy框架為例:

IP代理池(本人ip代理是從網上爬取的免費代理,存放在數據庫中):

下載器中間件文件:

class AllJdDownloaderMiddleware:
    # Not all methods need to be defined. If a method is not defined,
    # scrapy acts as if the downloader middleware does not modify the
    # passed objects.
    conn = None
    cursor = None
    proxy_list = []

    def __init__(self):
        self.conn = pymysql.Connect(host=MYSQL_IPS_CONNECT['host'], user=MYSQL_IPS_CONNECT['user'],
                                    port=MYSQL_IPS_CONNECT['port'], password=MYSQL_IPS_CONNECT['password'],
                                    db=MYSQL_IPS_CONNECT['db_name'],
                                    charset='utf8')
        self.cursor = self.conn.cursor()
        sql = 'select ip,port,http_type from ips'
        try:
            self.cursor.execute(sql)
            # 取數據庫中所有的ip
            all_ip = self.cursor.fetchall()
            if not all_ip:
                raise ValueError('您沒有代理ip了!')
            for ips in all_ip:
                ip, port, http_type = ips
                self.proxy_list.append(f"{http_type.lower()}s://{ip}:{port}")
        except Exception as e:
            print(e)

    @classmethod
    def from_crawler(cls, crawler):
        # This method is used by Scrapy to create your spiders.
        s = cls()
        crawler.signals.connect(s.spider_opened, signal=signals.spider_opened)
        return s

    def process_request(self, request, spider):
        request.meta['http_proxy'] = random.choice(self.proxy_list)
        request.cookie = COOKIE

        return None

    def process_response(self, request, response, spider):
        print(response['cookies'])
        if (spider.comment_url.split('?')[0] in request.url):
            if not response.text:
                # 如果評論頁面數量數據取不到,換代理重新請求
                request.meta['http_proxy'] = random.choice(self.proxy_list)
                return request
        return response

    def process_exception(self, request, exception, spider):
        # 捕獲到異常請求,換代理ip,重新發送請求
        request.meta['http_proxy'] = random.choice(self.proxy_list)
        return request

    def spider_opened(self, spider):
        spider.logger.info('Spider opened: %s' % spider.name)

設置請求發送間隔時間:

settings.py

DOWNLOAD_DELAY = 2 # 單位秒

然后你就可以開搞了。

本人此次項目獲取的是每個商品的價格、好評、差評、好評度等數據 ,並未爬取評論,但數據接口是相同的,看一下運行結果

 總結一下分析的url:

商品列表url:
for page in range(1, 200):
    url = 'https://search.jd.com/s_new.php?keyword=%s&page=%d&s=%d' % ('電腦', page, page * 30)
參數:
    keyword:搜索關鍵字
    page:列表頁碼
    s:展示的商品數量
    
評論列表url:
for page in range(0,100)
    url = 'https://club.jd.com/comment/productPageComments.action?productId=%s&score=0&sortType=5&page=%d&pageSize=%d' % ('100003383325',page,10)
參數:
    productId=100003383325 # 商品id,其他參數不變
    score=0
    sortType=5
    page=0       # 評論頁碼數,
    pageSize=10  # 每頁評論條數

完。。。。。。。。。。。。。

 


免責聲明!

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



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