Files
MuMuAINovel/install-termux.sh
T
Fly143 71babda777 Add files via upload
Android/termux一键安装脚本
2026-04-18 13:08:32 +08:00

312 lines
12 KiB
Bash
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
#!/bin/bash
# MuMuAINovel Termux 一键安装脚本
# 用法: curl -fsSL <url> | bash
# 或者: bash install-termux.sh
set -e
INSTALL_DIR="$HOME/MuMuAINovel"
DATA_DIR="$HOME/mumuainovel/data"
LOG_DIR="$HOME/mumuainovel/logs"
REPO="https://github.com/xiamuceer-j/MuMuAINovel.git"
# 颜色
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
RED='\033[0;31m'
CYAN='\033[0;36m'
NC='\033[0m'
info() { echo -e "${GREEN}[✓]${NC} $1"; }
warn() { echo -e "${YELLOW}[!]${NC} $1"; }
err() { echo -e "${RED}[✗]${NC} $1"; }
step() { echo -e "\n${CYAN}[$1/$2]${NC} $3"; }
echo ""
echo -e "${CYAN}╔══════════════════════════════════════════╗${NC}"
echo -e "${CYAN}║ 📚 MuMuAINovel Termux 一键安装 ║${NC}"
echo -e "${CYAN}╚══════════════════════════════════════════╝${NC}"
echo ""
TOTAL=9
# ──────────────────────────────────────────
step 1 $TOTAL "检查环境"
# ──────────────────────────────────────────
if [ ! -d "/data/data/com.termux" ]; then
err "未检测到 Termux 环境,请在 Termux 中运行"
exit 1
fi
info "Termux 环境检测通过"
# ──────────────────────────────────────────
step 2 $TOTAL "安装系统依赖"
# ──────────────────────────────────────────
pkg install -y python nodejs git > /dev/null 2>&1
info "python/nodejs/git 已安装"
# ──────────────────────────────────────────
step 3 $TOTAL "克隆项目"
# ──────────────────────────────────────────
if [ -d "$INSTALL_DIR" ]; then
warn "检测到旧安装,清理中..."
rm -rf "$INSTALL_DIR"
fi
git clone "$REPO" "$INSTALL_DIR"
info "项目已就位: $INSTALL_DIR"
BACKEND="$INSTALL_DIR/backend"
FRONTEND="$INSTALL_DIR/frontend"
PYTHON="$BACKEND/venv/bin/python"
# ──────────────────────────────────────────
step 4 $TOTAL "应用 Termux 补丁"
# ──────────────────────────────────────────
# 4a. Patch memory_service.py - 让 chromadb/sentence_transformers 缺失不崩溃
MEM_FILE="$BACKEND/app/services/memory_service.py"
python3 << PYEOF
import os
f = os.path.expanduser("~/MuMuAINovel/backend/app/services/memory_service.py")
with open(f) as fh:
c = fh.read()
# 替换顶层 import
c = c.replace(
"import chromadb\nfrom sentence_transformers import SentenceTransformer",
"""try:
import chromadb
from sentence_transformers import SentenceTransformer
MEMORY_AVAILABLE = True
except ImportError:
MEMORY_AVAILABLE = False
chromadb = None
SentenceTransformer = None"""
)
# 在 __init__ 的 _initialized 检查后加 MEMORY_AVAILABLE 保护
old_init = """ def __init__(self):
\"\"\"初始化ChromaDB和Embedding模型\"\"\"
if self._initialized:
return
try:"""
new_init = """ def __init__(self):
\"\"\"初始化ChromaDB和Embedding模型\"\"\"
if self._initialized:
return
if not MEMORY_AVAILABLE:
self.client = None
self.model = None
self.collection = None
self._initialized = True
logger.warning("⚠️ 向量记忆功能不可用(缺少 chromadb/sentence-transformers")
return
try:"""
c = c.replace(old_init, new_init, 1)
with open(f, "w") as fh:
fh.write(c)
print(" ✅ memory_service.py 已修补")
PYEOF
info "memory_service.py 已修补"
# 4b. Patch API files - memory_service 导入改为 try/except
python3 << 'PYEOF'
import os
home = os.path.expanduser("~")
files = [
f"{home}/MuMuAINovel/backend/app/api/chapters.py",
f"{home}/MuMuAINovel/backend/app/api/memories.py",
f"{home}/MuMuAINovel/backend/app/api/outlines.py",
f"{home}/MuMuAINovel/backend/app/api/projects.py",
f"{home}/MuMuAINovel/backend/app/services/foreshadow_service.py",
]
old = 'from app.services.memory_service import memory_service'
new = 'try:\n from app.services.memory_service import memory_service\nexcept ImportError:\n memory_service = None'
count = 0
for f in files:
if not os.path.exists(f): continue
with open(f) as fh: c = fh.read()
if old in c:
c = c.replace(old, new)
with open(f, 'w') as fh: fh.write(c)
count += 1
print(f" ✅ API 文件已修补({count} 个)")
PYEOF
info "API 文件已修补"
# 4c. 创建 .env
mkdir -p "$DATA_DIR" "$LOG_DIR"
cat > "$BACKEND/.env" << 'ENVEOF'
# MuMuAINovel Termux 配置
APP_NAME=MuMuAINovel
APP_HOST=0.0.0.0
APP_PORT=8000
DEBUG=false
TZ=Asia/Shanghai
# SQLite 数据库(替代 PostgreSQL
DATABASE_URL=sqlite+aiosqlite:///data/data/com.termux/files/home/mumuainovel/data/ai_story.db
# 日志
LOG_LEVEL=INFO
LOG_TO_FILE=true
LOG_FILE_PATH=/data/data/com.termux/files/home/mumuainovel/logs/app.log
LOG_MAX_BYTES=10485760
LOG_BACKUP_COUNT=5
# CORS
CORS_ORIGINS=["http://localhost:8000","http://127.0.0.1:8000"]
# ⚠️ 请填入你的 API Key
OPENAI_API_KEY=sk-your-key-here
OPENAI_BASE_URL=https://api.openai.com/v1
DEFAULT_AI_PROVIDER=openai
DEFAULT_MODEL=gpt-4o-mini
DEFAULT_TEMPERATURE=0.7
DEFAULT_MAX_TOKENS=4096
# 本地登录账号
LOCAL_AUTH_USERNAME=admin
LOCAL_AUTH_PASSWORD=admin123
LOCAL_AUTH_DISPLAY_NAME=管理员
ENVEOF
# 修正 DATABASE_URL 路径(替换占位符为实际路径)
sed -i "s|/data/data/com.termux/files/home|$HOME|g" "$BACKEND/.env"
sed -i "s|LOG_FILE_PATH=.*|LOG_FILE_PATH=$LOG_DIR/app.log|" "$BACKEND/.env"
info ".env 已创建(SQLite + admin/admin123"
# ──────────────────────────────────────────
step 5 $TOTAL "安装 Python 依赖"
# ──────────────────────────────────────────
if [ ! -d "$BACKEND/venv" ]; then
python -m venv "$BACKEND/venv"
fi
PIP="$BACKEND/venv/bin/pip"
$PIP install --upgrade pip setuptools wheel -q
# 精简依赖(跳过 Termux 不兼容的包)
cat > "$BACKEND/requirements-lite.txt" << 'REQEOF'
fastapi==0.121.0
uvicorn==0.38.0
python-multipart==0.0.20
sqlalchemy==2.0.36
alembic==1.14.0
aiosqlite==0.22.1
pydantic==2.12.4
pydantic-settings==2.11.0
openai==2.7.0
anthropic==0.72.0
httpx==0.28.1
python-dotenv==1.1.0
aiosmtplib==4.0.2
mcp==1.22.0
greenlet>=3.0
REQEOF
$PIP install -r "$BACKEND/requirements-lite.txt" -q
info "Python 依赖已安装"
# ──────────────────────────────────────────
step 6 $TOTAL "数据库迁移"
# ──────────────────────────────────────────
export DATABASE_URL="sqlite+aiosqlite:///$DATA_DIR/ai_story.db"
cd "$BACKEND"
"$BACKEND/venv/bin/python" -m alembic -c alembic-sqlite.ini upgrade head || {
warn "alembic 迁移失败,尝试修复后重试..."
"$BACKEND/venv/bin/pip" install --force-reinstall alembic==1.14.0 -q
"$BACKEND/venv/bin/python" -m alembic -c alembic-sqlite.ini upgrade head || {
err "数据库迁移失败,请手动运行: cd $BACKEND && python -m alembic -c alembic-sqlite.ini upgrade head"
exit 1
}
}
info "SQLite 数据库已初始化"
# ──────────────────────────────────────────
step 7 $TOTAL "安装前端依赖"
# ──────────────────────────────────────────
cd "$FRONTEND"
npm install --include=dev
info "前端依赖已安装"
# ──────────────────────────────────────────
step 8 $TOTAL "构建前端"
# ──────────────────────────────────────────
# Termux 下 npm 的符号链接可能失效,用 node 直接调用
node "$FRONTEND/node_modules/typescript/bin/tsc" -b 2>/dev/null || warn "TypeScript 有类型警告(已跳过)"
node "$FRONTEND/node_modules/vite/bin/vite.js" build || {
err "前端构建失败"
exit 1
}
info "前端已构建 → $BACKEND/static/"
# ──────────────────────────────────────────
step 9 $TOTAL "创建启动脚本"
# ──────────────────────────────────────────
cat > "$HOME/mumuainovel-start.sh" << STARTEOF
#!/bin/bash
# MuMuAINovel Termux 启动脚本
set -e
BACKEND="$BACKEND"
PYTHON="\$BACKEND/venv/bin/python"
DATA_DIR="$DATA_DIR"
LOG_DIR="$LOG_DIR"
mkdir -p "\$DATA_DIR" "\$LOG_DIR"
export DATABASE_URL="sqlite+aiosqlite:///\$DATA_DIR/ai_story.db"
cd "\$BACKEND"
if [ "\$1" = "--bg" ]; then
echo "🚀 后台启动 MuMuAINovel (端口 8000)..."
nohup "\$PYTHON" -m uvicorn app.main:app --host 0.0.0.0 --port 8000 \\
> "\$LOG_DIR/app.log" 2>&1 &
echo \$! > "$HOME/mumuainovel.pid"
sleep 2
if kill -0 \$(cat "$HOME/mumuainovel.pid") 2>/dev/null; then
echo "✅ 已启动, PID: \$(cat $HOME/mumuainovel.pid)"
else
echo "❌ 启动失败,查看日志: \$LOG_DIR/app.log"
exit 1
fi
else
echo "🚀 启动 MuMuAINovel (端口 8000, Ctrl+C 停止)..."
exec "\$PYTHON" -m uvicorn app.main:app --host 0.0.0.0 --port 8000
fi
STARTEOF
chmod +x "$HOME/mumuainovel-start.sh"
info "启动脚本已创建: ~/mumuainovel-start.sh"
# ──────────────────────────────────────────
echo ""
echo -e "${GREEN}╔══════════════════════════════════════════════╗${NC}"
echo -e "${GREEN}║ 🎉 MuMuAINovel 安装完成! ║${NC}"
echo -e "${GREEN}╠══════════════════════════════════════════════╣${NC}"
echo -e "${GREEN}║ ║${NC}"
echo -e "${GREEN}║ 前台运行(Ctrl+C 停止): ║${NC}"
echo -e "${GREEN}║ bash ~/mumuainovel-start.sh ║${NC}"
echo -e "${GREEN}║ ║${NC}"
echo -e "${GREEN}║ 后台运行: ║${NC}"
echo -e "${GREEN}║ bash ~/mumuainovel-start.sh --bg ║${NC}"
echo -e "${GREEN}║ ║${NC}"
echo -e "${GREEN}║ 停止后台: ║${NC}"
echo -e "${GREEN}║ kill \\\$(cat ~/mumuainovel.pid) ║${NC}"
echo -e "${GREEN}║ ║${NC}"
echo -e "${GREEN}║ 查看日志: ║${NC}"
echo -e "${GREEN}║ tail -f ~/mumuainovel/logs/app.log ║${NC}"
echo -e "${GREEN}║ ║${NC}"
echo -e "${GREEN}║ 🌐 访问: http://127.0.0.1:8000 ║${NC}"
echo -e "${GREEN}║ 🔑 账号: admin / admin123 ║${NC}"
echo -e "${GREEN}║ ║${NC}"
echo -e "${GREEN}╚══════════════════════════════════════════════╝${NC}"
echo ""
echo -e "${YELLOW} ⚠️ 首次使用前请编辑 API Key:${NC}"
echo -e " nano $BACKEND/.env"
echo -e " 修改 OPENAI_API_KEY 和 OPENAI_BASE_URL"
echo ""