1import * as GCP from "@/GCP";
2import * as Test from "@/Test/Alchemy";
3import * as licensing from "@distilled.cloud/gcp/licensing_v1";
4import { expect } from "alchemy-test";
5import * as Effect from "effect/Effect";
6import {
7 customerId,
8 logLevel,
9 missingUserId,
10 runLifecycle,
11 productId,
12 skuId,
13 updateSkuId,
14 userId,
15 waitUntilGone,
16} from "./common.ts";
17
18const { test } = Test.make({ providers: GCP.providers() });
19
20test.provider.skipIf(!runLifecycle)(
21 "getLicenseAssignments on a missing assignment fails with NotFound",
22 (stack) =>
23 Effect.gen(function* () {
24 yield* stack.destroy();
25
26 const error = yield* Effect.flip(
27 licensing.getLicenseAssignments({
28 productId,
29 skuId,
30 userId: missingUserId,
31 }),
32 );
33 expect(error._tag).toEqual("NotFound");
34
35 yield* stack.destroy();
36 }).pipe(logLevel),
37 { tags: ["provider:gcp", "provider:gcp:licensing", "live"], timeout: 90_000 },
38);
39
40test.provider.skipIf(runLifecycle)(
41 "insertLicenseAssignments without the licensing scope fails with InsufficientAuthenticationScopes",
42 (stack) =>
43 Effect.gen(function* () {
44 yield* stack.destroy();
45
46 const error = yield* Effect.flip(
47 licensing.insertLicenseAssignments({
48 productId,
49 skuId,
50 body: { userId: missingUserId },
51 }),
52 );
53 expect(error._tag).toEqual("InsufficientAuthenticationScopes");
54
55 yield* stack.destroy();
56 }).pipe(logLevel),
57 { tags: ["provider:gcp", "provider:gcp:licensing", "live"], timeout: 90_000 },
58);
59
60test.provider.skipIf(!runLifecycle)(
61 "create, update, and delete a license assignment",
62 (stack) =>
63 Effect.gen(function* () {
64 yield* stack.destroy();
65
66 const created = yield* stack.deploy(
67 Effect.gen(function* () {
68 return yield* GCP.Licensing.LicenseAssignment("Seat", {
69 productId,
70 skuId,
71 userId,
72 customerId,
73 });
74 }),
75 );
76
77 expect(created.productId).toEqual(productId);
78 expect(created.skuId).toEqual(skuId);
79 expect(created.userId.toLowerCase()).toEqual(userId.toLowerCase());
80 expect(created.project.length).toBeGreaterThan(0);
81
82 const fetched = yield* licensing.getLicenseAssignments({
83 productId: created.productId,
84 skuId: created.skuId,
85 userId: created.userId,
86 });
87 expect(fetched.productId).toEqual(productId);
88 expect(fetched.skuId).toEqual(skuId);
89 expect((fetched.userId ?? "").toLowerCase()).toEqual(
90 userId.toLowerCase(),
91 );
92
93 const updated = yield* stack.deploy(
94 Effect.gen(function* () {
95 return yield* GCP.Licensing.LicenseAssignment("Seat", {
96 productId,
97 skuId: updateSkuId,
98 userId,
99 customerId,
100 });
101 }),
102 );
103
104 expect(updated.productId).toEqual(productId);
105 expect(updated.userId.toLowerCase()).toEqual(userId.toLowerCase());
106 expect(updated.skuId).toEqual(updateSkuId);
107
108 const fetchedUpdate = yield* licensing.getLicenseAssignments({
109 productId: updated.productId,
110 skuId: updated.skuId,
111 userId: updated.userId,
112 });
113 expect(fetchedUpdate.skuId).toEqual(updateSkuId);
114
115 yield* stack.destroy();
116
117 const gone = yield* waitUntilGone({
118 productId: updated.productId,
119 skuId: updated.skuId,
120 userId: updated.userId,
121 });
122 expect(gone).toEqual("gone");
123 }).pipe(logLevel),
124 { tags: ["provider:gcp", "provider:gcp:licensing", "live"], timeout: 90_000 },
125);