爬蟲(十四):Scrapy框架(一) 初識Scrapy、第一個案例

来源:https://www.cnblogs.com/liuhui0308/archive/2019/12/27/12107739.html
-Advertisement-
Play Games

1. Scrapy框架 Scrapy功能非常強大,爬取效率高,相關擴展組件多,可配置和可擴展程度非常高,它幾乎可以應對所有反爬網站,是目前Python中使用最廣泛的爬蟲框架。 1.1 Scrapy介紹 1.1.1 架構介紹 Scrapy是一個基於Twisted的非同步處理框架,是純Python實現的爬 ...


1. Scrapy框架

Scrapy功能非常強大,爬取效率高,相關擴展組件多,可配置和可擴展程度非常高,它幾乎可以應對所有反爬網站,是目前Python中使用最廣泛的爬蟲框架。

1.1 Scrapy介紹

1.1.1 架構介紹

Scrapy是一個基於Twisted的非同步處理框架,是純Python實現的爬蟲框架,其架構清晰,模塊之間的耦合程度低,可擴展性極強,可以靈活完成各種需求。我們只需要定製開發幾個模塊就可以輕鬆實現一個爬蟲。

它可以分為如下的幾個部分:

Engine:引擎,處理整個系統的數據流處理、觸發事務,是整個框架的核心。

Item:項目,它定義了爬取結果的數據結構,爬取的數據會被賦值成該Item對象。

Scheduler:調度器,接受引擎發過來的請求並將其加入隊列中,在引擎再次請求的時候將請求提供給引擎。

Downloader:下載器,下載網頁內容,並將網頁內容返回給蜘蛛。

Spiders:蜘蛛,其內定義了爬取的邏輯和網頁的解析規則,它主要負責解析響應並生成提取結果和新的請求。

Item Pipeline:項目管道,負責處理由蜘蛛從網頁中抽取的項目,它的主要任務是清洗、驗證和存儲數據。

Downloader Middlewares:下載器中間件,位於引擎和下載器之 的鉤子框架,主要處理引擎與下載器之間的請求及響應。

Spider Middlewares:蜘蛛中間件,位於引擎和蜘蛛之間的鉤子框架,主要處理蜘蛛輸入的響應和輸出的結果及新的請求。

1.1.2 數據流

Scrapy中的數據流由引擎控制,數據流的過程如下:

(1) Engine首先打開一個網站,找到處理該網站的Spider,並向該Spider請求第一個要爬取的URL。

(2) Engine從Spider中獲取到第一個要爬取的URL,並通過Scheduler以Request的形式調度。

(3) Engine向Scheduler請求下一個要爬取的URL。

(4) Scheduler返回下一個要爬取的URL給Engine,Engine將URL通過Downloader Middlewares發給 Downloader下載。

(5) 一旦頁面下載完畢,Downloader生成該頁面的Response,並將其通過Downloader Middlewares發送給Engine。

(6) Engine從下載器中接收到Response,並將其通過Spider Middleware發送給Spider處理。

(7) Spider處理Response,並返回爬取到的Item及新的Request給Engine。

(8) Engine將Spider返回的Item給Item Pipeline,將新的Request給Scheduler。

(9)重覆第(2)步到第(8)步,直到Scheduler中沒有更多的Request,Engine關閉該網站,爬取結束。

通過多個組件的相互協作、不同組件完成工作的不同、組件對非同步處理的支持Scrapy最大限度地利用了網路帶寬,大大提高了數據爬取和處理的效率。

1.1.3 項目結構

Scrapy框架是通過命令行來創建項目的,代碼的編寫還是需要IDE。項目創建之後,項目文件的格式如下所示:

scrapy.cfg

project/

  __init__.py

  items.py

  pipelines.py

  settings.py

  middlewares.py

  spiders/

    __init__.py

    spider1.py

    spider2.py

    ...

這裡各個文件的功能描述如下:

scrapy.cfg:它是Scrapy項目的配置文件,其內定義了項目的配置文件路徑、部署相關信息等內容

items.py:它定義Item數據結構,所有的Item的定義都可以放這裡。

pipelines.py:它定義Item Pipeline的實現,所有的Item Pipeline的實現都可以放這裡。

settings.py:它定義項目的全局配置。

middlewares.py:它定義Spider Middlewares和Downloader Middlewares的實現。

spiders:其內包含一個個Spider的實現,每個Spider都有一個文件。

1.2 Scrapy入門

接下來就寫一個簡單的項目,讓我們對Scrapy的基本用法和原理有大致的瞭解。

1.2.1 創建項目

首先安裝Scrapy模塊,再創建Scrapy項目。

pip install scrapy -i http://pypi.douban.com/simple/ --trusted-host pypi.douban.com

創建Scrapy一個項目,項目文件可以直接用scrapy命令生成:

scrapy startproject tutorial

這個命令可以在任意文件夾運行。

這個命令將會創建一個名為tutoria文件夾,文件夾結構如下所示:

1.2.2 創建Spider

Spider是自己定義的類,Scrapy用它來從網頁里抓取內容,並解析抓取的結果。不過這個類必須繼承Scrapy提供的Spider類scrapy.Spider,還要定義Spider的名稱和起始請求,以及怎樣處理爬取後的結果的方法。

也可以使用命令行創建一個Spider。比如要生成top250這個Spider。

cd tutorial

scrapy genspider top250 movie.douban.com/250

進入剛纔創建的tutorial文件夾,然後執行genspider命令。第一個參數是Spider名稱,第二個參數是網站功能變數名稱。執行完畢之後,spiders文件夾中多了一個quotes.py,它就是剛剛創建的Spider。

這裡有三個屬性——name、allowed_domains和start_urls,還有一個方法parse。

name,它是每個項目唯一的名字,用來區分不同的Spider。

allowed_domains,它是允許爬取的功能變數名稱,如果初始或後續的請求鏈接不是這個功能變數名稱下的,則請求鏈接會被過濾掉。

start_urls,它包含了Spider在啟動時爬取的url列表,初始請求是由它來定義的。

parse,它是Spider一個方法。預設情況下,被調用時start_urls裡面的鏈接構成的請求完成下載執行後,返回的響應就會作為唯一的參數傳遞給這個函數。該方法負責解析返回的響應、提取數據或者進一步生成要處理的請求。

1.2.3 創建Item

Item是保存爬取數據的容器,它的使用方法和字典類似。不過,相比字典,Item多了額外的保護機制,可以避免拼寫錯誤或者定義欄位錯誤。

創建Item需要繼承scrapy.Item類,並且定義類型為scrapy.Field的欄位。觀察目標網站,我們可以獲取到到內容有serial_number、movie_name、introduce、star、evaluate、describe。

定義Item,此時修改items.py:

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

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

import scrapy

class DoubanItem(scrapy.Item):
    # define the fields for your item here like:
    # name = scrapy.Field()
    serial_number = scrapy.Field()
    movie_name = scrapy.Field()
    introduce = scrapy.Field()
    star = scrapy.Field()
    evaluate = scrapy.Field()
    describe = scrapy.Field()

這裡定義了三個欄位,接下來爬取時我們會使用到這個Item。

1.2.4 解析Response

前面已經說了,parse()方法的參數resposne是start_urls裡面的鏈接爬取後的結果。所以在parse()方法中,我們可以直接對response變數包含的內容進行解析,比如瀏覽請求結果的網頁源代碼,或者進一步分析源代碼內容,或者找出結果中的鏈接而得到下一個請求。我們可以看到網頁中既有我們想要的結果,又有下一頁的鏈接,這兩部分內容我們都要進行處理。

首先看看網頁結構:

每一頁都有多個class為item的區塊,每個區塊內都包含serial_number、movie_name、introduce、star、evaluate、describe那麼我們先找出所有的item,然後提取每一個item中的內容。

提取的方式可以是css選擇器或XPath選擇器,top250.py的XPath改寫如下:

# -*- coding: utf-8 -*-
import scrapy

class Top250Spider(scrapy.Spider):
    name = 'top250'
    allowed_domains = ['movie.douban.com']
    start_urls = ['http://movie.douban.com/250/']

    def parse(self, response):
        movie_list = response.xpath('//div[@class="item"]')
        for i_item in movie_list:
            serial_number = i_item.xpath('.//em/text()').extract_first()
            movie_name = i_item.xpath('.//div[@class="hd"]/a/span[1]/text()').extract_first()
            content = i_item.xpath('.//div[@class="bd"]/p[1]/text()').extract()
            for i_content in content:
                introduce = "".join(i_content.split())
            star = i_item.xpath('.//span[@class="rating_num"]/text()').extract_first()
            evaluate = i_item.xpath('.//div[@class="star"]//span[4]/text()').extract_first()
            describe = i_item.xpath('.//p[@class="quote"]//span/text()').extract_first()

這裡首先利用選擇器選取所有的item,並將其賦值為movie_list變數,然後利用for迴圈對每個item遍歷,解析每個item的內容。

1.2.5 使用Item

前面定義了Item,接下來就要使用它了。Item可以理解為字典,不過在聲明的時候需要實例化。然後依次用剛纔解析的結果賦值Item的每一段,最後將Item返回即可。

修改top250.py文件:

# -*- coding: utf-8 -*-
import scrapy

class Top250Spider(scrapy.Spider):
    name = 'top250'
    allowed_domains = ['movie.douban.com']
    start_urls = ['http://movie.douban.com/250/']

    def parse(self, response):
        movie_list = response.xpath('//div[@class="item"]')
        for i_item in movie_list:
            douban_item = DoubanItem()
            douban_item['serial_number'] = i_item.xpath('.//em/text()').extract_first()
            douban_item['movie_name'] = i_item.xpath('.//div[@class="hd"]/a/span[1]/text()').extract_first()
            content = i_item.xpath('.//div[@class="bd"]/p[1]/text()').extract()
            for i_content in content:
                content_s = "".join(i_content.split())
                douban_item['introduce'] = content_s
            douban_item['star'] = i_item.xpath('.//span[@class="rating_num"]/text()').extract_first()
            douban_item['evaluate'] = i_item.xpath('.//div[@class="star"]//span[4]/text()').extract_first()
            douban_item['describe'] = i_item.xpath('.//p[@class="quote"]//span/text()').extract_first()
            yield douban_item

這樣首頁的所有內容都可以被解析出來,並被賦值成一個個DoubanItem。

1.2.6 後續Request

前面的操作實現了從初始頁面抓取內容。那麼,下一頁的內容該如何抓取?這就需要我們從當前頁面中找到信息來生成下一個請求,然後在下一個請求的頁面里找到信息再構造再下一個請求。這樣 迴圈往複迭代,從而實現整站的爬取。

將頁面拉到最底部,如圖:

這裡有後頁按鈕。查看它的源代碼,可以發現它的鏈接是?start=25&filter=,完整鏈接是:https://movie.douban.com/top250?start=25&filter=,通過這個鏈接我們就可以構造下一個請求。 

構造請求時需要用到scrapy.Request這裡我們傳遞兩個參數——url和callback。

Request參數:

url:它是請求鏈接。

callback:它是回調函數。當指定了該回調函數的請求完成之後,獲取到響應,引擎會將該響應作為參數傳遞給這個回調函數。回調函數進行解析或生成下一個請求,回調函數如上文parse()所示。

由於parse()就是解析serial_number、movie_name、introduce、star、evaluate、describe的方法,而下一頁的結構和剛纔已經解析的頁面結構是一樣的,所以我們可以再次使用parse()方法來做頁面解析。

接下來我們要做的就是利用選擇器得到下一頁鏈接並生成請求,在parse()方法後追加代碼:

# -*- coding: utf-8 -*-
import scrapy
from tutorial.items import DoubanItem

class Top250Spider(scrapy.Spider):
    name = 'top250'
    allowed_domains = ['movie.douban.com']
    start_urls = ['http://movie.douban.com/250/']

    def parse(self, response):
        movie_list = response.xpath('//div[@class="item"]')
        for i_item in movie_list:
            douban_item = DoubanItem()
            douban_item['serial_number'] = i_item.xpath('.//em/text()').extract_first()
            douban_item['movie_name'] = i_item.xpath('.//div[@class="hd"]/a/span[1]/text()').extract_first()
            content = i_item.xpath('.//div[@class="bd"]/p[1]/text()').extract()
            for i_content in content:
                content_s = "".join(i_content.split())
                douban_item['introduce'] = content_s
            douban_item['star'] = i_item.xpath('.//span[@class="rating_num"]/text()').extract_first()
            douban_item['evaluate'] = i_item.xpath('.//div[@class="star"]//span[4]/text()').extract_first()
            douban_item['describe'] = i_item.xpath('.//p[@class="quote"]//span/text()').extract_first()
            yield douban_item
        next_link = response.xpath('//span[@class="next"]/link/@href').extract()
        if next_link:
            next_link = next_link[0]
            yield scrapy.Request('https://movie.douban.com/top250' + next_link, callback=self.parse)

1.2.7 運行程式

進入目錄,運行如下命令:

scrapy crawl top250

信息刷的太快了,上面都刷沒了,只要顯示中沒有出現報錯,這樣就算成功了,大家可以自己運行一遍。

首先,Scrapy輸出了當前的版本號以及正在啟動的項目名稱。接著輸出了當前settings.py中一些重寫後的配置。然後輸出了當前所應用的Middlewares和Pipelines。Middlewares預設是啟用的,可以settings.py中修改。Pipelines 預設是空,同樣也可以在settings.py中配置。

settings.py:

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

# Scrapy settings for tutorial project
#
# For simplicity, this file contains only settings considered important or
# commonly used. You can find more settings consulting the documentation:
#
#     https://docs.scrapy.org/en/latest/topics/settings.html
#     https://docs.scrapy.org/en/latest/topics/downloader-middleware.html
#     https://docs.scrapy.org/en/latest/topics/spider-middleware.html

BOT_NAME = 'tutorial'

SPIDER_MODULES = ['tutorial.spiders']
NEWSPIDER_MODULE = 'tutorial.spiders'


# Crawl responsibly by identifying yourself (and your website) on the user-agent
#USER_AGENT = 'tutorial (+http://www.yourdomain.com)'
USER_AGENT = 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_2) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.110 Safari/537.36'


# Obey robots.txt rules
# ROBOTSTXT_OBEY = True
ROBOTSTXT_OBEY = False

# Configure maximum concurrent requests performed by Scrapy (default: 16)
#CONCURRENT_REQUESTS = 32

# Configure a delay for requests for the same website (default: 0)
# See https://docs.scrapy.org/en/latest/topics/settings.html#download-delay
# See also autothrottle settings and docs
#DOWNLOAD_DELAY = 3
DOWNLOAD_DELAY = 0.5

# The download delay setting will honor only one of:
#CONCURRENT_REQUESTS_PER_DOMAIN = 16
#CONCURRENT_REQUESTS_PER_IP = 16

# Disable cookies (enabled by default)
#COOKIES_ENABLED = False

# Disable Telnet Console (enabled by default)
#TELNETCONSOLE_ENABLED = False

# Override the default request headers:
#DEFAULT_REQUEST_HEADERS = {
#   'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
#   'Accept-Language': 'en',
#}

# Enable or disable spider middlewares
# See https://docs.scrapy.org/en/latest/topics/spider-middleware.html
#SPIDER_MIDDLEWARES = {
#    'tutorial.middlewares.TutorialSpiderMiddleware': 543,
#}

# Enable or disable downloader middlewares
# See https://docs.scrapy.org/en/latest/topics/downloader-middleware.html
#DOWNLOADER_MIDDLEWARES = {
#    'tutorial.middlewares.TutorialDownloaderMiddleware': 543,
#}

# Enable or disable extensions
# See https://docs.scrapy.org/en/latest/topics/extensions.html
#EXTENSIONS = {
#    'scrapy.extensions.telnet.TelnetConsole': None,
#}

# Configure item pipelines
# See https://docs.scrapy.org/en/latest/topics/item-pipeline.html
ITEM_PIPELINES = {
   'tutorial.pipelines.TutorialPipeline': 300,
}


# Enable and configure the AutoThrottle extension (disabled by default)
# See https://docs.scrapy.org/en/latest/topics/autothrottle.html
#AUTOTHROTTLE_ENABLED = True
# The initial download delay
#AUTOTHROTTLE_START_DELAY = 5
# The maximum download delay to be set in case of high latencies
#AUTOTHROTTLE_MAX_DELAY = 60
# The average number of requests Scrapy should be sending in parallel to
# each remote server
#AUTOTHROTTLE_TARGET_CONCURRENCY = 1.0
# Enable showing throttling stats for every response received:
#AUTOTHROTTLE_DEBUG = False

# Enable and configure HTTP caching (disabled by default)
# See https://docs.scrapy.org/en/latest/topics/downloader-middleware.html#httpcache-middleware-settings
#HTTPCACHE_ENABLED = True
#HTTPCACHE_EXPIRATION_SECS = 0
#HTTPCACHE_DIR = 'httpcache'
#HTTPCACHE_IGNORE_HTTP_CODES = []
#HTTPCACHE_STORAGE = 'scrapy.extensions.httpcache.FilesystemCacheStorage'

接下來就是輸出各個頁面的抓取結果了,可以看到爬蟲一邊解析,一邊翻頁,直至將所有內容取完畢,然後終止。

最後,Scrapy輸出了整個抓取過程的統計信息,如請求的位元組數、請求次數、響應次數、完成原因等。

整個Scrapy程式成功運行。我們通過非常簡單的代碼就完成了一個網站內容的爬取,這樣相比之前一步一步寫程式簡潔很多。 

1.2.8 保存到文件

運行完Scrapy後,我們只在控制台看到了輸出結果。如果想保存結果該怎麼辦呢?

要完成這個任務其實不需要任何額外的代碼,Scrapy提供的Feed Exports可以輕鬆將抓取結果輸出。例如,我們想將上面的結果保存成JSON文件,可以執行如下命令:

scrapy crawl top250 -o top250.json

命令運行後,項目內多了一個quotes.json文件(沒有就刷新),文件包含了剛纔抓取的所有內容,內容是JSON格式。

另外我們還可以每一個Item輸出一行JSON,輸出尾碼為jl,為jsonline的縮寫:

scrapy crawl top250 -o top250.jl

scrapy crawl top250 -o top250.jsonlines

輸出格式還支持很多種,例如csv、xml、pickle、marshal等,還支持ftp、s3等遠程輸出,另外還可以通過自定義ItemExporter來實現其他的輸出。

例如,下麵命令對應的輸出分別為csv、xml、pickle、marshal格式以及ftp遠程輸出:

scrapy crawl top250 -o top250.csv

scrapy crawl top250 -o top250.xml

scrapy crawl top250 -o top250.pickle

scrapy crawl top250 -o top250.marshal

scrapy crawl top250 -o ftp://user:[email protected]/path/to/top250.csv

其中,ftp輸出需要正確配置用戶名、密碼、地址、輸出路徑,否則會報錯。

通過Scrapy提供的Feed Exports,我們可以輕鬆地輸出抓取結果到文件。對於一些小型項目來說, 這應該足夠了。不過如果想要更複雜的輸出,如輸出到資料庫等,我們可以使用Item Pileline來完成。


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 環境:xadmin django2.0 python3.7.4 操作登錄login()或者註銷logout()報以上錯誤的解決辦法如下: 在xadmin的views/website.py中 修改如下: from django.contrib.auth.views import login from ...
  • 問題現象 django xadmin中logout頁面在chrome瀏覽器中點擊關閉頁面無效,無法關閉相應的頁面 問題原因 高版本的chrome等瀏覽器不支持在window.colse()的寫法 問題源碼 在xadmin的templates的xadmin的views的logged_out.html中 ...
  • 問題描述 Alice和Bob正在玩井字棋游戲。 井字棋游戲的規則很簡單:兩人輪流往3*3的棋盤中放棋子,Alice放的是“X”,Bob放的是“O”,Alice執先。當同一種棋子占據一行、一列或一條對角線的三個格子時,游戲結束,該種棋子的持有者獲勝。當棋盤被填滿的時候,游戲結束,雙方平手。 Alice ...
  • 這幾個變數判斷函數在PHP開發中用的其實挺多的,而且粗看上去都差不多,但其實還是有不少的區別的,如果搞不清楚,也許就會遺留一些潛在的bug, 包括我自已也遇到過這樣的坑,比如有一次我就遇到過用empty判斷出現的問題,前端是允許輸入0的,但是我用empty判斷的話就為真,我就直接給報錯了,所以這裡就 ...
  • 需求場景 不同終端(PC端、手機端、平板),不同界面(列表頁、詳情頁),對圖片大小的要求不一樣, 如果所有場景下都使用同一尺寸的圖片,勢必對會網路帶寬及伺服器性能造成一定的影響,由此需要伺服器端能夠根據前端的請求參數,自動匹配出相對應的圖片資源,以此來降低服務端的壓力,同時也能給用戶帶來更友好的用戶 ...
  • ThinkPHP6 源碼分析之應用初始化 官方群點擊此處。 App Construct 先來看看在 __construct 中做了什麼,基本任何框架都會在這裡做一些基本的操作,也就是從這裡開始延伸出去。 public function __construct(string $rootPath = ' ...
  • ThinkPHP 6 從原先的 App 類中分離出 Http 類,負責應用的初始化和調度等功能,而 App 類則專註於容器的管理,符合單一職責原則。 以下源碼分析,我們可以從 App,Http 類的實例化過程,瞭解類是如何實現自動實例化的,依賴註入是怎麼實現的。 從入口文件出發 當訪問一個 Thin ...
  • 一、PHP核心技術 更多PHP相關知識請關註我的專欄PHP​zhuanlan.zhihu.com 1.寫出一個能創建多級目錄的PHP函數(新浪網技術部) <?php /** * 創建多級目錄 * @param $path string 要創建的目錄 * @param $mode int 創建目錄的模 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...