s
This commit is contained in:
@@ -26,13 +26,22 @@ MDNS_HOST="${HOSTNAME_ALIAS:-live}.local"
|
|||||||
getent hosts "$MDNS_HOST" >/dev/null 2>&1 && echo "$MDNS_HOST resolves: yes" || echo "$MDNS_HOST resolves: fail"
|
getent hosts "$MDNS_HOST" >/dev/null 2>&1 && echo "$MDNS_HOST resolves: yes" || echo "$MDNS_HOST resolves: fail"
|
||||||
|
|
||||||
section "config"
|
section "config"
|
||||||
|
if [[ -f "$REPO/config/system-stack.env" ]]; then
|
||||||
|
echo "repo stack env: present ($REPO/config/system-stack.env)"
|
||||||
|
else
|
||||||
|
echo "repo stack env: missing"
|
||||||
|
fi
|
||||||
if [[ -f /opt/live/config/system.json ]]; then
|
if [[ -f /opt/live/config/system.json ]]; then
|
||||||
echo "system.json: present"
|
echo "system.json: present"
|
||||||
|
elif [[ -f "$REPO/config/system-stack.env" ]]; then
|
||||||
|
echo "system.json: not used by repo-managed install"
|
||||||
else
|
else
|
||||||
echo "system.json: MISSING (run install-core)"
|
echo "system.json: MISSING (run install-core)"
|
||||||
fi
|
fi
|
||||||
if [[ -f /opt/live/generated/system-stack.env ]]; then
|
if [[ -f /opt/live/generated/system-stack.env ]]; then
|
||||||
echo "generated env: present"
|
echo "generated env: present"
|
||||||
|
elif [[ -f "$REPO/config/system-stack.env" ]]; then
|
||||||
|
echo "generated env: repo-managed via config/system-stack.env"
|
||||||
else
|
else
|
||||||
echo "generated env: missing"
|
echo "generated env: missing"
|
||||||
fi
|
fi
|
||||||
|
|||||||
@@ -6,5 +6,6 @@ tqdm>=4.67.1
|
|||||||
httpx[http2]>=0.28.1
|
httpx[http2]>=0.28.1
|
||||||
PyExecJS>=1.5.1
|
PyExecJS>=1.5.1
|
||||||
fastapi>=0.115.0
|
fastapi>=0.115.0
|
||||||
|
eval-type-backport>=0.2.0
|
||||||
uvicorn[standard]>=0.30.0
|
uvicorn[standard]>=0.30.0
|
||||||
python-multipart>=0.0.9
|
python-multipart>=0.0.9
|
||||||
|
|||||||
@@ -262,6 +262,9 @@ def _try_local_console_build() -> tuple[bool, str]:
|
|||||||
return True, "up-to-date"
|
return True, "up-to-date"
|
||||||
|
|
||||||
print("[launch] 正在构建 Web 控制台…")
|
print("[launch] 正在构建 Web 控制台…")
|
||||||
|
for path in (CONSOLE / "node_modules", CONSOLE / ".next"):
|
||||||
|
if path.exists():
|
||||||
|
shutil.rmtree(path, ignore_errors=True)
|
||||||
lock = CONSOLE / "package-lock.json"
|
lock = CONSOLE / "package-lock.json"
|
||||||
if lock.is_file():
|
if lock.is_file():
|
||||||
rc = _run_console_cmd([npm, "ci"], cwd=CONSOLE, env=env)
|
rc = _run_console_cmd([npm, "ci"], cwd=CONSOLE, env=env)
|
||||||
@@ -290,9 +293,18 @@ def _docker_console_build() -> bool:
|
|||||||
print(f"[launch] 本机 Node 不足,改用 Docker 构建: {DOCKER_NODE_IMAGE}")
|
print(f"[launch] 本机 Node 不足,改用 Docker 构建: {DOCKER_NODE_IMAGE}")
|
||||||
script = (
|
script = (
|
||||||
"set -e; "
|
"set -e; "
|
||||||
|
"rm -rf /tmp/web-console; "
|
||||||
|
"mkdir -p /tmp/web-console; "
|
||||||
"cd /workspace/web-console; "
|
"cd /workspace/web-console; "
|
||||||
"if [ ! -d node_modules ]; then npm ci || npm install; fi; "
|
"tar --exclude=node_modules --exclude=.next --exclude=out -cf - . | tar -C /tmp/web-console -xf -; "
|
||||||
"npm run build"
|
"cd /tmp/web-console; "
|
||||||
|
"rm -rf node_modules .next out; "
|
||||||
|
"export HOME=/tmp npm_config_cache=/tmp/npm-cache; "
|
||||||
|
"if [ -f package-lock.json ]; then npm ci || npm install; else npm install; fi; "
|
||||||
|
"test -x node_modules/.bin/next; "
|
||||||
|
"npm run build; "
|
||||||
|
"rm -rf /workspace/web-console/out; "
|
||||||
|
"cp -a out /workspace/web-console/out"
|
||||||
)
|
)
|
||||||
cmd = [
|
cmd = [
|
||||||
docker,
|
docker,
|
||||||
@@ -300,6 +312,10 @@ def _docker_console_build() -> bool:
|
|||||||
"--rm",
|
"--rm",
|
||||||
"-u",
|
"-u",
|
||||||
f"{os.getuid()}:{os.getgid()}",
|
f"{os.getuid()}:{os.getgid()}",
|
||||||
|
"-e",
|
||||||
|
"HOME=/tmp",
|
||||||
|
"-e",
|
||||||
|
"npm_config_cache=/tmp/npm-cache",
|
||||||
"-v",
|
"-v",
|
||||||
f"{ROOT}:/workspace",
|
f"{ROOT}:/workspace",
|
||||||
"-w",
|
"-w",
|
||||||
@@ -390,7 +406,10 @@ def _start_docker_console_dev(*, host: str, port: str, next_port: str) -> subpro
|
|||||||
script = (
|
script = (
|
||||||
"set -e; "
|
"set -e; "
|
||||||
"cd /workspace/web-console; "
|
"cd /workspace/web-console; "
|
||||||
"if [ ! -d node_modules ]; then npm ci || npm install; fi; "
|
"if [ ! -x node_modules/.bin/next ]; then rm -rf node_modules .next; fi; "
|
||||||
|
"if [ ! -d node_modules ]; then "
|
||||||
|
"if [ -f package-lock.json ]; then npm ci || npm install; else npm install; fi; "
|
||||||
|
"fi; "
|
||||||
"npm run dev -- --hostname 0.0.0.0 --port 3000"
|
"npm run dev -- --hostname 0.0.0.0 --port 3000"
|
||||||
)
|
)
|
||||||
cmd = [
|
cmd = [
|
||||||
@@ -404,6 +423,10 @@ def _start_docker_console_dev(*, host: str, port: str, next_port: str) -> subpro
|
|||||||
"-e",
|
"-e",
|
||||||
f"API_PROXY_TARGET={proxy_target}",
|
f"API_PROXY_TARGET={proxy_target}",
|
||||||
"-e",
|
"-e",
|
||||||
|
"HOME=/tmp",
|
||||||
|
"-e",
|
||||||
|
"npm_config_cache=/tmp/npm-cache",
|
||||||
|
"-e",
|
||||||
"HOST=0.0.0.0",
|
"HOST=0.0.0.0",
|
||||||
"-e",
|
"-e",
|
||||||
"PORT=3000",
|
"PORT=3000",
|
||||||
|
|||||||
45
d2ypp2/scripts/linux/install_all.sh
Normal file
45
d2ypp2/scripts/linux/install_all.sh
Normal file
@@ -0,0 +1,45 @@
|
|||||||
|
#!/usr/bin/env bash
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
SELF_DIR="$(cd "$(dirname "$0")" && pwd)"
|
||||||
|
INSTALL_TAG="all"
|
||||||
|
. "$SELF_DIR/lib/common.sh"
|
||||||
|
|
||||||
|
ensure_root "$@"
|
||||||
|
load_env
|
||||||
|
|
||||||
|
ensure_live_user
|
||||||
|
normalize_repo_root
|
||||||
|
ensure_runtime_dirs_owned_by_live
|
||||||
|
install_base_packages
|
||||||
|
install_media_packages
|
||||||
|
configure_adb_udev
|
||||||
|
install_nodejs
|
||||||
|
install_docker_stack
|
||||||
|
install_android_panel
|
||||||
|
prepare_python_runtime
|
||||||
|
prepare_web_console
|
||||||
|
install_live_console_service
|
||||||
|
configure_sudoers
|
||||||
|
configure_mdns
|
||||||
|
configure_wifi_profile
|
||||||
|
install_shellcrash
|
||||||
|
install_browser_stack
|
||||||
|
install_neko_browser
|
||||||
|
install_redroid
|
||||||
|
prepare_mitmproxy
|
||||||
|
prepare_vscode_server
|
||||||
|
prepare_uptime_kuma
|
||||||
|
prepare_openclaw
|
||||||
|
install_pulseaudio_service
|
||||||
|
install_kmscube_service
|
||||||
|
install_webtty
|
||||||
|
install_cockpit
|
||||||
|
install_netdata
|
||||||
|
prepare_homepage
|
||||||
|
prepare_filebrowser
|
||||||
|
prepare_srs
|
||||||
|
run_hardware_probe
|
||||||
|
install_live_edge_proxy
|
||||||
|
ensure_runtime_dirs_owned_by_live
|
||||||
|
print_summary "all"
|
||||||
@@ -12,8 +12,7 @@ case "$PROFILE" in
|
|||||||
exec bash "$ROOT_DIR/scripts/linux/install_business.sh" "${@:2}"
|
exec bash "$ROOT_DIR/scripts/linux/install_business.sh" "${@:2}"
|
||||||
;;
|
;;
|
||||||
all|full)
|
all|full)
|
||||||
bash "$ROOT_DIR/scripts/linux/install_hub.sh" "${@:2}"
|
exec bash "$ROOT_DIR/scripts/linux/install_all.sh" "${@:2}"
|
||||||
bash "$ROOT_DIR/scripts/linux/install_business.sh" "${@:2}"
|
|
||||||
;;
|
;;
|
||||||
*)
|
*)
|
||||||
cat <<USAGE
|
cat <<USAGE
|
||||||
|
|||||||
@@ -701,31 +701,48 @@ install_docker_stack() {
|
|||||||
prepare_python_runtime() {
|
prepare_python_runtime() {
|
||||||
log "Preparing Python virtual environment"
|
log "Preparing Python virtual environment"
|
||||||
chown -R live:live "$ROOT_DIR"
|
chown -R live:live "$ROOT_DIR"
|
||||||
rm -rf "$ROOT_DIR/.venv"
|
local req_hash req_stamp
|
||||||
as_live "python3 -m venv .venv" || {
|
req_stamp="$ROOT_DIR/.venv/.requirements.sha256"
|
||||||
log "venv create failed; retry once with --clear"
|
req_hash="$(sha256sum "$ROOT_DIR/requirements.txt" "$ROOT_DIR/pyproject.toml" 2>/dev/null | sha256sum | awk '{print $1}')"
|
||||||
|
if ! as_live "test -x .venv/bin/python && .venv/bin/python -V >/dev/null 2>&1"; then
|
||||||
rm -rf "$ROOT_DIR/.venv"
|
rm -rf "$ROOT_DIR/.venv"
|
||||||
if ! as_live "python3 -m venv .venv"; then
|
as_live "python3 -m venv .venv" || {
|
||||||
log "WARN: venv still failed; using a shim over the system Python"
|
log "venv create failed; retry once with --clear"
|
||||||
rm -rf "$ROOT_DIR/.venv"
|
rm -rf "$ROOT_DIR/.venv"
|
||||||
create_python_venv_shim "$ROOT_DIR/.venv"
|
if ! as_live "python3 -m venv .venv"; then
|
||||||
fi
|
log "WARN: venv still failed; using a shim over the system Python"
|
||||||
}
|
rm -rf "$ROOT_DIR/.venv"
|
||||||
if ! as_live ". .venv/bin/activate && pip install --upgrade pip && pip install -r requirements.txt"; then
|
create_python_venv_shim "$ROOT_DIR/.venv"
|
||||||
log "pip install failed; retry with --no-cache-dir"
|
fi
|
||||||
as_live ". .venv/bin/activate && pip install --upgrade pip && pip install --no-cache-dir -r requirements.txt" || \
|
}
|
||||||
log "WARN: Python deps incomplete; control plane may fail until fixed manually"
|
else
|
||||||
|
log "Reusing existing Python virtual environment"
|
||||||
fi
|
fi
|
||||||
|
if [ -f "$req_stamp" ] && [ "$(cat "$req_stamp" 2>/dev/null)" = "$req_hash" ]; then
|
||||||
|
log "Python requirements unchanged; skipping pip install"
|
||||||
|
return 0
|
||||||
|
fi
|
||||||
|
if ! as_live ". .venv/bin/activate && python -m pip install --upgrade pip && python -m pip install -r requirements.txt"; then
|
||||||
|
log "pip install failed; retry with --no-cache-dir"
|
||||||
|
if ! as_live ". .venv/bin/activate && python -m pip install --upgrade pip && python -m pip install --no-cache-dir -r requirements.txt"; then
|
||||||
|
log "WARN: Python deps incomplete; control plane may fail until fixed manually"
|
||||||
|
return 0
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
printf '%s\n' "$req_hash" >"$req_stamp"
|
||||||
|
chown live:live "$req_stamp" 2>/dev/null || true
|
||||||
}
|
}
|
||||||
|
|
||||||
prepare_web_console() {
|
prepare_web_console() {
|
||||||
log "Building web console"
|
log "Building web console"
|
||||||
if as_live "cd web-console && if [ -f package-lock.json ]; then npm ci; else npm install; fi && npm run build"; then
|
if as_live ". .venv/bin/activate && python scripts/launch.py --build-only --no-env-check"; then
|
||||||
return 0
|
return 0
|
||||||
fi
|
fi
|
||||||
log "web console build failed; cleaning node_modules and retrying"
|
log "web console build failed; cleaning artifacts and retrying"
|
||||||
as_live "cd web-console && rm -rf node_modules .next && npm install && npm run build" || \
|
as_live "cd web-console && rm -rf node_modules .next out" || true
|
||||||
|
if ! as_live ". .venv/bin/activate && python scripts/launch.py --build-only --no-env-check"; then
|
||||||
log "WARN: web console build still failed — service may serve stale assets until rebuilt"
|
log "WARN: web console build still failed — service may serve stale assets until rebuilt"
|
||||||
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
install_live_console_service() {
|
install_live_console_service() {
|
||||||
@@ -736,6 +753,8 @@ install_live_console_service() {
|
|||||||
Description=Live Super Hub Control Plane
|
Description=Live Super Hub Control Plane
|
||||||
After=network-online.target docker.service
|
After=network-online.target docker.service
|
||||||
Wants=network-online.target
|
Wants=network-online.target
|
||||||
|
# 避免构建/依赖短暂失败时触发 systemd 默认「5 次/10s」后永久停跑(表现为 live-edge 502、:8001 无监听)
|
||||||
|
StartLimitIntervalSec=0
|
||||||
|
|
||||||
[Service]
|
[Service]
|
||||||
User=live
|
User=live
|
||||||
@@ -747,8 +766,6 @@ LimitNOFILE=$LIVE_NOFILE_SOFT
|
|||||||
ExecStart=$ROOT_DIR/start.sh
|
ExecStart=$ROOT_DIR/start.sh
|
||||||
Restart=always
|
Restart=always
|
||||||
RestartSec=5
|
RestartSec=5
|
||||||
# 避免构建/依赖短暂失败时触发 systemd 默认「5 次/10s」后永久停跑(表现为 live-edge 502、:8001 无监听)
|
|
||||||
StartLimitIntervalSec=0
|
|
||||||
# 首次 npm build / 冷启动较慢;过小会导致主进程在 listen 前被 SIGTERM
|
# 首次 npm build / 冷启动较慢;过小会导致主进程在 listen 前被 SIGTERM
|
||||||
TimeoutStartSec=300
|
TimeoutStartSec=300
|
||||||
TimeoutStopSec=30
|
TimeoutStopSec=30
|
||||||
@@ -1338,14 +1355,27 @@ else:
|
|||||||
path.write_text(text, encoding="utf-8")
|
path.write_text(text, encoding="utf-8")
|
||||||
PY
|
PY
|
||||||
chown -R live:live "$ANDROID_PANEL_DIR"
|
chown -R live:live "$ANDROID_PANEL_DIR"
|
||||||
rm -rf "$ANDROID_PANEL_DIR/.venv"
|
local panel_req_hash panel_req_stamp
|
||||||
if ! runuser -u live -- bash -lc "python3 -m venv '$ANDROID_PANEL_DIR/.venv'"; then
|
panel_req_stamp="$ANDROID_PANEL_DIR/.venv/.requirements.sha256"
|
||||||
log "WARN: Android panel venv failed; using a shim over the system Python"
|
panel_req_hash="$(sha256sum "$ANDROID_PANEL_DIR/requirements.txt" 2>/dev/null | awk '{print $1}')"
|
||||||
|
if ! runuser -u live -- bash -lc "test -x '$ANDROID_PANEL_DIR/.venv/bin/python' && '$ANDROID_PANEL_DIR/.venv/bin/python' -V >/dev/null 2>&1"; then
|
||||||
rm -rf "$ANDROID_PANEL_DIR/.venv"
|
rm -rf "$ANDROID_PANEL_DIR/.venv"
|
||||||
create_python_venv_shim "$ANDROID_PANEL_DIR/.venv"
|
if ! runuser -u live -- bash -lc "python3 -m venv '$ANDROID_PANEL_DIR/.venv'"; then
|
||||||
chown -R live:live "$ANDROID_PANEL_DIR/.venv"
|
log "WARN: Android panel venv failed; using a shim over the system Python"
|
||||||
|
rm -rf "$ANDROID_PANEL_DIR/.venv"
|
||||||
|
create_python_venv_shim "$ANDROID_PANEL_DIR/.venv"
|
||||||
|
chown -R live:live "$ANDROID_PANEL_DIR/.venv"
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
log "Reusing Android panel virtual environment"
|
||||||
|
fi
|
||||||
|
if [ ! -f "$panel_req_stamp" ] || [ "$(cat "$panel_req_stamp" 2>/dev/null)" != "$panel_req_hash" ]; then
|
||||||
|
runuser -u live -- bash -lc ". '$ANDROID_PANEL_DIR/.venv/bin/activate' && python -m pip install --upgrade pip && python -m pip install -r '$ANDROID_PANEL_DIR/requirements.txt'"
|
||||||
|
printf '%s\n' "$panel_req_hash" >"$panel_req_stamp"
|
||||||
|
chown live:live "$panel_req_stamp" 2>/dev/null || true
|
||||||
|
else
|
||||||
|
log "Android panel requirements unchanged; skipping pip install"
|
||||||
fi
|
fi
|
||||||
runuser -u live -- bash -lc ". '$ANDROID_PANEL_DIR/.venv/bin/activate' && pip install --upgrade pip && pip install -r '$ANDROID_PANEL_DIR/requirements.txt'"
|
|
||||||
allow_tcp_port_if_firewall_active "$ANDROID_PANEL_PORT"
|
allow_tcp_port_if_firewall_active "$ANDROID_PANEL_PORT"
|
||||||
|
|
||||||
cat >/etc/systemd/system/live-android-panel.service <<UNIT
|
cat >/etc/systemd/system/live-android-panel.service <<UNIT
|
||||||
|
|||||||
Reference in New Issue
Block a user