Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
161 changes: 161 additions & 0 deletions docs/app.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,9 @@ Manage apps, and app installations in your projects
* [`mw app create php-worker`](#mw-app-create-php-worker)
* [`mw app create python`](#mw-app-create-python)
* [`mw app create static`](#mw-app-create-static)
* [`mw app database link [INSTALLATION-ID]`](#mw-app-database-link-installation-id)
* [`mw app database replace [INSTALLATION-ID]`](#mw-app-database-replace-installation-id)
* [`mw app database unlink [INSTALLATION-ID]`](#mw-app-database-unlink-installation-id)
* [`mw app dependency list`](#mw-app-dependency-list)
* [`mw app dependency update [INSTALLATION-ID]`](#mw-app-dependency-update-installation-id)
* [`mw app dependency versions SYSTEMSOFTWARE`](#mw-app-dependency-versions-systemsoftware)
Expand Down Expand Up @@ -411,6 +414,164 @@ FLAG DESCRIPTIONS
```


## `mw app database link [INSTALLATION-ID]`

Link a database to an app installation.

```
USAGE
$ mw app database link [INSTALLATION-ID] --database-id <value> --purpose primary|cache|custom --admin-user-id <value>
[--token <value>] [-q]

ARGUMENTS
[INSTALLATION-ID] ID or short ID of an app installation; this argument is optional if a default app installation is
set in the context.

FLAGS
-q, --quiet suppress process output and only display a machine-readable summary
--admin-user-id=<value> (required) the ID of the database user to link as the administrative user.
--database-id=<value> (required) the ID or name of the database to link to the app installation.
--purpose=<option> (required) [default: primary] the purpose the database serves for the app installation.
<options: primary|cache|custom>

AUTHENTICATION FLAGS
--token=<value> API token to use for authentication (overrides environment and config file). NOTE: watch out that
tokens passed via this flag might be logged in your shell history.

DESCRIPTION
Link a database to an app installation.

Creates a linkage between an app installation and an existing database, so the app can use it for the given purpose.

EXAMPLES
Link a database as the primary database of an app

$ mw app database link a-XXXXXX --database-id my-database --admin-user-id dbu-XXXXXX

FLAG DESCRIPTIONS
-q, --quiet suppress process output and only display a machine-readable summary

This flag controls if you want to see the process output or only a summary. When using mw non-interactively (e.g. in
scripts), you can use this flag to easily get the IDs of created resources for further processing.

--admin-user-id=<value> the ID of the database user to link as the administrative user.

The ID of the database user that should be used as the administrative ('admin') user for the linked database.

--database-id=<value> the ID or name of the database to link to the app installation.

The ID (UUID) or name of an existing database that should be linked to the app installation. When a name is given,
it is resolved against the databases of the app installation's project.

--purpose=primary|cache|custom the purpose the database serves for the app installation.

Describes how the app installation uses the linked database. Must be one of 'primary', 'cache' or 'custom'.
```


## `mw app database replace [INSTALLATION-ID]`

Replace the database linked to an app installation.

```
USAGE
$ mw app database replace [INSTALLATION-ID] --new-database-id <value> --admin-user-id <value> [--token <value>] [-q]
[--purpose primary|cache|custom]

ARGUMENTS
[INSTALLATION-ID] ID or short ID of an app installation; this argument is optional if a default app installation is
set in the context.

FLAGS
-q, --quiet suppress process output and only display a machine-readable summary
--admin-user-id=<value> (required) the ID of the database user to link as the administrative user.
--new-database-id=<value> (required) the ID or name of the database to link instead.
--purpose=<option> the purpose of the linked database to act on.
<options: primary|cache|custom>

AUTHENTICATION FLAGS
--token=<value> API token to use for authentication (overrides environment and config file). NOTE: watch out that
tokens passed via this flag might be logged in your shell history.

DESCRIPTION
Replace the database linked to an app installation.

Replaces the database that is currently linked to an app installation with another one, keeping the same purpose. The
currently linked database is determined automatically.

EXAMPLES
Replace the linked database of an app installation

$ mw app database replace a-XXXXXX --new-database-id my-new-database --admin-user-id dbu-XXXXXX

FLAG DESCRIPTIONS
-q, --quiet suppress process output and only display a machine-readable summary

This flag controls if you want to see the process output or only a summary. When using mw non-interactively (e.g. in
scripts), you can use this flag to easily get the IDs of created resources for further processing.

--admin-user-id=<value> the ID of the database user to link as the administrative user.

The ID of the database user that should be used as the administrative ('admin') user for the linked database.

--new-database-id=<value> the ID or name of the database to link instead.

The ID (UUID) or name of the database that should replace the currently linked database. When a name is given, it is
resolved against the databases of the app installation's project.

--purpose=primary|cache|custom the purpose of the linked database to act on.

Selects which linked database to act on by its purpose ('primary', 'cache' or 'custom'). Only needed when the app
installation has more than one linked database.
```


## `mw app database unlink [INSTALLATION-ID]`

Unlink a database from an app installation.

```
USAGE
$ mw app database unlink [INSTALLATION-ID] [--token <value>] [-q] [-f] [--purpose primary|cache|custom]

ARGUMENTS
[INSTALLATION-ID] ID or short ID of an app installation; this argument is optional if a default app installation is
set in the context.

FLAGS
-f, --force do not ask for confirmation
-q, --quiet suppress process output and only display a machine-readable summary
--purpose=<option> the purpose of the linked database to act on.
<options: primary|cache|custom>

AUTHENTICATION FLAGS
--token=<value> API token to use for authentication (overrides environment and config file). NOTE: watch out that
tokens passed via this flag might be logged in your shell history.

DESCRIPTION
Unlink a database from an app installation.

Removes the linkage between an app installation and its database. The currently linked database is determined
automatically; the database itself is not deleted.

EXAMPLES
Unlink the database from an app installation

$ mw app database unlink a-XXXXXX

FLAG DESCRIPTIONS
-q, --quiet suppress process output and only display a machine-readable summary

This flag controls if you want to see the process output or only a summary. When using mw non-interactively (e.g. in
scripts), you can use this flag to easily get the IDs of created resources for further processing.

--purpose=primary|cache|custom the purpose of the linked database to act on.

Selects which linked database to act on by its purpose ('primary', 'cache' or 'custom'). Only needed when the app
installation has more than one linked database.
```


## `mw app dependency list`

Get all available dependencies
Expand Down
95 changes: 95 additions & 0 deletions src/commands/app/database/link.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
import { ExecRenderBaseCommand } from "../../../lib/basecommands/ExecRenderBaseCommand.js";
import { Flags } from "@oclif/core";
import { ReactNode } from "react";
import {
makeProcessRenderer,
processFlags,
} from "../../../rendering/process/process_flags.js";
import { Success } from "../../../rendering/react/components/Success.js";
import assertSuccess from "../../../lib/apiutil/assert_success.js";
import { appInstallationArgs } from "../../../lib/resources/app/flags.js";
import { getAppInstallationFromUuid } from "../../../lib/resources/app/uuid.js";
import {
adminUserIdFlag,
databasePurposeFlag,
} from "../../../lib/resources/app/database/flags.js";
import { resolveDatabaseId } from "../../../lib/resources/app/database/lookup.js";

export default class Link extends ExecRenderBaseCommand<typeof Link, void> {
static summary = "Link a database to an app installation.";
static description =
"Creates a linkage between an app installation and an existing database, so the app can use it for the given purpose.";

static examples = [
{
description: "Link a database as the primary database of an app",
command:
"<%= config.bin %> <%= command.id %> a-XXXXXX --database-id my-database --admin-user-id dbu-XXXXXX",
},
];

static args = {
...appInstallationArgs,
};

static flags = {
...processFlags,
"database-id": Flags.string({
summary:
"the ID or name of the database to link to the app installation.",
description:
"The ID (UUID) or name of an existing database that should be linked to the app installation. When a name is given, it is resolved against the databases of the app installation's project.",
required: true,
}),
purpose: databasePurposeFlag,
"admin-user-id": adminUserIdFlag,
};

protected async exec(): Promise<void> {
const process = makeProcessRenderer(
this.flags,
"Linking database to app installation",
);

const appInstallationId = await this.withAppInstallationId(Link);
const {
"database-id": databaseIdentifier,
purpose,
"admin-user-id": adminUserId,
} = this.flags;

const databaseId = await process.runStep("resolving database", async () => {
const appInstallation = await getAppInstallationFromUuid(
this.apiClient,
appInstallationId,
);
return resolveDatabaseId(
this.apiClient,
appInstallation.projectId,
databaseIdentifier,
);
});

await process.runStep("linking database", async () => {
const response = await this.apiClient.app.linkDatabase({
appInstallationId,
data: {
databaseId,
purpose: purpose as "primary" | "cache" | "custom",
databaseUserIds: {
admin: adminUserId,
},
},
});
assertSuccess(response);
});

await process.complete(
<Success>The database was successfully linked to the app.</Success>,
);
}

protected render(): ReactNode {
return null;
}
}
111 changes: 111 additions & 0 deletions src/commands/app/database/replace.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,111 @@
import { ExecRenderBaseCommand } from "../../../lib/basecommands/ExecRenderBaseCommand.js";
import { Flags } from "@oclif/core";
import { ReactNode } from "react";
import {
makeProcessRenderer,
processFlags,
} from "../../../rendering/process/process_flags.js";
import { Success } from "../../../rendering/react/components/Success.js";
import assertSuccess from "../../../lib/apiutil/assert_success.js";
import { appInstallationArgs } from "../../../lib/resources/app/flags.js";
import { getAppInstallationFromUuid } from "../../../lib/resources/app/uuid.js";
import {
adminUserIdFlag,
databasePurposeSelectorFlag,
} from "../../../lib/resources/app/database/flags.js";
import {
resolveDatabaseId,
selectLinkedDatabase,
} from "../../../lib/resources/app/database/lookup.js";

export default class Replace extends ExecRenderBaseCommand<
typeof Replace,
void
> {
static summary = "Replace the database linked to an app installation.";
static description =
"Replaces the database that is currently linked to an app installation with another one, keeping the same purpose. The currently linked database is determined automatically.";

static examples = [
{
description: "Replace the linked database of an app installation",
command:
"<%= config.bin %> <%= command.id %> a-XXXXXX --new-database-id my-new-database --admin-user-id dbu-XXXXXX",
},
];

static args = {
...appInstallationArgs,
};

static flags = {
...processFlags,
purpose: databasePurposeSelectorFlag,
"new-database-id": Flags.string({
summary: "the ID or name of the database to link instead.",
description:
"The ID (UUID) or name of the database that should replace the currently linked database. When a name is given, it is resolved against the databases of the app installation's project.",
required: true,
}),
"admin-user-id": adminUserIdFlag,
};

protected async exec(): Promise<void> {
const process = makeProcessRenderer(
this.flags,
"Replacing linked database of app installation",
);

const appInstallationId = await this.withAppInstallationId(Replace);
const {
"new-database-id": newDatabaseIdentifier,
"admin-user-id": adminUserId,
purpose,
} = this.flags;

const { oldDatabaseId, newDatabaseId } = await process.runStep(
"resolving databases",
async () => {
const appInstallation = await getAppInstallationFromUuid(
this.apiClient,
appInstallationId,
);
const linkedDatabase = selectLinkedDatabase(
appInstallation.linkedDatabases,
purpose,
);
const resolvedNewDatabaseId = await resolveDatabaseId(
this.apiClient,
appInstallation.projectId,
newDatabaseIdentifier,
);
return {
oldDatabaseId: linkedDatabase.databaseId,
newDatabaseId: resolvedNewDatabaseId,
};
},
);

await process.runStep("replacing database", async () => {
const response = await this.apiClient.app.replaceDatabase({
appInstallationId,
data: {
oldDatabaseId,
newDatabaseId,
databaseUserIds: {
admin: adminUserId,
},
},
});
assertSuccess(response);
});

await process.complete(
<Success>The linked database was successfully replaced.</Success>,
);
}

protected render(): ReactNode {
return null;
}
}
Loading
Loading