用Pyinstaller打包Scrapy專案問題解決!!!(轉載)
使用Pyinstaller打包Scrapy專案的時候遇到各種坑,首先感謝La_vie_est_belle分享的文章,給了很大的幫助。結合他的分享我稍微整理一下。遇到的最難的坑,文末有提到。
轉載地址:https://blog.csdn.net/la_vie_est_belle/article/details/79017358
這個是我的專案目錄:
眾所周知,dist,build和crawl.spec是打包後生成的檔案。
思路就是:寫一個指令碼來執行我們的Scrapy專案,接著用Pyinstaller將該指令碼轉化為exe檔案。
剛開始想用以下指令碼檔案來執行:
from scrapy import cmdline
cmdline.execute("scrapy crawl SpiderName".split())
最終發現不行(所以想用該指令碼來打包的同學三思。。不過你當然也可以試試。。。說不定可以解決。)
後來突然想到Scrapy文件有專門講是怎麼執行爬蟲的:https://doc.scrapy.org/en/latest/topics/practices.html
- from scrapy.crawler import CrawlerProcess
- from scrapy.utils.project import get_project_settings
- process = CrawlerProcess(get_project_settings())
- # 'followall' is the name of one of the spiders of the project.
- process.crawl('followall', domain='scrapinghub.com')
- process.start() # the script will block here until the crawling is finished
然後開始用Pyinstaller打包:
在專案下shift+右鍵,然後點選‘’在此處開啟命令視窗‘’,輸入:
pyinstaller crawl.py
最終生成dist,build和crawl.spec這三個檔案。
開啟dist->crawl->crawl.exe,會發現有閃退現象(解決辦法就是把該exe檔案拖入cmd中執行)
在cmd中我們發現錯誤是缺少scrapy資料夾下的VERSION
接下來你需要在crawl.exe同目錄下新建一個scrapy資料夾
然後到你安裝的scrapy資料夾中把VERSION和mime.types兩個檔案複製到剛才建立的scrapy資料夾中(如果只複製VERSION的話,那之後還會提示找不到mime.types檔案,所以這裡就兩個一塊講了)
完成後再執行crawl.exe檔案,發現提示缺少模組,缺哪一個就在crawl.py中import哪一個,於是乎,好像差點要把整個scrapy框架都import進來。。。(這裡花了我蠻久時間)
以下就是提示缺少的模組
- import robotparser
- import scrapy.spiderloader
- import scrapy.statscollectors
- import scrapy.logformatter
- import scrapy.dupefilters
- import scrapy.squeues
- import scrapy.extensions.spiderstate
- import scrapy.extensions.corestats
- import scrapy.extensions.telnet
- import scrapy.extensions.logstats
- import scrapy.extensions.memusage
- import scrapy.extensions.memdebug
- import scrapy.extensions.feedexport
- import scrapy.extensions.closespider
- import scrapy.extensions.debug
- import scrapy.extensions.httpcache
- import scrapy.extensions.statsmailer
- import scrapy.extensions.throttle
- import scrapy.core.scheduler
- import scrapy.core.engine
- import scrapy.core.scraper
- import scrapy.core.spidermw
- import scrapy.core.downloader
- import scrapy.downloadermiddlewares.stats
- import scrapy.downloadermiddlewares.httpcache
- import scrapy.downloadermiddlewares.cookies
- import scrapy.downloadermiddlewares.useragent
- import scrapy.downloadermiddlewares.httpproxy
- import scrapy.downloadermiddlewares.ajaxcrawl
- import scrapy.downloadermiddlewares.chunked
- import scrapy.downloadermiddlewares.decompression
- import scrapy.downloadermiddlewares.defaultheaders
- import scrapy.downloadermiddlewares.downloadtimeout
- import scrapy.downloadermiddlewares.httpauth
- import scrapy.downloadermiddlewares.httpcompression
- import scrapy.downloadermiddlewares.redirect
- import scrapy.downloadermiddlewares.retry
- import scrapy.downloadermiddlewares.robotstxt
- import scrapy.spidermiddlewares.depth
- import scrapy.spidermiddlewares.httperror
- import scrapy.spidermiddlewares.offsite
- import scrapy.spidermiddlewares.referer
- import scrapy.spidermiddlewares.urllength
- import scrapy.pipelines
- import scrapy.core.downloader.handlers.http
- import scrapy.core.downloader.contextfactory
- import scrapy.pipelines.images # 用到圖片管道
- import openpyxl # 用到openpyxl庫
上面沒有註釋的那些行應該就是要必須引入的了。
所以整個crawl.py檔案看起來是這樣的(為了方便看官區分,我加了一些註釋)
- # -*- coding: utf-8 -*-
- from scrapy.crawler import CrawlerProcess
- from scrapy.utils.project import get_project_settings
- # 這裡是必須引入的
- import robotparser
- import scrapy.spiderloader
- import scrapy.statscollectors
- import scrapy.logformatter
- import scrapy.dupefilters
- import scrapy.squeues
- import scrapy.extensions.spiderstate
- import scrapy.extensions.corestats
- import scrapy.extensions.telnet
- import scrapy.extensions.logstats
- import scrapy.extensions.memusage
- import scrapy.extensions.memdebug
- import scrapy.extensions.feedexport
- import scrapy.extensions.closespider
- import scrapy.extensions.debug
- import scrapy.extensions.httpcache
- import scrapy.extensions.statsmailer
- import scrapy.extensions.throttle
- import scrapy.core.scheduler
- import scrapy.core.engine
- import scrapy.core.scraper
- import scrapy.core.spidermw
- import scrapy.core.downloader
- import scrapy.downloadermiddlewares.stats
- import scrapy.downloadermiddlewares.httpcache
- import scrapy.downloadermiddlewares.cookies
- import scrapy.downloadermiddlewares.useragent
- import scrapy.downloadermiddlewares.httpproxy
- import scrapy.downloadermiddlewares.ajaxcrawl
- import scrapy.downloadermiddlewares.chunked
- import scrapy.downloadermiddlewares.decompression
- import scrapy.downloadermiddlewares.defaultheaders
- import scrapy.downloadermiddlewares.downloadtimeout
- import scrapy.downloadermiddlewares.httpauth
- import scrapy.downloadermiddlewares.httpcompression
- import scrapy.downloadermiddlewares.redirect
- import scrapy.downloadermiddlewares.retry
- import scrapy.downloadermiddlewares.robotstxt
- import scrapy.spidermiddlewares.depth
- import scrapy.spidermiddlewares.httperror
- import scrapy.spidermiddlewares.offsite
- import scrapy.spidermiddlewares.referer
- import scrapy.spidermiddlewares.urllength
- import scrapy.pipelines
- import scrapy.core.downloader.handlers.http
- import scrapy.core.downloader.contextfactory
- # 以下兩行是我的專案有用到的
- import scrapy.pipelines.images # 用到圖片管道
- import openpyxl # 用到openpyxl庫
- process = CrawlerProcess(get_project_settings())
- # 'Books' is the name of one of the spiders of the project.
- process.crawl('Books')
- process.start() # the script will block here until the crawling is finished
因為我這個例子專案用到一張圖片資源blank.png(當爬取不到圖片的時候就用這個白色圖片代替),所以還需要把這張圖片放到crawl.exe同路徑下。
好,到這裡就差不多可以了。重新用Pyinstaller打包:pyinstaller crawl.py
完成後點選dist->crawl->crawl.exe
以為到這裡就完成了,結果提示:KeyError: 'Spider not found:' ,難道是爬蟲名不對,重新確認一遍後,沒有任何問題,沒打包前執行是正常的。嘗試了各種方法後發現問題了。
Pyinstaller打包的時候,目錄要進入到專案目錄中去,不然打包後就容易出這個問題,即進入:Scrapy_Books。
重新打包,執行,提示:not found mould xxxx.aaaa,在 crawl.py中匯入模組依舊不行,原因是這個模組是我自己寫的一個介面,呼叫傳送郵件的,結果怎麼調整都不對。後面乾脆寫到piplines裡去。
重新打包,執行。這次終於可以了。不知道為啥Pyinstaller打包,自己寫的介面無法打包進入,嘗試過pyinstaller crawl.py -p +介面路徑 打包依舊未成功。最後放棄整合到了piplines裡了。
雖然麻煩,但總算是解決了。。。
總之一句話:缺什麼,import什麼
還遇到一個問題,就是打包好後,移植到其他電腦上,自己電腦是64位系統,移植過去的是32位系統,結果無法執行,存在相容問題。各種查詢後,據說32位系統的,要在32位系統上打包。未驗證,不知道有沒有其他方式可以直接在64位系統裡打包32位的包。望知道的大神路過能指點一二。