# swb release-hold

Releases the hold on an installed app, which follows its subscription's
channel again.

## Synopsis

```
usage: swb release-hold <app> --env <env> [--json]
```

## Arguments and flags

| Argument or flag | Takes | Default |
|---|---|---|
| `<app>` | The app's **id** — the app whose install is released. Required. | — |
| `--env` | An environment's **name or id**; a name is matched first. Required. | — |
| `--json` | Nothing. Prints the subscription as the API answered it instead of the one-line summary. | off |
| `--help`, `-h` | Prints the command's help and exits. | off |

## What it does

Calls `Mutation.releaseHold` for the app's install in that environment. The
hold is removed from the install's subscription, which keeps its channel and
policy. A release takes no client token: releasing an install that holds
nothing changes nothing and prints the subscription as it stands.

A release shows in the app's [history](/command-line/history) as a
`hold-released` entry, and returns the install to its channel: within a
minute it has a deploy of the channel's head, started by `CHANNEL` and
requested by you, as its subscription's policy and gate say, replacing the
held version's deploy if nobody ran it. No deploy is written where the
install already has that version standing or running, or where the channel
has no head yet, as a production environment's `stable` has none before its
first approved release.

## What it prints

```
crew-signout in prod: not held, following stable
```

— the app, the environment, and the channel the subscription follows.

`--json` prints the subscription as the API answered it: `installId`,
`appId`, `environmentId`, `channel`, `policy`, `held`, `heldBy` and `heldAt`.

## The operation and the permission

`Mutation.releaseHold`. The caller needs `swb.deploys.run` on the tenant.
`swb release-hold` also reads `Query.me` once for the tenant and
`Query.tenant` to turn the `--env` name into an id.

## Refusals and exit status

Exit status is 0 once the install is released, or found holding nothing, and
1 on every refusal below.

| Refusal | When |
|---|---|
| `swb release-hold takes <app>` | The app is missing. |
| `swb release-hold needs --env <env>` | `--env` was not given. |
| `no environment named "<env>" in tenant <tenant> (have: dev, staging, prod)` | No environment of the tenant has that name or id. |
| `not signed in or token expired — run swb login` | There is no usable credential. |
| `NotFound: Install <app>#<env> not found` | The tenant has not installed the app in that environment. |
| `NotFound: ChannelSubscription <app>#<env> not found` | The install has never had a subscription: it was never held. |
| `NotAuthorized: …` | The caller lacks `swb.deploys.run`. |
| `Conflict: …` | Another hold or release of the install landed first; the refusal names the hold that stands. |

## Example

```console
$ swb release-hold crew-signout --env prod
crew-signout in prod: not held, following stable
```
