@microagi/alchemy-gcp 0.3.0 → 0.5.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (91) hide show
  1. package/CHANGELOG.md +124 -0
  2. package/lib/ArtifactRegistry/Operations.d.ts +47 -0
  3. package/lib/ArtifactRegistry/Operations.d.ts.map +1 -0
  4. package/lib/ArtifactRegistry/Operations.js +47 -0
  5. package/lib/ArtifactRegistry/Operations.js.map +1 -0
  6. package/lib/ArtifactRegistry/Repository.d.ts +263 -0
  7. package/lib/ArtifactRegistry/Repository.d.ts.map +1 -0
  8. package/lib/ArtifactRegistry/Repository.js +256 -0
  9. package/lib/ArtifactRegistry/Repository.js.map +1 -0
  10. package/lib/ArtifactRegistry/Types.d.ts +32 -0
  11. package/lib/ArtifactRegistry/Types.d.ts.map +1 -0
  12. package/lib/ArtifactRegistry/Types.js +12 -0
  13. package/lib/ArtifactRegistry/Types.js.map +1 -0
  14. package/lib/ArtifactRegistry/Validation.d.ts +43 -0
  15. package/lib/ArtifactRegistry/Validation.d.ts.map +1 -0
  16. package/lib/ArtifactRegistry/Validation.js +95 -0
  17. package/lib/ArtifactRegistry/Validation.js.map +1 -0
  18. package/lib/ArtifactRegistry/index.d.ts +4 -0
  19. package/lib/ArtifactRegistry/index.d.ts.map +1 -0
  20. package/lib/ArtifactRegistry/index.js +2 -0
  21. package/lib/ArtifactRegistry/index.js.map +1 -0
  22. package/lib/Auth/Credentials.d.ts +2 -1
  23. package/lib/Auth/Credentials.d.ts.map +1 -1
  24. package/lib/Auth/Credentials.js +3 -2
  25. package/lib/Auth/Credentials.js.map +1 -1
  26. package/lib/CloudResourceManager/Project.d.ts +1 -1
  27. package/lib/Compute/GlobalAddress.d.ts +1 -1
  28. package/lib/Compute/Network.d.ts +1 -1
  29. package/lib/Compute/SharedVpcHost.d.ts +1 -1
  30. package/lib/Compute/SharedVpcServiceProject.d.ts +1 -1
  31. package/lib/Compute/Subnetwork.d.ts +1 -1
  32. package/lib/Container/Cluster.d.ts +1 -1
  33. package/lib/Container/NodePool.d.ts +1 -1
  34. package/lib/ManagedLustre/Instance.d.ts +1 -1
  35. package/lib/Providers.d.ts +1 -1
  36. package/lib/Providers.d.ts.map +1 -1
  37. package/lib/Providers.js +9 -1
  38. package/lib/Providers.js.map +1 -1
  39. package/lib/Run/Job.d.ts +1 -1
  40. package/lib/Run/Service.d.ts +1 -1
  41. package/lib/ServiceNetworking/PsaConnection.d.ts +1 -1
  42. package/lib/ServiceUsage/ApiEnable.d.ts +1 -1
  43. package/lib/Sqladmin/Database.d.ts +82 -0
  44. package/lib/Sqladmin/Database.d.ts.map +1 -0
  45. package/lib/Sqladmin/Database.js +87 -0
  46. package/lib/Sqladmin/Database.js.map +1 -0
  47. package/lib/Sqladmin/Instance.d.ts +234 -0
  48. package/lib/Sqladmin/Instance.d.ts.map +1 -0
  49. package/lib/Sqladmin/Instance.js +251 -0
  50. package/lib/Sqladmin/Instance.js.map +1 -0
  51. package/lib/Sqladmin/Operations.d.ts +41 -0
  52. package/lib/Sqladmin/Operations.d.ts.map +1 -0
  53. package/lib/Sqladmin/Operations.js +42 -0
  54. package/lib/Sqladmin/Operations.js.map +1 -0
  55. package/lib/Sqladmin/Types.d.ts +82 -0
  56. package/lib/Sqladmin/Types.d.ts.map +1 -0
  57. package/lib/Sqladmin/Types.js +28 -0
  58. package/lib/Sqladmin/Types.js.map +1 -0
  59. package/lib/Sqladmin/User.d.ts +110 -0
  60. package/lib/Sqladmin/User.d.ts.map +1 -0
  61. package/lib/Sqladmin/User.js +156 -0
  62. package/lib/Sqladmin/User.js.map +1 -0
  63. package/lib/Sqladmin/Validation.d.ts +60 -0
  64. package/lib/Sqladmin/Validation.d.ts.map +1 -0
  65. package/lib/Sqladmin/Validation.js +125 -0
  66. package/lib/Sqladmin/Validation.js.map +1 -0
  67. package/lib/Sqladmin/index.d.ts +9 -0
  68. package/lib/Sqladmin/index.d.ts.map +1 -0
  69. package/lib/Sqladmin/index.js +5 -0
  70. package/lib/Sqladmin/index.js.map +1 -0
  71. package/lib/Tags.d.ts +4 -4
  72. package/lib/index.d.ts +2 -0
  73. package/lib/index.d.ts.map +1 -1
  74. package/lib/index.js +2 -0
  75. package/lib/index.js.map +1 -1
  76. package/package.json +2 -2
  77. package/src/ArtifactRegistry/Operations.ts +79 -0
  78. package/src/ArtifactRegistry/Repository.ts +628 -0
  79. package/src/ArtifactRegistry/Types.ts +49 -0
  80. package/src/ArtifactRegistry/Validation.ts +112 -0
  81. package/src/ArtifactRegistry/index.ts +10 -0
  82. package/src/Auth/Credentials.ts +3 -2
  83. package/src/Providers.ts +15 -0
  84. package/src/Sqladmin/Database.ts +209 -0
  85. package/src/Sqladmin/Instance.ts +620 -0
  86. package/src/Sqladmin/Operations.ts +73 -0
  87. package/src/Sqladmin/Types.ts +101 -0
  88. package/src/Sqladmin/User.ts +333 -0
  89. package/src/Sqladmin/Validation.ts +148 -0
  90. package/src/Sqladmin/index.ts +19 -0
  91. package/src/index.ts +2 -0
package/CHANGELOG.md CHANGED
@@ -4,6 +4,130 @@ All notable changes to `@microagi/alchemy-gcp`. The format follows
4
4
  [Keep a Changelog](https://keepachangelog.com/en/1.1.0/); this package
5
5
  adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
6
6
 
7
+ ## 0.5.1 — 2026-06-08
8
+
9
+ ### Fixed
10
+
11
+ - **`Auth/Credentials.fromAuthProvider`** — adapt to upstream alchemy's
12
+ `Profile` service refactor. `loadOrConfigure` is no longer a top-level
13
+ export of `alchemy/Auth/Profile`; it's a method on the `Profile`
14
+ `Context.Service`. The Layer now yields `Profile` and calls
15
+ `profile.loadOrConfigure(...)`, mirroring the
16
+ `Cloudflare/Credentials.ts` shape in alchemy upstream. Required for
17
+ any alchemy version newer than the one this package was originally
18
+ built against — without this fix, a downstream stack that imports
19
+ `@microagi/alchemy-gcp` against current alchemy fails to load with
20
+ `SyntaxError: Export named 'loadOrConfigure' not found`.
21
+
22
+ - **`GCP.ArtifactRegistryRepository` diff** — `somePropsAreDifferent`
23
+ uses `!==` reference equality, which is always `true` for the
24
+ `remoteRepositoryConfig` object after JSON round-trip through the
25
+ state store. A plan against an unchanged stack would show
26
+ `replace` (destroy + recreate), which on a remote repository
27
+ destroys the pull-through cache. The diff now uses `deepEqual` for
28
+ `remoteRepositoryConfig` and keeps `somePropsAreDifferent` only for
29
+ string-typed stables.
30
+
31
+ ## 0.5.0 — 2026-06-07
32
+
33
+ Artifact Registry (artifactregistry v1) — Docker repositories, both
34
+ standard (self-hosted builds) and remote (pull-through caches for
35
+ Docker Hub and arbitrary upstreams like `nvcr.io`).
36
+
37
+ ### Added
38
+
39
+ - **`GCP.ArtifactRegistryRepository`** — Artifact Registry repository
40
+ resource for `format: "DOCKER"`. Supports:
41
+ - `mode: "STANDARD_REPOSITORY"` — repository hosts images uploaded
42
+ by the project (CI builds, etc.).
43
+ - `mode: "REMOTE_REPOSITORY"` — pull-through cache. The upstream is
44
+ either a Google-known preset (`{ publicRepository: "DOCKER_HUB" }`)
45
+ or an arbitrary HTTPS Docker registry
46
+ (`{ customRepository: { uri: "https://nvcr.io" } }`). Optional
47
+ `upstreamCredentials` for authenticated upstreams (Secret
48
+ Manager-backed password).
49
+ - Mutable-via-patch fields: `description`, `labels`, `dockerConfig`
50
+ (`immutableTags`), `cleanupPolicies`, `cleanupPolicyDryRun` —
51
+ diff'd against observed cloud state and patched with a precise
52
+ `updateMask`.
53
+ - Replace triggers: `project`, `location`, `name`, `format`, `mode`,
54
+ `kmsKeyName`, and any change to `remoteRepositoryConfig` (GCP
55
+ refuses in-place updates here).
56
+ - Standard adoption gate via `alchemy_*` labels — pre-existing
57
+ repositories without our labels surface as `Unowned` and require
58
+ `--adopt` to take over.
59
+ - Same API-enable propagation retry (15s × 20 ≈ 5 min) as
60
+ `Cluster` / `Service` / `SqlInstance` for the race between
61
+ `ApiEnable` and the first create.
62
+ - **Plan-time validation** — repo-name regex
63
+ (`/^[a-z0-9][a-z0-9-]{0,62}$/`), and the
64
+ `mode` ↔ `remoteRepositoryConfig` invariant (REMOTE requires a
65
+ docker upstream; STANDARD forbids a remote config). Fails fast with
66
+ typed `ConfigError` before any state mutation.
67
+ - **Branded literal types** — `ArtifactRegistryFormat` (DOCKER,
68
+ MAVEN, …) and `ArtifactRegistryMode`
69
+ (STANDARD/REMOTE/VIRTUAL_REPOSITORY) with `(string & {})` tails for
70
+ forward-compat with new server-side values.
71
+
72
+ ### LRO
73
+
74
+ - `ArtifactRegistry/Operations.ts` — Cloud Run-style poller. AR
75
+ operations use the standard `GoogleLongrunningOperation` shape
76
+ (`.done: boolean`), distinct from Sqladmin's tri-state `.status`.
77
+ Operation names are fully-qualified
78
+ (`projects/{p}/locations/{l}/operations/{id}`).
79
+
80
+ ## 0.4.0 — 2026-06-07
81
+
82
+ Cloud SQL (sqladmin v1) — Postgres instance + database + user, with
83
+ first-class IAM database authentication.
84
+
85
+ ### Added
86
+
87
+ - **`GCP.SqlInstance`** — Cloud SQL for Postgres instance. Tier,
88
+ edition, disk auto-resize, IP configuration (public IPv4 + private
89
+ IP via PSA), backups + PITR, database flags, deletion protection,
90
+ zonal/regional HA. Optimistic concurrency via the live
91
+ `settings.settingsVersion` round-trip (Cloud SQL's `etag` field is
92
+ deprecated). API-enable-propagation 403 retry mirroring the
93
+ `Cluster` / `Service` providers.
94
+ - **`GCP.SqlDatabase`** — logical Postgres database. Thin resource —
95
+ name, charset, collation. No labels on the GCP side so adoption is
96
+ best-effort (no `Unowned` wrapper).
97
+ - **`GCP.SqlUser`** — Postgres role with three auth modes:
98
+ - `BUILT_IN` — username + `Redacted` password.
99
+ - `CLOUD_IAM_USER` — human IAM principal authenticated via the
100
+ Cloud SQL Auth Proxy / IAM token exchange.
101
+ - `CLOUD_IAM_SERVICE_ACCOUNT` — GCP service-account principal
102
+ (name = SA email minus the `.gserviceaccount.com` tail).
103
+ Plan-time validation rejects passwords on IAM users and missing
104
+ passwords on `BUILT_IN`. Forward-compat `(string & {})` tail keeps
105
+ newer IAM variants (`CLOUD_IAM_GROUP*`, `ENTRAID_USER`) reachable.
106
+ - **Branded literal types** from `Sqladmin/Types.ts` —
107
+ `PostgresVersion` (15/16/17 only — narrower than distilled's
108
+ open-tailed enum so typos are caught at compile time), `SqlEdition`,
109
+ `SqlDataDiskType`, `SqlAvailabilityType`, `SqlActivationPolicy`,
110
+ `SqlUserType`.
111
+ - **Plan-time validation** — instance name regex (1–98 chars,
112
+ RFC 1123 label subset), database name length, user password/type
113
+ consistency. Fails fast with a typed `ConfigError` before any state
114
+ mutation.
115
+ - **`BadRequest` passthroughs** on `Instance`/`Database`/`User`
116
+ create/patch/delete — billing-not-enabled, missing PSA peering,
117
+ and invalid tier get remediation hints; anything else propagates
118
+ verbatim.
119
+
120
+ ### Notes
121
+
122
+ - Sqladmin operations use `status: "DONE"` (distinct from the
123
+ `done: boolean` shape Cloud Resource Manager / Cloud Run / Lustre
124
+ use). `Sqladmin/Operations.ts` polls `getOperations({ project,
125
+ operation })` accordingly.
126
+ - `SqlInstance` adoption is label-gated through
127
+ `settings.userLabels`. `SqlDatabase` and `SqlUser` cannot carry
128
+ labels, so they trust the logical id / parent address alone — be
129
+ cautious with `--adopt` on those.
130
+
7
131
  ## 0.3.0 — 2026-05-11
8
132
 
9
133
  Cloud Run v2 — production polish on the Service + Job + IAM surface.
@@ -0,0 +1,47 @@
1
+ import { ConfigError } from "@distilled.cloud/gcp";
2
+ import * as ar from "@distilled.cloud/gcp/artifactregistry-v1";
3
+ import type { ScopedPlanStatusSession } from "alchemy/Cli/Cli";
4
+ import * as Effect from "effect/Effect";
5
+ /**
6
+ * Resolved callable signature of `ar.getProjectsLocationsOperations`.
7
+ *
8
+ * `ar.getProjectsLocationsOperations` is itself an
9
+ * `Effect<callable, never, Credentials | HttpClient>`, so
10
+ * `Effect.Success` extracts the callable type. Using a derived alias
11
+ * keeps the helper aligned with the SDK without us hand-writing the
12
+ * input/output/error union, which would drift if the patch set changes.
13
+ */
14
+ type GetOperations = Effect.Success<typeof ar.getProjectsLocationsOperations>;
15
+ /**
16
+ * Build the Artifact Registry long-running-operation polling helper.
17
+ *
18
+ * Artifact Registry `Operation`s use the standard
19
+ * `GoogleLongrunningOperation` shape — doneness is `.done === true`
20
+ * (NOT `.status === "DONE"` like the GKE Container API and NOT
21
+ * Sqladmin's tri-state `.status`). Verified at
22
+ * `vendor/distilled/packages/gcp/src/services/artifactregistry-v1.ts:308–328`.
23
+ *
24
+ * Operation names returned by `artifactregistry-v1`
25
+ * (`createProjectsLocationsRepositories`,
26
+ * `patchProjectsLocationsRepositories`,
27
+ * `deleteProjectsLocationsRepositories`) are already fully qualified
28
+ * (`projects/{p}/locations/{l}/operations/{id}`), so callers pass them
29
+ * straight through to `getProjectsLocationsOperations` — no qualify
30
+ * dance needed (unlike Container, which returns bare ids).
31
+ *
32
+ * Schedule: exponential 1s → 1.5× growth, capped per-poll at 10s via
33
+ * `Schedule.either`, then a hard count cap of 60 retries → ~10 min wall
34
+ * ceiling. Repository CRUD is fast (seconds); the only long-running
35
+ * case is a delete on a repository with many cached images, where AR
36
+ * has to GC the underlying blobs.
37
+ *
38
+ * The helper is a factory — the caller resolves
39
+ * `ar.getProjectsLocationsOperations` once at provider construction
40
+ * and passes the resulting callable here, so we never re-resolve
41
+ * services on each await.
42
+ */
43
+ export declare const makeAwaitOperation: (getOperations: GetOperations) => (operationName: string, session: ScopedPlanStatusSession) => Effect.Effect<ar.Operation, ar.GetProjectsLocationsOperationsError | ConfigError | {
44
+ _tag: "OperationPending";
45
+ }, never>;
46
+ export {};
47
+ //# sourceMappingURL=Operations.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Operations.d.ts","sourceRoot":"","sources":["../../src/ArtifactRegistry/Operations.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,sBAAsB,CAAC;AACnD,OAAO,KAAK,EAAE,MAAM,0CAA0C,CAAC;AAC/D,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,iBAAiB,CAAC;AAE/D,OAAO,KAAK,MAAM,MAAM,eAAe,CAAC;AAGxC;;;;;;;;GAQG;AACH,KAAK,aAAa,GAAG,MAAM,CAAC,OAAO,CAAC,OAAO,EAAE,CAAC,8BAA8B,CAAC,CAAC;AAE9E;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,eAAO,MAAM,kBAAkB,GAAI,eAAe,aAAa;;SAgC3D,CAAC"}
@@ -0,0 +1,47 @@
1
+ import { ConfigError } from "@distilled.cloud/gcp";
2
+ import * as Duration from "effect/Duration";
3
+ import * as Effect from "effect/Effect";
4
+ import * as Schedule from "effect/Schedule";
5
+ /**
6
+ * Build the Artifact Registry long-running-operation polling helper.
7
+ *
8
+ * Artifact Registry `Operation`s use the standard
9
+ * `GoogleLongrunningOperation` shape — doneness is `.done === true`
10
+ * (NOT `.status === "DONE"` like the GKE Container API and NOT
11
+ * Sqladmin's tri-state `.status`). Verified at
12
+ * `vendor/distilled/packages/gcp/src/services/artifactregistry-v1.ts:308–328`.
13
+ *
14
+ * Operation names returned by `artifactregistry-v1`
15
+ * (`createProjectsLocationsRepositories`,
16
+ * `patchProjectsLocationsRepositories`,
17
+ * `deleteProjectsLocationsRepositories`) are already fully qualified
18
+ * (`projects/{p}/locations/{l}/operations/{id}`), so callers pass them
19
+ * straight through to `getProjectsLocationsOperations` — no qualify
20
+ * dance needed (unlike Container, which returns bare ids).
21
+ *
22
+ * Schedule: exponential 1s → 1.5× growth, capped per-poll at 10s via
23
+ * `Schedule.either`, then a hard count cap of 60 retries → ~10 min wall
24
+ * ceiling. Repository CRUD is fast (seconds); the only long-running
25
+ * case is a delete on a repository with many cached images, where AR
26
+ * has to GC the underlying blobs.
27
+ *
28
+ * The helper is a factory — the caller resolves
29
+ * `ar.getProjectsLocationsOperations` once at provider construction
30
+ * and passes the resulting callable here, so we never re-resolve
31
+ * services on each await.
32
+ */
33
+ export const makeAwaitOperation = (getOperations) => Effect.fn(function* (operationName, session) {
34
+ const op = yield* getOperations({ name: operationName }).pipe(Effect.flatMap((current) => current.done === true
35
+ ? Effect.succeed(current)
36
+ : Effect.fail({ _tag: "OperationPending" })), Effect.retry({
37
+ while: (e) => e?._tag === "OperationPending",
38
+ schedule: Schedule.exponential(Duration.seconds(1), 1.5).pipe(Schedule.either(Schedule.spaced(Duration.seconds(10))), Schedule.both(Schedule.recurs(60)), Schedule.tapOutput(() => session.note(`Waiting for Artifact Registry operation ${operationName}…`))),
39
+ }));
40
+ if (op.error) {
41
+ return yield* new ConfigError({
42
+ message: `Artifact Registry operation ${operationName} failed: ${op.error.message ?? JSON.stringify(op.error)}`,
43
+ });
44
+ }
45
+ return op;
46
+ });
47
+ //# sourceMappingURL=Operations.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Operations.js","sourceRoot":"","sources":["../../src/ArtifactRegistry/Operations.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,sBAAsB,CAAC;AAGnD,OAAO,KAAK,QAAQ,MAAM,iBAAiB,CAAC;AAC5C,OAAO,KAAK,MAAM,MAAM,eAAe,CAAC;AACxC,OAAO,KAAK,QAAQ,MAAM,iBAAiB,CAAC;AAa5C;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAAG,CAAC,aAA4B,EAAE,EAAE,CACjE,MAAM,CAAC,EAAE,CAAC,QAAQ,CAAC,EACjB,aAAqB,EACrB,OAAgC;IAEhC,MAAM,EAAE,GAAG,KAAK,CAAC,CAAC,aAAa,CAAC,EAAE,IAAI,EAAE,aAAa,EAAE,CAAC,CAAC,IAAI,CAC3D,MAAM,CAAC,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE,CACzB,OAAO,CAAC,IAAI,KAAK,IAAI;QACnB,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,OAAO,CAAC;QACzB,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,kBAA2B,EAAE,CAAC,CACvD,EACD,MAAM,CAAC,KAAK,CAAC;QACX,KAAK,EAAE,CAAC,CAAoB,EAAE,EAAE,CAAC,CAAC,EAAE,IAAI,KAAK,kBAAkB;QAC/D,QAAQ,EAAE,QAAQ,CAAC,WAAW,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC,IAAI,CAC3D,QAAQ,CAAC,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC,CAAC,EACtD,QAAQ,CAAC,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC,EAClC,QAAQ,CAAC,SAAS,CAAC,GAAG,EAAE,CACtB,OAAO,CAAC,IAAI,CACV,2CAA2C,aAAa,GAAG,CAC5D,CACF,CACF;KACF,CAAC,CACH,CAAC;IACF,IAAI,EAAE,CAAC,KAAK,EAAE,CAAC;QACb,OAAO,KAAK,CAAC,CAAC,IAAI,WAAW,CAAC;YAC5B,OAAO,EAAE,+BAA+B,aAAa,YACnD,EAAE,CAAC,KAAK,CAAC,OAAO,IAAI,IAAI,CAAC,SAAS,CAAC,EAAE,CAAC,KAAK,CAC7C,EAAE;SACH,CAAC,CAAC;IACL,CAAC;IACD,OAAO,EAAE,CAAC;AACZ,CAAC,CAAC,CAAC"}
@@ -0,0 +1,263 @@
1
+ import * as ar from "@distilled.cloud/gcp/artifactregistry-v1";
2
+ import { Resource } from "alchemy";
3
+ import * as Provider from "alchemy/Provider";
4
+ import type * as GCP from "../Providers.ts";
5
+ import type { ArtifactRegistryFormat, ArtifactRegistryMode } from "./Types.ts";
6
+ /**
7
+ * Docker remote upstream — either a Google-known public repository
8
+ * (today: Docker Hub) or an arbitrary HTTPS Docker registry like
9
+ * `https://nvcr.io` or `https://quay.io`. Discriminated union — the
10
+ * server rejects bodies that supply both. Matches
11
+ * `ar.DockerRepository`.
12
+ *
13
+ * @see https://cloud.google.com/artifact-registry/docs/reference/rest/v1/projects.locations.repositories#DockerRepository
14
+ */
15
+ export type ArtifactRegistryDockerUpstream = {
16
+ /**
17
+ * One of Artifact Registry's built-in public-repository
18
+ * presets. Today only `DOCKER_HUB` is meaningful for the docker
19
+ * format. The string-tail is left open for forward compat with
20
+ * any future presets the server adds.
21
+ */
22
+ publicRepository: "DOCKER_HUB" | (string & {});
23
+ customRepository?: never;
24
+ } | {
25
+ /**
26
+ * Arbitrary HTTPS Docker upstream — `https://nvcr.io`,
27
+ * `https://quay.io`, a self-hosted Harbor, etc. The server
28
+ * trims any path / pulls the manifest endpoint conventionally.
29
+ */
30
+ customRepository: {
31
+ uri: string;
32
+ };
33
+ publicRepository?: never;
34
+ };
35
+ /**
36
+ * A Google Artifact Registry **Repository** of `format: "DOCKER"` —
37
+ * either a standard upload-target (`STANDARD_REPOSITORY`) for the
38
+ * project's own container builds, or a pull-through cache
39
+ * (`REMOTE_REPOSITORY`) pointing at Docker Hub or a custom upstream
40
+ * like `nvcr.io`.
41
+ *
42
+ * **Resource model.** A repository lives at
43
+ * `projects/{project}/locations/{location}/repositories/{name}`.
44
+ * Format and mode are immutable; the upstream config for a remote
45
+ * repository is also immutable on the GCP side (any change triggers a
46
+ * replace).
47
+ *
48
+ * **Lifecycle.** observe → ensure (create LRO; retry on the
49
+ * "API not yet enabled" 403 propagation race) → sync (patch
50
+ * description, labels, dockerConfig, cleanup policies via
51
+ * `updateMask`) → return. Mirrors `Sqladmin/Instance.ts` /
52
+ * `Run/Service.ts`.
53
+ *
54
+ * **Replace triggers.** `project`, `location`, `name`, `format`,
55
+ * `mode`, `kmsKeyName`, and any change inside `remoteRepositoryConfig`.
56
+ *
57
+ * **Adoption.** Label-gated via `alchemy_*` labels. A repository
58
+ * whose `labels` lack our keys is wrapped in `Unowned(attrs)` from
59
+ * `read`, forcing `--adopt` before takeover.
60
+ *
61
+ * @example Standard Docker repo for the project's own builds
62
+ * ```typescript
63
+ * const apps = yield* GCP.ArtifactRegistryRepository("Apps", {
64
+ * project: project.projectId,
65
+ * location: "europe-west4",
66
+ * format: "DOCKER",
67
+ * description: "App images built by CI",
68
+ * });
69
+ * ```
70
+ *
71
+ * @example Pull-through cache for Docker Hub
72
+ * ```typescript
73
+ * yield* GCP.ArtifactRegistryRepository("DockerHubMirror", {
74
+ * project: project.projectId,
75
+ * location: "europe-west4",
76
+ * format: "DOCKER",
77
+ * mode: "REMOTE_REPOSITORY",
78
+ * remoteRepositoryConfig: {
79
+ * description: "Pull-through cache for docker.io",
80
+ * dockerRepository: { publicRepository: "DOCKER_HUB" },
81
+ * },
82
+ * });
83
+ * ```
84
+ *
85
+ * @example Pull-through cache for nvcr.io
86
+ * ```typescript
87
+ * yield* GCP.ArtifactRegistryRepository("NvcrMirror", {
88
+ * project: project.projectId,
89
+ * location: "europe-west4",
90
+ * format: "DOCKER",
91
+ * mode: "REMOTE_REPOSITORY",
92
+ * remoteRepositoryConfig: {
93
+ * description: "Pull-through cache for nvcr.io",
94
+ * dockerRepository: { customRepository: { uri: "https://nvcr.io" } },
95
+ * },
96
+ * });
97
+ * ```
98
+ *
99
+ * @see https://cloud.google.com/artifact-registry/docs/reference/rest/v1/projects.locations.repositories#Repository
100
+ */
101
+ export type ArtifactRegistryRepositoryProps = {
102
+ /**
103
+ * GCP project ID hosting the repository. Immutable — replace if
104
+ * changed.
105
+ * @see https://cloud.google.com/artifact-registry/docs/reference/rest/v1/projects.locations.repositories#Repository
106
+ */
107
+ project: string;
108
+ /**
109
+ * Artifact Registry location (e.g. `europe-west4`). Regional only —
110
+ * multi-region is not supported by this resource. Immutable.
111
+ * @see https://cloud.google.com/artifact-registry/docs/repositories/repo-locations
112
+ */
113
+ location: string;
114
+ /**
115
+ * Repository short name (the trailing path segment under
116
+ * `…/repositories/`). Defaults to a sanitised
117
+ * `createPhysicalName({ id, lowercase: true, maxLength: 63 })`.
118
+ * Lowercase letters/digits/hyphens; start with a letter or digit;
119
+ * 1–63 chars. Immutable — replace if changed.
120
+ * @see https://cloud.google.com/artifact-registry/docs/repositories/create-repos#create
121
+ */
122
+ name?: string;
123
+ /**
124
+ * Package format. Today the provider exercises only `DOCKER`; other
125
+ * formats are reachable via the open-tail union but un-tested.
126
+ * Immutable — replace if changed.
127
+ * @see https://cloud.google.com/artifact-registry/docs/reference/rest/v1/projects.locations.repositories#Format
128
+ */
129
+ format: ArtifactRegistryFormat;
130
+ /**
131
+ * Repository mode. Defaults to `STANDARD_REPOSITORY`. Set to
132
+ * `REMOTE_REPOSITORY` to act as a pull-through cache for an upstream
133
+ * Docker registry; in that case `remoteRepositoryConfig` is
134
+ * required. Immutable — replace if changed (GCP does not allow
135
+ * flipping a repository between modes).
136
+ * @see https://cloud.google.com/artifact-registry/docs/reference/rest/v1/projects.locations.repositories#Mode
137
+ */
138
+ mode?: ArtifactRegistryMode;
139
+ /**
140
+ * Human-readable description. Mutable via `patch` with
141
+ * `updateMask=description`.
142
+ * @see https://cloud.google.com/artifact-registry/docs/reference/rest/v1/projects.locations.repositories#Repository.FIELDS.description
143
+ */
144
+ description?: string;
145
+ /**
146
+ * Resource labels. Alchemy internal labels (`alchemy_app`,
147
+ * `alchemy_stage`, `alchemy_id`) are merged on top automatically.
148
+ * Mutable via `patch` with `updateMask=labels`.
149
+ * @see https://cloud.google.com/artifact-registry/docs/reference/rest/v1/projects.locations.repositories#Repository.FIELDS.labels
150
+ */
151
+ labels?: Record<string, string>;
152
+ /**
153
+ * Customer-managed encryption key, fully-qualified
154
+ * (`projects/{p}/locations/{l}/keyRings/{kr}/cryptoKeys/{k}`).
155
+ * Immutable on the GCP side — we surface that as a replace trigger.
156
+ * Requires the AR service agent to hold
157
+ * `roles/cloudkms.cryptoKeyEncrypterDecrypter` on the key.
158
+ * @see https://cloud.google.com/artifact-registry/docs/cmek
159
+ */
160
+ kmsKeyName?: string;
161
+ /**
162
+ * Docker-format repository configuration. Mutable via `patch` with
163
+ * `updateMask=dockerConfig`.
164
+ * @see https://cloud.google.com/artifact-registry/docs/reference/rest/v1/projects.locations.repositories#DockerRepositoryConfig
165
+ */
166
+ dockerConfig?: {
167
+ /**
168
+ * When true, image tags inside this repository cannot be moved or
169
+ * deleted once written. Useful for supply-chain hardening.
170
+ */
171
+ immutableTags?: boolean;
172
+ };
173
+ /**
174
+ * Remote-repository configuration. Required (and only meaningful)
175
+ * when `mode === "REMOTE_REPOSITORY"`. Immutable on the GCP side —
176
+ * any change to fields under this object triggers a replace.
177
+ * @see https://cloud.google.com/artifact-registry/docs/reference/rest/v1/projects.locations.repositories#RemoteRepositoryConfig
178
+ */
179
+ remoteRepositoryConfig?: {
180
+ /**
181
+ * Description of the remote source (distinct from the top-level
182
+ * `description`).
183
+ */
184
+ description?: string;
185
+ /** Docker upstream — public preset or arbitrary HTTPS URI. */
186
+ dockerRepository?: ArtifactRegistryDockerUpstream;
187
+ /**
188
+ * If true, AR skips the create-time HEAD request against the
189
+ * upstream. Useful for upstreams that gate unauthenticated probes
190
+ * (private nvcr.io paths, etc.).
191
+ */
192
+ disableUpstreamValidation?: boolean;
193
+ /**
194
+ * Credentials for authenticated upstreams — supply a Secret
195
+ * Manager version reference for the password rather than the
196
+ * cleartext value.
197
+ */
198
+ upstreamCredentials?: {
199
+ usernamePasswordCredentials?: {
200
+ username?: string;
201
+ /**
202
+ * Secret Manager secret version path:
203
+ * `projects/{p}/secrets/{s}/versions/{v}`.
204
+ */
205
+ passwordSecretVersion?: string;
206
+ };
207
+ };
208
+ };
209
+ /**
210
+ * Cleanup policies — map of policy ID → policy spec. Pass-through
211
+ * to the API today; the policy types are accepted via the
212
+ * distilled SDK's `CleanupPolicy` shape but not specifically
213
+ * validated by this provider. Mutable via `patch` with
214
+ * `updateMask=cleanupPolicies`.
215
+ * @see https://cloud.google.com/artifact-registry/docs/repositories/cleanup-policy
216
+ */
217
+ cleanupPolicies?: Record<string, ar.CleanupPolicy>;
218
+ /**
219
+ * If true, cleanup policies are evaluated and reported but no
220
+ * versions are actually deleted. Mutable via `patch` with
221
+ * `updateMask=cleanupPolicyDryRun`.
222
+ * @see https://cloud.google.com/artifact-registry/docs/repositories/cleanup-policy#test
223
+ */
224
+ cleanupPolicyDryRun?: boolean;
225
+ };
226
+ export type ArtifactRegistryRepositoryAttributes = {
227
+ /** Bare repository name (no `projects/.../repositories/` prefix). */
228
+ name: string;
229
+ /**
230
+ * Server-side fully-qualified name:
231
+ * `projects/{project}/locations/{location}/repositories/{name}`.
232
+ */
233
+ fullyQualifiedName: string;
234
+ /** GCP project ID. */
235
+ project: string;
236
+ /** Region. */
237
+ location: string;
238
+ /** Echoed format (e.g. `DOCKER`). */
239
+ format: string;
240
+ /** Echoed mode (e.g. `STANDARD_REPOSITORY`). */
241
+ mode: string;
242
+ /**
243
+ * Repository endpoint (e.g. `europe-west4-docker.pkg.dev/proj/repo`)
244
+ * — the host:path you'd `docker pull` from. Populated by the server.
245
+ */
246
+ registryUri: string | undefined;
247
+ /** Total stored size in bytes, server-reported. */
248
+ sizeBytes: string | undefined;
249
+ /** PZS compliance flag. */
250
+ satisfiesPzs: boolean | undefined;
251
+ /** PZI compliance flag. */
252
+ satisfiesPzi: boolean | undefined;
253
+ /** Labels currently set, including alchemy internals. */
254
+ labels: Record<string, string>;
255
+ /** RFC3339 create timestamp. */
256
+ createTime: string;
257
+ /** RFC3339 last-update timestamp. */
258
+ updateTime: string;
259
+ };
260
+ export type ArtifactRegistryRepository = Resource<"GCP.ArtifactRegistryRepository", ArtifactRegistryRepositoryProps, ArtifactRegistryRepositoryAttributes, never, GCP.Providers>;
261
+ export declare const ArtifactRegistryRepository: import("alchemy").ResourceClass<ArtifactRegistryRepository>;
262
+ export declare const ArtifactRegistryRepositoryProvider: () => import("effect/Layer").Layer<Provider.Provider<ArtifactRegistryRepository>, never, import("alchemy").Stack | import("alchemy").Stage | import("@distilled.cloud/gcp").Credentials | import("effect/unstable/http/HttpClient").HttpClient>;
263
+ //# sourceMappingURL=Repository.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Repository.d.ts","sourceRoot":"","sources":["../../src/ArtifactRegistry/Repository.ts"],"names":[],"mappings":"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"}