使用 Ollama 和 FastAPI 部署 Python AI 應(yīng)用

使用 Ollama 和 FastAPI 部署 Python AI 應(yīng)用

一個(gè)在本地構(gòu)建的 AI 項(xiàng)目,可能使用了像 Ollama 和 FastAPI 這樣的庫(kù),最終需要部署到服務(wù)器上,以便更廣泛地訪問(wèn)或?qū)崿F(xiàn)可靠的 24/7 運(yùn)行。本文檔詳細(xì)介紹了將這樣一個(gè)基于 Python 的 AI 應(yīng)用部署到 Linux 服務(wù)器上的常用流程。

這些步驟涵蓋了連接到服務(wù)器、設(shè)置環(huán)境、管理 AI 模型、手動(dòng)運(yùn)行應(yīng)用程序進(jìn)行測(cè)試,以及使用 systemd 將其配置為可靠的后臺(tái)服務(wù)運(yùn)行。雖然這些步驟是基于部署使用 FastAPI 和 Ollama 的應(yīng)用程序,但許多步驟展示了適用于各種 Python Web 應(yīng)用程序的標(biāo)準(zhǔn)部署實(shí)踐。

目錄

通過(guò) SSH 連接到服務(wù)器

安全外殼協(xié)議 (SSH) 是安全連接和管理遠(yuǎn)程 Linux 服務(wù)器的標(biāo)準(zhǔn)方法。這通常是部署過(guò)程的第一步。

生成 SSH 密鑰

如果本地計(jì)算機(jī)上還沒(méi)有 SSH 密鑰對(duì),需要生成一個(gè):一個(gè)私鑰(安全地保存在本地)和一個(gè)公鑰(與服務(wù)器共享)。

在本地計(jì)算機(jī)上使用 ssh-keygen 命令。通常遵循提示即可。常見(jiàn)的算法是 ED25519 (推薦) 或 RSA。

# 使用 ED25519 的示例
ssh-keygen -t ed25519 -C "your_email@example.com"
# 遵循提示保存密鑰(默認(rèn)位置通常即可)并可選地設(shè)置密碼。

在 macOS 和 Linux 上,密鑰通常存儲(chǔ)在 ~/.ssh 目錄中。使用 ls -al ~/.ssh 檢查:

  • id_ed25519id_rsa私鑰切勿共享此文件。
  • id_ed25519.pubid_rsa.pub公鑰。復(fù)制此文件的內(nèi)容以提供給服務(wù)器管理員,或者如果有權(quán)限,自行添加。

服務(wù)器管理員(或自己)必須將公鑰文件 (id_xxx.pub) 的內(nèi)容添加到服務(wù)器上目標(biāo)用戶主目錄下的 ~/.ssh/authorized_keys 文件中。

連接

一旦公鑰在服務(wù)器上被授權(quán),就可以使用私鑰建立連接:

ssh -i /path/to/your/private_key your_server_username@your_server_hostname_or_ip -p <ssh_port_number>

替換占位符:

  • /path/to/your/private_key私鑰文件的路徑(例如 ~/.ssh/id_ed25519)。
  • your_server_username:遠(yuǎn)程服務(wù)器上的用戶名。
  • your_server_hostname_or_ip:服務(wù)器的 IP 地址或可解析的主機(jī)名。
  • <ssh_port_number>:服務(wù)器上配置的 SSH 端口號(hào)(默認(rèn)為 22,但為了安全通常會(huì)更改)。

注意: 替換像 <ssh_port_number> 這樣的占位符時(shí),省略尖括號(hào) (<>)。

首次連接到新服務(wù)器時(shí),可能會(huì)看到一個(gè)主機(jī)真實(shí)性警告。這是正常的。輸入 yes 繼續(xù)。

The authenticity of host '...' can't be established.
... key fingerprint is ...
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes

克隆項(xiàng)目代碼庫(kù)

成功建立 SSH 連接后,使用 Git 將項(xiàng)目代碼獲取到服務(wù)器上:

git clone your_repository_link
# 示例: git clone git@github.com:your_username/your_project.git
# 或: git clone https://github.com/your_username/your_project.git

your_repository_link 替換為 Git 代碼庫(kù)的實(shí)際 SSH 或 HTTPS URL。進(jìn)入克隆的目錄:cd your_project_directory_name。

環(huán)境配置

在服務(wù)器上設(shè)置必要的軟件和環(huán)境。

1. 安裝 uv (可選但推薦)

uv 是一個(gè)用 Rust 編寫(xiě)的非??焖俚?Python 包安裝器和解析器。與標(biāo)準(zhǔn)的 pip 相比,使用它可以顯著加快依賴項(xiàng)的安裝速度。它是可選的,但推薦使用。

# 使用 pip 安裝 uv (確保 pip 可用)
pip install uv
# 或者,遵循官方說(shuō)明:https://github.com/astral-sh/uv#installation

驗(yàn)證安裝:

uv --version
# 預(yù)期輸出類(lèi)似于:uv x.y.z

2. 安裝 Python

確保安裝了兼容的 Python 版本(例如 3.8-3.11,檢查項(xiàng)目的需求)。

如果安裝了 uv,可以用它來(lái)安裝 Python:

# 將 3.x.y 替換為目標(biāo)版本 (例如 3.10.13)
uv python install 3.x.y
# 遵循任何關(guān)于 PATH 更新的提示。

或者,使用系統(tǒng)的包管理器(在 Linux 服務(wù)器上很常見(jiàn)):

# Debian/Ubuntu 示例
sudo apt update
sudo apt install python3 python3-pip python3-venv

# CentOS/RHEL 示例
sudo yum update
sudo yum install python3 python3-pip

確認(rèn) Python 安裝:

python3 --version
# 或有時(shí)只是 'python --version',取決于 PATH 設(shè)置

3. 安裝軟件依賴

項(xiàng)目依賴

項(xiàng)目應(yīng)該有一個(gè) requirements.txt 文件,列出了 Python 依賴項(xiàng)。導(dǎo)航到項(xiàng)目目錄并安裝它們。

使用 uv (如果已安裝,推薦):

cd /path/to/your/project
uv pip install -r requirements.txt

或者,使用 pip (通常在虛擬環(huán)境中):

cd /path/to/your/project
# 最佳實(shí)踐:首先創(chuàng)建并激活虛擬環(huán)境
# python3 -m venv venv
# source venv/bin/activate
pip install -r requirements.txt
# 或 pip3 install -r requirements.txt

注意:/path/to/your/project 替換為克隆的代碼庫(kù)的實(shí)際絕對(duì)路徑。

安裝并運(yùn)行 Ollama

Ollama 允許在本地運(yùn)行大型語(yǔ)言模型。使用官方腳本在 Linux 服務(wù)器上安裝它:

curl -fsSL https://ollama.com/install.sh | sh

為了初步測(cè)試,可以在后臺(tái)手動(dòng)啟動(dòng) Ollama 服務(wù)器:

ollama serve & # '&' 符號(hào)使其僅在當(dāng)前會(huì)話的后臺(tái)運(yùn)行。

注意: 對(duì)于生產(chǎn)環(huán)境,Ollama 應(yīng)設(shè)置為 systemd 服務(wù)(安裝腳本通常會(huì)自動(dòng)執(zhí)行此操作,請(qǐng)使用 systemctl status ollama 檢查)。運(yùn)行 ollama serve & 主要用于臨時(shí)測(cè)試。

驗(yàn)證 Ollama 是否正在運(yùn)行且可訪問(wèn)(此命令與正在運(yùn)行的服務(wù)器通信):

ollama list
# 應(yīng)該顯示一個(gè)空列表或任何已經(jīng)拉取/創(chuàng)建的模型。
# 如果命令掛起或出錯(cuò),則表示服務(wù)器未正確運(yùn)行。

4. 準(zhǔn)備 AI 模型

將所需的 AI 模型文件放在服務(wù)器上。選擇一個(gè)合適的位置,例如項(xiàng)目?jī)?nèi)的 models/ 子目錄或中央的 /opt/ai-models/ 目錄。

上傳/下載模型

  • 從 Hugging Face: 使用 huggingface-cli (通過(guò) pip install huggingface_hub 安裝):

    huggingface-cli download repo_id path/to/model.gguf --local-dir /path/on/server/models --local-dir-use-symlinks False
    # 替換 repo_id, 模型文件名, 和 /path/on/server/models
    
  • 從本地機(jī)器: 使用 scp (Secure Copy) 從開(kāi)發(fā)機(jī)器上傳模型。替換占位符。

    # 上傳單個(gè)模型文件
    scp /path/on/local/model.gguf your_server_username@your_server_hostname_or_ip:/path/on/server/models/
    
    # 上傳一個(gè) Ollama Modelfile
    scp /path/on/local/Modelfile your_server_username@your_server_hostname_or_ip:/path/on/server/models/
    
    # 遞歸上傳整個(gè)目錄
    scp -r /path/on/local/model_directory your_server_username@your_server_hostname_or_ip:/path/on/server/models/
    
  • GGUF 合并: 如果模型被分割(例如 model-part-1.gguf, model-part-2.gguf),可能需要 llama.cpp 工具來(lái)合并它們。克隆 llama.cpp,構(gòu)建它,并使用 llama-gguf-split:

    # 假設(shè) llama.cpp 工具已構(gòu)建并在 PATH 中
    # llama-gguf-split --merge input_part_*.gguf output_merged.gguf
    

使用 Ollama 構(gòu)建模型

要將本地模型文件(如 .gguf)與 Ollama 集成或定義自定義模型參數(shù),請(qǐng)使用 Modelfile。在服務(wù)器上,與基礎(chǔ)模型文件 (.gguf) 相同的目錄中創(chuàng)建這個(gè)文本文件(例如 MyModelModelfile)。

Modelfile 內(nèi)容示例:

# 使用 FROM 指向同一目錄中的模型文件的相對(duì)路徑
FROM ./local_model_filename.gguf

# (可選) 定義提示模板
TEMPLATE """[INST] {{ .Prompt }} [/INST]"""

# (可選) 設(shè)置參數(shù)
PARAMETER temperature 0.7
PARAMETER top_k 40
# 根據(jù)需要添加其他參數(shù) (停止序列等)

使用選定的名稱構(gòu)建模型并將其注冊(cè)到 Ollama:

# 確保 Ollama 服務(wù)器正在運(yùn)行
# 導(dǎo)航到包含 Modelfile 和 .gguf 文件的目錄
cd /path/on/server/models/

# 創(chuàng)建模型 - 使用一個(gè)描述性的名稱
ollama create your_custom_model_name -f MyModelModelfile

驗(yàn)證模型是否可用:ollama list。

5. 設(shè)置環(huán)境變量

應(yīng)用程序通常需要配置,如 API 密鑰或數(shù)據(jù)庫(kù) URL,最好通過(guò)環(huán)境變量來(lái)管理。一種常見(jiàn)的方法是在項(xiàng)目的根目錄中使用 .env 文件。切勿將 .env 文件提交到 Git。.env 添加到.gitignore 文件中。

在項(xiàng)目根目錄 (/path/to/your/project/.env) 創(chuàng)建一個(gè)名為 .env 的文件,內(nèi)容類(lèi)似這樣(替換占位符值):

# 示例 .env 文件內(nèi)容
# 框架密鑰 (生成一個(gè)強(qiáng)隨機(jī)密鑰)
SECRET_KEY=your_strong_random_secret_key

# 外部服務(wù)的 API 密鑰
EXTERNAL_API_KEY=your_external_api_key_value

# 如果應(yīng)用需要顯式連接 Ollama 的配置
OLLAMA_HOST=http://127.0.0.1:11434

# 其他配置變量
DATABASE_URL=your_database_connection_string

Python 應(yīng)用程序代碼需要加載這些變量,通常使用像 python-dotenv (pip install python-dotenv) 這樣的庫(kù)。

6. 手動(dòng)運(yùn)行項(xiàng)目 (測(cè)試)

在設(shè)置服務(wù)之前,從終端手動(dòng)運(yùn)行應(yīng)用程序,以確保它能正確啟動(dòng)和運(yùn)行。

  1. 確保 Ollama 正在運(yùn)行: 使用 ollama listsystemctl status ollama (如果作為服務(wù)安裝) 來(lái)驗(yàn)證。

  2. 激活環(huán)境 (如果使用 venv): source /path/to/your/project/venv/bin/activate

  3. 啟動(dòng)應(yīng)用程序: 導(dǎo)航到項(xiàng)目根目錄。使用像 uvicorn 這樣的 ASGI 服務(wù)器來(lái)運(yùn)行 FastAPI。替換占位符。

    cd /path/to/your/project
    
    # 使用 uvicorn 的示例命令
    # 假設(shè) FastAPI 應(yīng)用實(shí)例在 'main.py' 中名為 'app'
    # 使用應(yīng)用配置監(jiān)聽(tīng)的端口
    uvicorn main:app --host 0.0.0.0 --port <your_app_port> --reload
    
    • --host 0.0.0.0:使應(yīng)用可以從網(wǎng)絡(luò)上的其他機(jī)器訪問(wèn)(確保防火墻規(guī)則允許 <your_app_port> 端口的流量)。
    • --port <your_app_port>:應(yīng)用程序?qū)⒈O(jiān)聽(tīng)的端口(例如 8000)。
    • --reload僅用于測(cè)試。 在代碼更改時(shí)啟用自動(dòng)重新加載。對(duì)于生產(chǎn)部署,請(qǐng)移除此標(biāo)志。
  4. 測(cè)試:

    • API 端點(diǎn): 使用 curl、Postman 或 Insomnia 等工具發(fā)送請(qǐng)求(例如 curl http://your_server_hostname_or_ip:<your_app_port>/api/some_endpoint)。
    • Web UI: 通過(guò)瀏覽器訪問(wèn) http://your_server_hostname_or_ip:<your_app_port> 上的任何 Web 界面。
    • 日志: 檢查終端輸出以查找錯(cuò)誤。

使用 systemd 作為服務(wù)部署

在終端中手動(dòng)運(yùn)行應(yīng)用程序不適合生產(chǎn)環(huán)境。systemd 是標(biāo)準(zhǔn)的 Linux 服務(wù)管理器,用于:

  1. 在服務(wù)器啟動(dòng)時(shí)自動(dòng)啟動(dòng)應(yīng)用程序。
  2. 在應(yīng)用程序崩潰時(shí)自動(dòng)重啟。
  3. 將應(yīng)用程序作為后臺(tái)進(jìn)程進(jìn)行管理,并進(jìn)行適當(dāng)?shù)娜罩居涗洝?/li>

創(chuàng)建服務(wù)文件

使用具有 sudo 權(quán)限的文本編輯器創(chuàng)建一個(gè)服務(wù)定義文件。使用描述性的名稱(例如 your-app-name.service)。

sudo nano /etc/systemd/system/your-app-name.service

將以下模板粘貼到文件中。請(qǐng)仔細(xì)閱讀注釋并替換所有占位符。

[Unit]
Description=My Python AI Application Service # 服務(wù)的描述性名稱
After=network.target
# 如果應(yīng)用嚴(yán)格要求 Ollama 首先運(yùn)行 (并且 Ollama 是一個(gè) systemd 服務(wù)), 取消注釋:
# Wants=ollama.service
# After=network.target ollama.service

[Service]
# !!! 安全最佳實(shí)踐:切勿以 ROOT 用戶身份運(yùn)行 !!!
# 為應(yīng)用程序創(chuàng)建一個(gè)專(zhuān)用的非 root 用戶。
# 將 'your_app_user' 替換為實(shí)際的用戶名。確保此用戶具有
# 讀取項(xiàng)目文件和寫(xiě)入必要目錄 (例如日志、上傳文件) 的權(quán)限。
User=your_app_user
# Group=your_app_group # 通常與用戶相同,如果需要?jiǎng)t取消注釋

# 將工作目錄設(shè)置為項(xiàng)目的根目錄絕對(duì)路徑
WorkingDirectory=/path/to/your/project # !!! 務(wù)必替換此絕對(duì)路徑 !!!

# 啟動(dòng)應(yīng)用程序的命令。使用可執(zhí)行文件 (uvicorn, gunicorn 等) 的絕對(duì)路徑。
# 查找路徑: 'which uvicorn' (以 your_app_user 身份, 可能在激活 venv 后)
# 或者可能是類(lèi)似: /path/to/your/project/venv/bin/uvicorn 或 /home/your_app_user/.local/bin/uvicorn
# 調(diào)整 'main:app', host, port, 和其他參數(shù)。移除 --reload!
ExecStart=/path/to/executable/uvicorn main:app --host 0.0.0.0 --port <your_app_port> --forwarded-allow-ips='*' # !!! 務(wù)必替換路徑, 應(yīng)用, 端口并檢查參數(shù) !!!

# 重啟策略
Restart=always
RestartSec=5 # 重啟前等待 5 秒

# 日志記錄: 將 stdout/stderr 重定向到 systemd journal
StandardOutput=journal
StandardError=journal

# 可選: 從 .env 文件加載環(huán)境變量
# 確保路徑是絕對(duì)路徑。權(quán)限必須允許 'your_app_user' 讀取它。
# EnvironmentFile=/path/to/your/project/.env # !!! 務(wù)必替換此絕對(duì)路徑 !!!
# 注意: 此處的變量可能會(huì)覆蓋系統(tǒng)范圍或用戶特定的環(huán)境設(shè)置。

[Install]
WantedBy=multi-user.target # 在正常系統(tǒng)啟動(dòng)期間啟動(dòng)服務(wù)

需要驗(yàn)證的關(guān)鍵占位符和設(shè)置:

  1. Description:一個(gè)清晰的名稱。
  2. User/Group必須更改為一個(gè)專(zhuān)用的非 root 用戶 (your_app_user)。確保此用戶的文件/目錄權(quán)限正確。
  3. WorkingDirectory:項(xiàng)目根目錄的絕對(duì)路徑。
  4. ExecStart
    • uvicorn(或其他 WSGI/ASGI 服務(wù)器)可執(zhí)行文件的絕對(duì)路徑。如果使用虛擬環(huán)境,通常在 venv/bin/ 內(nèi)。
    • main:app 必須與 Python 文件和 FastAPI/Flask 應(yīng)用實(shí)例匹配。
    • <your_app_port>--host 和其他參數(shù)必須適合生產(chǎn)環(huán)境。移除 --reload。
    • 如果位于反向代理(如 Nginx 或 Apache)之后,可能需要 --forwarded-allow-ips='*'。根據(jù)安全需要進(jìn)行調(diào)整。
  5. (可選) EnvironmentFile:如果使用,指向 .env 文件的絕對(duì)路徑

保存文件并退出編輯器(在 nano 中按 Ctrl+X,然后按 Y,然后按 Enter)。

啟用并啟動(dòng)服務(wù)

使用 systemctl 管理新服務(wù):

  1. 重新加載 systemd 配置: 使其知道新文件。
    sudo systemctl daemon-reload
    
  2. 啟用服務(wù): 使其在啟動(dòng)時(shí)自動(dòng)運(yùn)行。使用創(chuàng)建的相同文件名。
    sudo systemctl enable your-app-name.service
    
  3. 啟動(dòng)服務(wù): 立即運(yùn)行它。
    sudo systemctl start your-app-name.service
    
  4. 檢查狀態(tài): 驗(yàn)證它是否正在運(yùn)行。
    sudo systemctl status your-app-name.service
    
    查找 active (running)。如果顯示 failed 或不是 active,請(qǐng)檢查日志。
  5. 查看日志: 查看應(yīng)用程序輸出并排查錯(cuò)誤。
    sudo journalctl -u your-app-name.service -f
    
    • -u your-app-name.service:過(guò)濾特定服務(wù)的日志。
    • -f:實(shí)時(shí)跟蹤日志(類(lèi)似 tail -f)。按 Ctrl+C 停止跟蹤。
    • 要查看較早的日志,移除 -fsudo journalctl -u your-app-name.service --since "1 hour ago"

AI 應(yīng)用程序現(xiàn)在應(yīng)該作為托管的后臺(tái)服務(wù)運(yùn)行了。

常見(jiàn)問(wèn)題 (FAQ)

設(shè)置或運(yùn)行時(shí)遇到的常見(jiàn)問(wèn)題。

環(huán)境配置問(wèn)題

  • SSH 連接/輸入緩慢:
    • 原因: 網(wǎng)絡(luò)延遲高。
    • 解決方案: 使用 -C 標(biāo)志啟用 SSH 壓縮:
      ssh -C your_server_username@your_server_hostname_or_ip ...
      

運(yùn)行時(shí)問(wèn)題

  • 缺少環(huán)境變量: 出現(xiàn)類(lèi)似 KeyError: 'SECRET_KEY'ValueError: Required setting X not found 的錯(cuò)誤。

    • 原因: 應(yīng)用程序需要的環(huán)境變量在其運(yùn)行上下文中未定義。
    • 解決方案: 確保所需變量已設(shè)置,可以通過(guò)以下方式之一:
      • .env 文件中,并且應(yīng)用程序使用 python-dotenv 加載它。
      • 或者在 systemd 服務(wù)文件中使用 Environment="VAR_NAME=value" 指令(對(duì)于許多變量不太常見(jiàn))或 EnvironmentFile= 指令指向 .env 文件。驗(yàn)證 systemd 服務(wù)用戶是否有權(quán)限讀取 EnvironmentFile。更改后重新加載 (daemon-reload) 并重啟服務(wù)。
  • Ollama 運(yùn)行時(shí)錯(cuò)誤: Error: llama runner process has terminated: exit status X.

    • 原因: 多種多樣??赡苁?Ollama 的 bug、模型所需的 RAM/VRAM 不足、模型文件損壞或不兼容。
    • 解決方案:
      • 檢查 Ollama 的日志:journalctl -u ollama.service(如果作為 systemd 服務(wù)運(yùn)行)。
      • Ollama GitHub Issues 中搜索具體的錯(cuò)誤消息或退出狀態(tài)碼。
      • 確保服務(wù)器滿足模型的資源需求。
      • 嘗試不同的(可能更小的)模型來(lái)隔離問(wèn)題。
      • 考慮嘗試不同的 Ollama 版本(降級(jí)或升級(jí)),檢查兼容性說(shuō)明。
  • Ollama 響應(yīng)緩慢/無(wú)響應(yīng)/推理時(shí)間長(zhǎng):

    • 原因 1: 網(wǎng)絡(luò)代理干擾。
      解決方案 1: 如果手動(dòng)運(yùn)行 Ollama 或配置其環(huán)境,嘗試取消設(shè)置代理變量:unset http_proxy https_proxy NO_PROXY。對(duì)于 systemd 服務(wù),可能需要在系統(tǒng)范圍或服務(wù)環(huán)境設(shè)置中配置/禁用代理。
    • 原因 2: 硬件資源不足 (CPU, RAM, VRAM 如果使用 GPU)。
    • 解決方案 2: 驗(yàn)證模型需求與服務(wù)器規(guī)格。監(jiān)控資源使用情況 (htop, nvidia-smi 如果有 GPU)。如果需要,使用更小的模型或升級(jí)硬件。
  • ollama serve 失?。憾丝谝驯徽加? 出現(xiàn)類(lèi)似 listen tcp 127.0.0.1:11434: bind: address already in use 的錯(cuò)誤。

    • 原因: 另一個(gè)進(jìn)程(很可能是另一個(gè) Ollama 實(shí)例或配置錯(cuò)誤的應(yīng)用程序)正在使用端口 11434。
    • 解決方案: 停止沖突的進(jìn)程。
      • 如果 Ollama 是一個(gè)服務(wù):sudo systemctl stop ollama
      • 手動(dòng)查找并終止:
      sudo lsof -i :11434 # 查找使用該端口的 PID
      sudo kill <PID>      # 將 <PID> 替換為找到的進(jìn)程 ID
      # 或者更強(qiáng)制地 (謹(jǐn)慎使用):
      # sudo pkill ollama
      # sudo killall ollama
      
      • 停止沖突后,再次嘗試啟動(dòng)服務(wù)/Ollama。

結(jié)論

部署 Python AI 應(yīng)用涉及仔細(xì)的環(huán)境配置、依賴管理、模型處理和健壯的進(jìn)程管理。像 uv (提高速度)、Ollama (本地模型服務(wù))、FastAPI (提供 API) 和 systemd (可靠的服務(wù)操作) 這樣的工具提供了堅(jiān)實(shí)的基礎(chǔ)。請(qǐng)記住,通過(guò)使用非 root 用戶并通過(guò)環(huán)境變量適當(dāng)?shù)毓芾砻荑€來(lái)優(yōu)先考慮安全性。通過(guò)遵循這些步驟并根據(jù)具體項(xiàng)目需求進(jìn)行調(diào)整,可以成功部署應(yīng)用程序以實(shí)現(xiàn)持續(xù)運(yùn)行。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容