support multiple Coolify instances — select by identifier instead of editing .coolify.env #14

Closed
opened 2026-07-13 15:35:42 +00:00 by dan-claude-bot · 0 comments
dan-claude-bot commented 2026-07-13 15:35:42 +00:00 (Migrated from github.com)

Problem

loadConfig (src/config.ts) reads exactly one COOLIFY_BASE_URL +
COOLIFY_ACCESS_TOKEN from <state>/.coolify.env, with no env-var or flag
override. The connection target is implicit in a file's current contents.
Retargeting cast at a different Coolify instance therefore means hand-editing
that file — and putting it back afterwards.

That is uncomfortable in normal use and genuinely unsafe during the prod
migration (D-193). There, the state repo's .coolify.env holds a
write + deploy token for the new control plane, while the migration's
verification gate requires a --full diff of the new manifest against the
legacy, hand-built box that is currently serving live users. Today the only
ways to do that are to overwrite the live .coolify.env or to clone the whole
state dir just to vary one untracked file. The failure mode of getting it wrong
is running apply against production.

The instance you are pointing at is the single most consequential input to any
cast command. It should be explicit at the call site.

Proposal

  • Keep <state>/.coolify.env working exactly as today (single instance, no
    flag → no behavior change).
  • Add named instances: <state>/.coolify/<name>.env, each holding its own
    COOLIFY_BASE_URL + COOLIFY_ACCESS_TOKEN.
  • Add --instance <name> to every verb that reaches Coolify
    (apply, diff, server add, smoke, team).
  • Optionally let environments.yaml bind a default instance per environment
    (environments.prod.instance: prod-cp), so --env prod selects the right
    control plane with no flag and no file edit at all.
  • Refuse, don't guess, when --instance names an unknown instance — and
    name the instances that do exist, in the same spirit as the absent-target
    refusal from #12 (D-237).

Nice-to-have on the same theme: let an instance declare its expected token
scope (e.g. read_only: true), so an instance configured for inspection cannot
be used by apply even if the token itself would permit the writes. That turns
"I pointed the wrong token at the wrong box" from a live incident into an exit
code.

Acceptance

  • cast diff <slug> --env prod --instance legacy works with no edit to
    .coolify.env.
  • An unknown --instance refuses and lists the known instances.
  • With no --instance flag, behavior is unchanged from today.
## Problem `loadConfig` (`src/config.ts`) reads exactly one `COOLIFY_BASE_URL` + `COOLIFY_ACCESS_TOKEN` from `<state>/.coolify.env`, with no env-var or flag override. **The connection target is implicit in a file's current contents.** Retargeting cast at a different Coolify instance therefore means hand-editing that file — and putting it back afterwards. That is uncomfortable in normal use and genuinely unsafe during the prod migration (D-193). There, the state repo's `.coolify.env` holds a **`write` + `deploy`** token for the new control plane, while the migration's verification gate requires a `--full` diff of the new manifest against the **legacy, hand-built box that is currently serving live users**. Today the only ways to do that are to overwrite the live `.coolify.env` or to clone the whole state dir just to vary one untracked file. The failure mode of getting it wrong is running `apply` against production. The instance you are pointing at is the single most consequential input to any cast command. It should be explicit at the call site. ## Proposal - Keep `<state>/.coolify.env` working exactly as today (single instance, no flag → no behavior change). - Add **named instances**: `<state>/.coolify/<name>.env`, each holding its own `COOLIFY_BASE_URL` + `COOLIFY_ACCESS_TOKEN`. - Add **`--instance <name>`** to every verb that reaches Coolify (`apply`, `diff`, `server add`, `smoke`, `team`). - Optionally let `environments.yaml` bind a default instance per environment (`environments.prod.instance: prod-cp`), so `--env prod` selects the right control plane with no flag and no file edit at all. - **Refuse, don't guess**, when `--instance` names an unknown instance — and name the instances that do exist, in the same spirit as the absent-target refusal from #12 (D-237). Nice-to-have on the same theme: let an instance declare its expected token scope (e.g. `read_only: true`), so an instance configured for inspection cannot be used by `apply` even if the token itself would permit the writes. That turns "I pointed the wrong token at the wrong box" from a live incident into an exit code. ## Acceptance - `cast diff <slug> --env prod --instance legacy` works with **no** edit to `.coolify.env`. - An unknown `--instance` refuses and lists the known instances. - With no `--instance` flag, behavior is unchanged from today.
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference: heavy-duty/cast#14
No description provided.