# popiartServer Local development backend for `popiartcli`. This is a thin single-server backend for local integration. It keeps the CLI contract stable while pushing model-heavy responsibilities back to `PopiNewAPI`. It is meant to validate these product-facing APIs first: - `auth` - `skills` - `run` - `jobs` - `artifacts` - `media` - basic `budget`, `project`, and `models` stubs ## Project Relationship See [docs/project-relationship.md](./docs/project-relationship.md). Persistence details for the current local backend are documented in [docs/persistence.md](./docs/persistence.md). Stable media URL behavior and rollout notes are documented in [docs/stable-media-url-v1.md](./docs/stable-media-url-v1.md). This note explains how `popiartcli`, `popiartServer`, and `PopiNewAPI` split responsibilities, and why routing, billing attribution, and provider access belong in the backend layers rather than the CLI. ## Run ```sh make run ``` Default address: ```text http://127.0.0.1:8080 ``` Health check: ```sh curl http://127.0.0.1:8080/health ``` Use it from `popiartcli`: ```sh cd /Users/jiajia/popiartcli go run ./cmd/popiart --endpoint http://127.0.0.1:8080/v1 auth login --key go run ./cmd/popiart --endpoint http://127.0.0.1:8080/v1 skills list go run ./cmd/popiart --endpoint http://127.0.0.1:8080/v1 media upload ./source.png go run ./cmd/popiart --endpoint http://127.0.0.1:8080/v1 artifacts upload ./source.png --role source ``` ### Jimeng action transfer `popiartServer` supports the `popiart video action-transfer` CLI path by routing `jimeng*` / DreamActor video model requests through PopiNewAPI's unified video gateway: ```text popiartcli -> POST /v1/models/infer -> popiartServer video.image2video job -> PopiNewAPI POST /v1/video/generations -> PopiNewAPI GET /v1/video/generations/{task_id} ``` CLI usage: ```sh popiart --endpoint http://127.0.0.1:8080/v1 video action-transfer \ --image ./face.jpg \ --video ./source-action.mp4 \ --cut-result-first-second-switch \ --wait \ --output json \ --quiet \ --non-interactive ``` Request mapping: - `model_id=jimeng_dreamactor_m20_gen_video` - `model_type=video` - `input.images[0]` becomes gateway `images[0]` - `input.videos[0]` becomes gateway `videos[0]` - `metadata.action` defaults to `actionGenerate` for DreamActor - `--cut-result-first-second-switch` maps to `metadata.cut_result_first_second_switch` - Image data URLs are normalized to pure base64 before submission because Jimeng rejects the `data:image/*;base64,` prefix. The test server at `http://101.42.99.35:18080/v1` has been verified with a 5 second action-transfer preview returning an MP4 artifact. ### Seedance / Doubao video `popiartServer` also supports Seedance / Doubao video models through the same `video.image2video` job lane, but submits them to PopiNewAPI's unified JSON video generations endpoint instead of the OpenAI-style `/v1/videos` path. CLI usage: ```sh popiart --endpoint http://127.0.0.1:8080/v1 video seedance \ --prompt "keep the motion style consistent" \ --video https://example.com/ref.mp4 \ --ratio 16:9 \ --return-last-frame \ --wait \ --output json \ --quiet \ --non-interactive ``` Request mapping: - default model: `doubao-seedance-2-0-260128` - `images[]`, `videos[]`, `audios[]` pass through to gateway JSON input - `size` and `duration` stay at top level - `action`, `frames`, `ratio`, `return_last_frame`, `generate_audio`, `service_tier`, and related options map into `metadata` Optional skillhub source: ```sh export POPIART_SKILLHUB_DIR=/tmp/Popiart_skillhub ``` In local development, `/tmp/Popiart_skillhub` is used automatically when it exists. ## Notes - Local persistence is intentionally thin: `sessions`, `job refs`, and project route overrides live in SQLite. - The local backend now keeps a lightweight media store under `POPIART_DATA_DIR/media/` and exposes stable `media` URLs for uploaded files and persisted job outputs. - `artifact` metadata is still derived from `result_refs_json`, but new artifacts bind to a local `media_id` and a stable `url`. - New endpoints now include: - `POST /v1/media/upload` - `GET /v1/media/:id` - `GET /v1/media/:id/content` - `job logs` are synthesized from job state transitions instead of being stored as a separate table. - The local development backend verifies your login key against the local `PopiNewAPI`. - This server is a development backend, not the final production architecture.