| name | alibabacloud-ecs-code-deploy |
| description | 基于 aliyun appmanager 一键把项目代码部署到阿里云 ECS 云服务器,覆盖环境预检、询价、部署、日志验证、失败诊断重试全流程。支持 App / AI Agent(LangChain / AutoGen / AgentScope / MCP / FastAPI / Flask / Spring Boot 等),新建或已有 ECS 实例,自动处理分组冲突、zip 解压、余额不足、地域参数透传、重复部署免初始化。触发词:部署到ECS、部署项目到ECS、部署到云服务器、把这个项目部署上去、上线到ECS、把仓库部署到ECS、当前目录部署、阿里云ECS部署、appmanager部署、aliyun appmanager、一键部署App、部署AI Agent、deploy to ECS、code deploy、deploy app、deploy agent、appmanager deploy、ECS code deploy、跑一下这个项目、把代码跑到ECS上、ECS上线。 |
Deploy to Alibaba Cloud ECS via aliyun appmanager
Overview
aliyun appmanager is an Agent-friendly CLI tool for one-click deployment of applications (App) and AI Agents to Alibaba Cloud ECS. It supports non-interactive mode (--non-interactive), structured JSON output (--output json), and streaming NDJSON responses.
Default behavior: When user invokes /alibabacloud-ecs-code-deploy without specifying a project path or URL, deploy the current working directory project to Alibaba Cloud ECS. If user provides a git URL, clone it to the current directory first, then cd into the cloned directory and proceed with deployment.
EXECUTION ORDER: The Agent MUST follow the "Complete Deployment Workflow" section at the bottom of this document for the correct execution sequence. The Task sections below are organized by topic for reference — their numbering does NOT imply execution order.
MANDATORY: Create Todo List Before Starting
Before executing any step, the Agent MUST create a todo list with ALL of the following items. Do NOT omit any item. Do NOT start deployment until the todo list is created.
Todo list (Deploy to Alibaba Cloud ECS):
[ ] 0. Resolve $SKILL_DIR (cross-platform path — MUST run first; see "Step 0" below)
[ ] 1. Environment pre-check (MUST run deploy_toolkit.py check; manual commands FORBIDDEN as replacement)
[ ] 2. Obtain project (clone git URL here if needed; skip for local projects)
── Check whether .appmanager/config.yaml already exists (repeat-deploy shortcut) ──
│ Exists + new ECS (no instanceId) → skip 3-5, start from 5.5 (price check)
│ Exists + existing ECS (has instanceId) → skip 3-5.5, jump to 6 (deploy)
│ Does not exist → proceed normally from 3
───────────────────────────────────────────────────────────────────────────────
[ ] 3. Read project (README.md -> quick-deploy method) + identify type (agent / app)
[ ] 4. Ask user for deployment config (region + new ECS / existing ECS)
[ ] 5. Init + generate scripts (appmanager init -> write start/stop scripts to config.yaml)
[ ] 5.5. Pre-deploy price check + risk warning (MUST run deploy_toolkit.py price; confirm price / OSS billing / existing-ECS impact / group overwrite item by item)
[ ] 6. Deploy (MUST run deploy_toolkit.py deploy; manual deploy command FORBIDDEN as replacement)
[ ] 7. Verify (MUST run deploy_toolkit.py verify; manual status command FORBIDDEN as replacement)
[ ] 8. Output final result (console link + cost reminder + management commands)
⛔ SCRIPT-FIRST RULE: Steps 1, 5, 6, 7 have a dedicated toolkit script at $SKILL_DIR/scripts/deploy_toolkit.py (where $SKILL_DIR is resolved in Step 0 below — works on Qoder, Claude Code, and any other platform). The Agent MUST run the corresponding subcommand DIRECTLY as the FIRST and ONLY action for that step — NEVER run manual CLI commands (like aliyun version, version checks, credential checks) BEFORE or INSTEAD of the script. The script already handles ALL checks internally. Manual commands are ONLY allowed as fallback if the script file itself does not exist.
❌ WRONG (Step 1): Run aliyun version → check version → run ~/.aliyun/appmanager-venv/bin/python ... → check version → THEN run deploy_toolkit.py check
✅ CORRECT (Step 1): Run python3 "$SKILL_DIR/scripts/deploy_toolkit.py" check → if exit 1, fix the issue it reports → if script file missing, THEN fall back to manual checks
Item 6 is NON-NEGOTIABLE. An Agent that skips log verification and directly outputs "deployment succeeded" has NOT completed this skill correctly. If deploy_toolkit.py verify exits 1 (failed), the Agent MUST fix the issue and re-deploy before proceeding to item 7.
Step 0 (MANDATORY): Resolve $SKILL_DIR — Cross-Platform Path
The toolkit script lives at <skill-root>/scripts/deploy_toolkit.py. Different platforms install skills to different locations (Qoder/Claude Code/Qwen/...). The Agent MUST resolve the absolute skill root once at session start and reuse it everywhere $SKILL_DIR appears below. Hardcoding any platform-specific path is FORBIDDEN.
See references/skill-dir-resolution.md for the full 10-candidate detection algorithm, the export + test -f verify snippet, and Pattern A / Pattern B / ⛔ Anti-pattern usage rules.
Quick recap (read the reference for details):
- ✅ Pattern A (persistent shell):
export SKILL_DIR="/abs/path" then later python3 "$SKILL_DIR/scripts/deploy_toolkit.py" <sub>
- ✅ Pattern B (fresh shell per call): inline the absolute path —
python3 "/abs/path/scripts/deploy_toolkit.py" <sub>
- ⛔ Anti-pattern:
SKILL_DIR=/path python3 "$SKILL_DIR/..." — outer shell expands $SKILL_DIR BEFORE the prefix assignment, producing /scripts/deploy_toolkit.py and ENOENT. If you see python3: can't open file '/scripts/deploy_toolkit.py', switch to Pattern A or B.
Task 1: Install Alibaba Cloud CLI
Primary action: Run python3 "$SKILL_DIR/scripts/deploy_toolkit.py" check — it checks CLI version + appmanager-cli version + credentials in one run. Only if the script file is missing, use the fallback in references/init-and-credentials.md.
MUST — Handling unmet environment prerequisites: When check exits 1 because the aliyun CLI is missing or older than 3.3.19 (or appmanager-cli is missing/outdated), the Agent MUST NOT stop the workflow silently. The required flow is:
- CLI NOT installed → Auto-install directly without asking user — execute the install command (see snippet below or references/init-and-credentials.md for the right arch), then re-run
deploy_toolkit.py check to confirm.
- CLI already installed → ASK the user first — show the detected version + the required version + the upgrade command, and ask for explicit consent (e.g. "aliyun CLI 3.3.4 is already installed but below the required >= 3.3.19 for appmanager; approve upgrade (overwrite-install into /usr/local/bin, requires sudo)?"). Never assume yes; never paste credentials.
- On approval — execute the install/upgrade command, then re-run
deploy_toolkit.py check to confirm.
- On refusal — stop with the refusal as the reason. Do NOT continue with the older version (deployment will fail anyway).
The toolkit's check output already includes an → AGENT: DO NOT stop. ASK user ... line for each fixable issue — follow it verbatim (except for the "not installed" case, which is auto-handled).
MUST — Upgrade method priority: brew-managed → brew upgrade (do NOT overwrite /usr/local/bin/ again); sudo → overwrite /usr/local/bin/; no sudo → ~/bin/ + PATH persist (Unix). Scoop/Choco → %USERPROFILE%\bin + User PATH (Windows). Full priority rules → references/init-and-credentials.md § "CLI Install/Upgrade Method Priority". After install/upgrade, ALWAYS rerun deploy_toolkit.py check to confirm; if which -a aliyun still shows the old binary first, fix PATH order — DO NOT repeat the same overwrite.
Observability (MANDATORY): User-Agent Injection
⛔ Every aliyun CLI call MUST carry this skill's User-Agent so all API requests are traceable in cloud-side logs. The Agent MUST export the UA env var ONCE at session start (right after Step 0), before any aliyun / deploy_toolkit.py invocation.
Full UA template:
AlibabaCloud-Agent-Skills/alibabacloud-ecs-code-deploy/{session-id}
session-id unified rules:
- Generate ONCE per agent session:
SESSION_ID=$(uuidgen | tr '[:upper:]' '[:lower:]') — lowercase UUID (any lowercase-hex random token ≥ 16 chars is equivalent).
- Reuse the SAME session-id for ALL CLI calls within the session — NEVER regenerate per command, otherwise one deployment scatters into untraceable fragments.
- Persist consistently with the Step 0 rules: Pattern A
export SESSION_ID=... (persistent shell) or inline the literal value (fresh shell per call).
Injection method (modern — env var):
export ALIBABA_CLOUD_USER_AGENT="AlibabaCloud-Agent-Skills/alibabacloud-ecs-code-deploy/${SESSION_ID}"
⛔ The legacy aliyun configure ai-mode enable / set-user-agent mechanism is DEPRECATED — do NOT use it. Do NOT combine ALIBABA_CLOUD_USER_AGENT with ai-mode or per-command env prefixes for the same skill token: the CLI stacks these sources and produces duplicate UAs. Set the env var ONCE per session and leave it.
Task 2: Configure Credentials
deploy_toolkit.py check already validates credentials. Only if credentials are missing/invalid, see references/init-and-credentials.md for the default-credential-chain remediation flow.
⛔ PREFER OAuth OVER AK: OAuth is more secure and convenient (no long-term secret storage). The Agent MUST present OAuth as the first option. When the user agrees, the Agent runs the login command directly — but MUST first warn the user that the command opens a browser authorization page and blocks until the user completes authorization in the browser — then execute aliyun configure --mode OAuth --profile oauth and verify with aliyun sts get-caller-identity --profile oauth.
⛔ SA-2.12 — DO NOT collect AK/SK in chat: If the user prefers AK auth, give one ready-to-run command template with placeholders — aliyun configure set --profile default --mode AK --access-key-id <your-access-key-id> --access-key-secret <your-access-key-secret> --region cn-hangzhou — and ask the user to fill in their own AK/SK and run it in their own terminal. The Agent NEVER asks the user to paste AccessKey/Secret/STS-Token values into the chat, NEVER puts raw AK/SK in tool-call arguments or scripts, and NEVER echoes credential values. The default credential chain (ECS RAM Role / env vars / pre-existing ~/.aliyun/config.json) is also honored. Full remediation flow → references/init-and-credentials.md.
CRITICAL PROHIBITION: NEVER run standalone appmanager or aliyun appmanager login.
Task 3: Initialize Project
Step 1 (MANDATORY): Read README.md FIRST
CRITICAL ORDERING RULE: Before scanning any project files, the Agent MUST read README.md (or README) in the project root. This is ALWAYS the first action in Task 3.
What to extract from README:
- Quick-start / deploy commands (e.g.
pip install -r requirements.txt && python main.py, npm install && npm start)
- Official build/run commands, Docker deploy methods, port number, required environment variables
MANDATORY: Present README Methods to User and Follow Decision Tree
Step A: List what README provides to the user.
Step B: Select method by priority:
| Priority | Method Type | Action |
|---|
| 1 (HIGHEST) | Native CLI / package manager install (npm install -g, pip install, go install) | Use directly |
| 2 | Native build + run (pip install && python main.py, npm install && npm start) | Use, install runtime |
| 3 | Script-based deploy (bash deploy.sh) | Must confirm non-interactive |
| 4 (LOWEST) | Docker / docker-compose | Only when no higher priority exists; check China accessibility |
Step C: Execute based on scenario:
- README has native method (priority 1/2) → Use it directly as start script core. NEVER ignore README and build from scratch.
- README only has Docker → Check image accessibility (see references/script-templates.md "Docker Image Accessibility Check"). Warn user about China mirror risks.
- README has no deploy info / absent → Agent scans project files independently (only allowed case).
Why README first? Most projects document the exact build/run commands. Auto-detecting from files alone is error-prone.
Step 2: Determine project type
| Condition | Type |
|---|
Project depends on agentscope | agent |
| Everything else (langchain, mcp, autogen, web services, tools, etc.) | app |
Determine --name
Use the project directory name (lowercased, hyphens). Inform user: Default app name uses the directory name <name>.
Determine --region and ECS target (MUST ask user)
Agent MUST ask both questions together in ONE message:
1. Which region do you want to deploy to?
- Shanghai (cn-shanghai) / Hangzhou (cn-hangzhou) / Beijing (cn-beijing) / Shenzhen (cn-shenzhen) / Guangzhou (cn-guangzhou) / Chengdu (cn-chengdu) / Nanjing (cn-nanjing) / Hong Kong (cn-hongkong)
2. New ECS or existing ECS?
- New ECS (auto-create instance, pay-as-you-go)
- Existing ECS (choose from the list below, or provide an instance ID manually)
NEVER use zone-based labels like "East China 1" / "North China 2". NEVER add descriptions. City names only.
Existing ECS — list the user's latest 10 instances in the chosen region (MANDATORY)
When the user picks existing ECS, the Agent MUST first query the account's 10 most-recently-created instances in the chosen region (plugin mode: aliyun ecs describe-instances) and present them as a numbered list for selection — do NOT force the user to recall an instance ID from memory. Always also allow manual instance ID entry (e.g. i-bp1xxxxxxxx) as a fallback. The query MUST pass the same --profile as deployment (same account), otherwise it may return zero / wrong instances. Full command (jq pipeline, no-jq fallback, zero-instance handling) → references/init-and-credentials.md § "Listing existing ECS instances". The selected/entered ID is passed to appmanager init --ecs existing --instance-id <ID>.
⚠️ REGION PROPAGATION CHECK (MANDATORY): The chosen region MUST be passed verbatim to appmanager init --region, written into config.yaml common.deployment.regionId, AND attached as --region <REGION_ID> to every subsequent deploy_toolkit.py {price,deploy,verify} invocation. Mismatch / omission triggers InvalidParameter: DeployRegionId is invalid from the OOS API.
Determine --port (App type only, OPTIONAL)
Only specify when the project actually listens on HTTP. Skip for background services (bots, workers, CLI tools). If needed but unknown, default to 8080. Agent type does NOT use --port.
Non-interactive init
See references/init-and-credentials.md for all init flag combinations.
Creates .appmanager/config.yaml. Does NOT support --overwrite — delete .appmanager/ first if exists.
Task 4: Generate Deploy Scripts
For ALL project types, the Agent MUST generate deployment scripts and write them into .appmanager/config.yaml.
Workflow
- Read README.md FIRST — follow Task 3 decision tree
- If README has no deploy info — scan project structure (Language Detection below)
- Docker accessibility check — if Docker path selected (see references/script-templates.md)
- Generate start & stop scripts — following rules below. Start script MUST ALWAYS include zip extraction sequence.
- Write to config.yaml — under
common.scripts.start and common.scripts.stop (NEVER top-level scripts)
Language Detection, Files to Read & Entry Points
Language detection rules (indicator files), MUST-read files per language, and entry point detection order → references/script-templates.md § "Project Analysis".
General Script Rules
| Rule | Requirement |
|---|
| ⛔ MANDATORY zip extract | Start script MUST: find zip → mkdir -p → unzip -o → cd. Without this, project dir DOES NOT EXIST on ECS |
| Runtime install | MUST install language runtime FIRST (ECS is bare) |
| Install unzip | command -v unzip &>/dev/null || $PKG_MGR install -y unzip |
| Idempotent | Safe to run multiple times |
| ⛔ Log file FIXED path | MUST be /root/app.log and /root/app.pid. verify script hardcodes these paths |
| Log append | Always >> (never >) |
| PID file | echo $! > /root/app.pid after nohup ... & |
| Background run | nohup ... >> /root/app.log 2>&1 & |
| Stop old process | [ -f /root/app.pid ] && kill "$(cat /root/app.pid)" 2>/dev/null || true |
| App dir | /root/{app_name} |
| No heredoc | NEVER use << 'EOF' inside scripts — breaks YAML. Use printf or python3 -c |
| MANDATORY tail log | End with sleep 3 && cat /root/app.log for verification capture |
| ⛔ Stop script: NO exit | MUST NOT contain exit. Deploy system concatenates stop+start — exit kills the entire process |
ECS instances are bare Linux (typically Alibaba Cloud Linux, RHEL-based, uses yum/dnf).
For script templates, language install commands, and config.yaml writing method, see references/script-templates.md.
Task 4.5: Pre-deploy Price Check + Risk Warning
MANDATORY: Before deploying, run deploy_toolkit.py price. The script outputs the price estimate (with OSS extra-billing reminder) and, when applicable, a risk warning block. The Agent MUST present every flagged item to the user and obtain explicit confirmation BEFORE running deploy.
python3 "$SKILL_DIR/scripts/deploy_toolkit.py" price --config .appmanager/config.yaml
- Exit 0 +
=== AGENT_CONFIRM_REQUIRED ===: present the complete price + risk warning to the user, confirm item by item.
- Exit 1: price query failed; do NOT proceed to deploy.
The Agent MUST confirm up to 3 items (price + OSS fees / existing-ECS risk / group overwrite choice) — see references/deploy-output-and-management.md § "Pre-deploy Price Check: Confirmation Items" for detailed descriptions and example phrasing.
Until ALL applicable confirmations are complete, the Agent MUST NOT invoke deploy_toolkit.py deploy.
Task 5: Deploy
aliyun appmanager <agent|app> deploy --overwrite --output json
STOP after deploy success — status: success only means orchestration completed. Agent MUST run Task 6 verification before outputting results.
Handling deployment failure
⛔ MANDATORY FAILURE GATE: After ANY deploy failure (exit 1, timeout, or ReleaseCancelled), the Agent MUST run deploy_toolkit.py verify IMMEDIATELY — BEFORE any fix attempt, fallback to manual commands, or partial output. Skipping verify after a failure is FORBIDDEN and counts as skill failure.
Semantics of ReleaseCancelled: it means the start script on ECS failed or timed out. It does NOT mean "someone cancelled the deploy". The only correct next action: run deploy_toolkit.py verify -> read the log -> fix the script -> redeploy.
Known failure patterns: Before ad-hoc troubleshooting, check references/lessons-learned.md for previously identified deployment failure patterns and proven fixes.
Failure-handling flow:
- Run
deploy_toolkit.py verify to fetch /root/app.log (DO NOT skip).
- Analyze the log to locate root cause.
- Fix scripts and redeploy (max 3 attempts).
- After 3 failures, stop — report the error, but still output console link + cost reminder + delete command.
Task 6: Post-deploy Verification (BLOCKING)
status: Deployed does NOT mean the application is running. The Agent MUST run verify and semantically analyze the log.
- Run
deploy_toolkit.py verify (auto-reads parameters from config.yaml).
- Agent semantically analyzes the log to decide whether the application actually started successfully.
- Not running -> diagnose -> fix -> redeploy + verify (max 3 attempts).
- Only when running is confirmed / user manual action required / 3 attempts failed should the Agent output the final result.
Task 7 & 8: List, Delete, Validate & Final Output
See references/deploy-output-and-management.md for:
- List/Delete commands
- Config validation
- Config template reference
- Critical notes & pitfalls
- MANDATORY post-deploy output format (console link, cost reminder, usage guide)
Pre-output Gate — Self-check (⛔ BLOCKING)
Before outputting results, Agent MUST print the exact Deployment self-check report template (see Workflow Step 7.5). Skipping the report = skill failure (not an optional summary). If any item is ❌, fix it BEFORE outputting Step 8.
📘 Hands-on walk-through with concrete inputs/outputs and edge cases (Python Flask example): see references/tutorial-flask-app.md.
Complete Deployment Workflow
⛔ MANDATORY EXECUTION RULE: The Agent MUST follow this sequence exactly. For steps that specify a script (steps 1, 5, 6), the Agent MUST run the script — NEVER manually replicate the script's logic with individual commands. The Task sections above are REFERENCE ONLY (for understanding what the scripts do internally or as fallback if scripts are missing).
# 0. Resolve $SKILL_DIR (MANDATORY — see "Step 0" section above for full algorithm)
# → Detect the absolute directory containing THIS SKILL.md (most accurate)
# → Or fall back to platform-specific candidates: ~/.qoder/skills/..., ~/.claude/skills/..., ~/.qwen/skills/..., $SKILLS_HOME/..., etc.
# → Pattern A (persistent shell): export SKILL_DIR=<abs_path> ; verify $SKILL_DIR/scripts/deploy_toolkit.py exists ; reuse $SKILL_DIR everywhere
# → Pattern B (fresh shell per command): inline the absolute path — `python3 "/abs/path/scripts/deploy_toolkit.py" ...`
# → ⛔ NEVER use `SKILL_DIR=/path python3 "$SKILL_DIR/..."` — outer shell expands $SKILL_DIR
# BEFORE the prefix assignment, producing `/scripts/deploy_toolkit.py` and ENOENT.
# 1. Environment check (MUST use deploy_toolkit.py check — DO NOT run manual commands)
python3 "$SKILL_DIR/scripts/deploy_toolkit.py" check
# ⛔ FORBIDDEN: running `aliyun version`, `~/.aliyun/appmanager-venv/bin/python -c "..."`,
# credential checks, or ANY manual version-check commands before or instead of this script.
# The script checks ALL of: CLI version + appmanager-cli version + credentials in one run.
# Just run the script. Period.
# → If exit 0: all checks passed, proceed to step 2
# → If exit 1, address the issue printed by the script:
# ⚠️ DO NOT stop silently. For every fixable ❌ line the script prints,
# Agent MUST follow the flow below:
# - aliyun CLI NOT installed: AUTO-INSTALL directly (no need to ask user)
# - aliyun CLI already installed but outdated: ASK user to approve upgrade
# (covers to /usr/local/bin, needs sudo), then run the install command
# printed by the script (see Task 1).
# - appmanager-cli < 1.1.1 or BROKEN venv: ASK user to approve
# `rm -rf ~/.aliyun/appmanager-venv` (auto-recreates on next aliyun
# appmanager run).
# ⚠️ This path is fixed at ~/.aliyun/appmanager-venv (the venv is self-managed
# by the aliyun CLI). After deletion, the next `aliyun appmanager` run
# auto-recreates it. The Agent MUST use this exact literal path —
# NEVER replace it with a variable or build it via concatenation,
# to avoid accidentally wiping user data.
# - credentials missing/invalid: present OAuth-first remediation
# to the user (OAuth / RAM Role / env vars / `aliyun configure` interactive) — NEVER
# collect AK/SK in chat. See Task 2 + references/init-and-credentials.md.
# → If user refuses any fix: stop with that refusal as the reason — DO NOT
# continue with a broken environment (deployment will fail anyway).
# → If script file not found: ONLY THEN fall back to manual checks (Task 1 + Task 2)
# 2. Obtain project source (if needed)
# → If git URL provided: clone to CURRENT WORKING DIRECTORY, cd into cloned dir
# git clone <URL> && cd <cloned_dir>
# → If local path / current directory: skip this step, use directly
# 🔀 REPEAT DEPLOYMENT SHORTCUT — check BEFORE step 3
# → Check if .appmanager/config.yaml already exists in the project directory
# → If YES (config.yaml exists):
# Read the file and check for common.deployment.instanceId:
# - instanceId ABSENT (new ECS): skip steps 3-5, jump to step 5.5 (price check)
# - instanceId PRESENT (existing ECS): skip steps 3-5.5, jump to step 6 (deploy)
# In both cases, inform user: "Existing .appmanager/config.yaml detected; will reuse the existing config and deploy directly."
# → If NO (config.yaml does NOT exist): proceed normally from step 3
# 3. Read project + identify type (agent or app)
# → READ README.md FIRST — highest priority source for deployment method:
# - Agent MUST list README's methods to user and select by priority:
# Native CLI install > Native build+run > Script deploy > Docker
# - ❌ NEVER ignore README methods and scan project files instead
# - ❌ NEVER prefer Docker when native methods are available
# - Docker: ONLY when no native method exists, MUST warn user about China mirror risks
# - Only if README absent/empty/no deploy info → Agent scans project files independently
# → Only classify as "agent" if project depends on `agentscope`; everything else is "app"
# → Determine --name from directory name, --port from project config/README
# → For Docker: check image accessibility from China (see references/script-templates.md)
# 4. Ask user for deployment region + ECS target (MANDATORY — ask together in one question)
# → Question 1: "Which region do you want to deploy to? Shanghai(cn-shanghai)/Hangzhou(cn-hangzhou)/Beijing(cn-beijing)/Shenzhen(cn-shenzhen)/Guangzhou(cn-guangzhou)..."
# → Question 2: "New ECS or existing ECS?" — if existing, FIRST query the account's 10 most-recently-created
# ECS instances in the chosen region and present them as a numbered list for selection:
# aliyun ecs describe-instances --biz-region-id <REGION> --region <REGION> --page-size 100 | jq -r '.Instances.Instance | sort_by(.CreationTime) | reverse | .[:10] | .[] | "..."' (plugin mode; no `--output json`; JSON is the default)
# Also always support manual instance ID entry (e.g. i-bp1xxxxxxxx). See Task 3 "Existing ECS" section.
# → NEVER use zone-based labels like "East China 1" / "North China 2" — always use city names
# → NEVER skip the ECS choice and default to creating new
# → ⚠️ Region MUST be propagated verbatim to: appmanager init --region, config.yaml common.deployment.regionId, AND every deploy_toolkit.py --region. Mismatch → InvalidParameter: DeployRegionId from OOS API.
# 5. Init + generate scripts (appmanager init → write start/stop to config.yaml)
# → If .appmanager/ already exists in the CURRENT project directory, ask user before removing.
# ⚠️ DESTRUCTIVE: `rm -rf .appmanager` deletes the existing deployment config.
# Required guard before deletion:
# a. Confirm CWD matches the intended project directory (`pwd` shows expected path)
# b. Confirm target is the relative path `.appmanager` (NEVER absolute, NEVER with variables)
# c. Inform the user "About to delete the existing deployment config under ./.appmanager/. This is irreversible." and obtain consent
# Recommended safer alternative: back up first
# mv .appmanager .appmanager.bak.$(date +%Y%m%d%H%M%S)
# Only after explicit user consent: rm -rf ./.appmanager
# → Run: aliyun appmanager init --non-interactive --name <DIR_NAME> --type <app|agent> --region <REGION> [--port <PORT>] [--ecs existing --instance-id <ID>] [--model qwen3.6-plus --api-key "$API_KEY"]
# (See references/init-and-credentials.md for full flag combinations by type)
# → Then generate start/stop scripts and write to config.yaml:
# - MUST write to common.scripts.start and common.scripts.stop (NEVER top-level scripts key)
# - Use python3 yaml library: config['common']['scripts'] = {'start': ..., 'stop': ...}
# - PRIORITY: README deployment commands → use directly; only auto-generate when README has none
# - ⛔ MANDATORY: Start script MUST ALWAYS include zip extraction (mkdir + unzip + cd) BEFORE
# any build/run commands. appmanager uploads zip but does NOT extract it.
# 5.5. Pre-deploy price check + risk warning (MUST run deploy_toolkit.py price — Agent handles user confirmation)
python3 "$SKILL_DIR/scripts/deploy_toolkit.py" price --config .appmanager/config.yaml
# → Script output structure:
# [Price table] estimate from `appmanager price` (order-billed resources: ECS/EIP/bandwidth) + the trailing 📦 OSS extra-billing reminder
# [Risk warning] only when detected: [Existing-ECS deployment risk] / [Group overwrite risk] / [Failure-leftover group]
# → Script does NOT ask user for confirmation — that's the Agent's job
# → If exit 0: Agent MUST read the output, present the COMPLETE breakdown to user — including:
# 1) Price estimate + OSS extra-billing reminder (OSS storage ~CNY 0.12/GB/month, public outbound ~CNY 0.50/GB only when cross-region, requests billed per 10k)
# 2) If output contains [Existing-ECS deployment risk] -> ask whether to deploy onto that existing ECS (may impact other apps on it)
# 3) If output contains [Group overwrite risk] -> ask user to choose A (overwrite) or B (new group)
# Example: "Estimated cost: compute resources CNY X.XXX/hour (~CNY XXX.XX/month); public traffic billed by usage at CNY 0.80/GB;
# the deployment also incurs minor OSS storage and request fees (intra-region pull is free of public outbound charges).
# Confirm to continue?"
# → After ALL items confirmed by user: run the matching deploy command per item 3's choice (default overwrite / --force-new-group for new group)
# → If ANY item refused: STOP deployment
# → If exit 1: price query failed, show error to user, do NOT proceed
# 6. Deploy (MUST use deploy_toolkit.py deploy — DO NOT run deploy manually)
python3 "$SKILL_DIR/scripts/deploy_toolkit.py" deploy \
--type <agent|app> --name <APP_NAME> --group <GROUP_NAME> --region <REGION_ID>
# ⛔ FORBIDDEN: running `aliyun appmanager deploy` directly without this script
# → Handles: group status check → conflict auto-resolve → deploy
# → Exit 0: deploy submitted, proceed to step 7
# → Exit 1: ⛔ MUST run step 7 (verify) IMMEDIATELY to fetch /root/app.log;
# skipping to step 8, outputting partial results, or running manual
# commands instead is FORBIDDEN. Then fix script per log and redeploy
# (max 3 attempts).
# 7. Verify (MUST use deploy_toolkit.py verify — DO NOT check status manually)
python3 "$SKILL_DIR/scripts/deploy_toolkit.py" verify \
--type <agent|app> --name <APP_NAME> --group <GROUP_NAME> --region <REGION_ID>
# ⛔ FORBIDDEN: running `aliyun appmanager status` + manual log analysis instead of this script
# → Optional: --wait <seconds> for slow-starting apps (default 3s, Java/heavy use 15-30)
# → Dual-path: Cloud Assistant cat /root/app.log (preferred) → deployCommandOutput (fallback)
# → Exit 0: app running, proceed to step 8
# → Exit 1: app failed — fix start script, re-deploy (back to step 6)
# → Exit 2: inconclusive — retry with longer --wait or suggest SSH check
# 7.5. Self-check summary (⛔ BLOCKING — skill fails if omitted)
# MUST print the exact template below to the user — this is a completion criterion, NOT optional.
#
# ---
# ✅ Deployment self-check report:
# 0. Path resolution — SKILL_DIR=___ (script exists ✅)
# 1. Environment pre-check — CLI v___ / appmanager-cli v___ / credentials valid ✅
# 2. Project obtained — (local / cloned) ✅
# 3. Project identified — type: ___ / deploy method source: README.md ✅
# 4. Deployment region — user choice: ___ ✅
# 5. Init + scripts — config.yaml generated; start script: ___ (key command summary) ✅
# 5.5. Pre-deploy price check — user confirmed price (CNY ___/hour, ~CNY ___/month) ✅
# 6. Deploy executed — deploy_toolkit.py deploy exit 0 ✅
# 7. Run verification — deploy_toolkit.py verify exit 0 / log keywords: ___ ✅
# ---
#
# If any item is ❌, fix it BEFORE step 8 — this is for the USER to see, proving the work is properly done.
# 8. Output results (MANDATORY: console link + cost reminder + management commands)
# → See references/deploy-output-and-management.md for full output format