1/**
2 * Shared name-mangling helpers for Prisma physical names and binding env
3 * keys. Internal — not exported from the Prisma package surface.
4 */
5
6export const fnv1a64 = (value: string) => {
7 let hash = 0xcbf29ce484222325n;
8 for (const byte of new TextEncoder().encode(value)) {
9 hash ^= BigInt(byte);
10 hash = BigInt.asUintN(64, hash * 0x100000001b3n);
11 }
12 return hash.toString(16).padStart(16, "0").toUpperCase();
13};
14
15/**
16 * Deterministic physical name for a cloud object owned by one resource
17 * instance: the logical name plus a 12-character token of the instance
18 * identity, inside a 65-character budget. Stable across retries, so a create
19 * whose response was lost (crash after the POST but before the state persist)
20 * can be recovered by name instead of minting a second object.
21 */
22export const physicalInstanceName = (name: string, instanceId: string) => {
23 const instanceToken = instanceId.replaceAll(/[^a-zA-Z0-9]/g, "");
24 const effectiveSuffix =
25 instanceToken.length >= 12
26 ? instanceToken.slice(0, 12)
27 : fnv1a64(instanceId).slice(0, 12);
28 const maxPrefixLength = 65 - effectiveSuffix.length - 1;
29 return `${name.trim().slice(0, maxPrefixLength)}-${effectiveSuffix}`;
30};
31
32export const envName = (value: string) => {
33 const normalized = value.replaceAll(/[^a-zA-Z0-9]/g, "_").toUpperCase();
34 // Preserve the established keys for conventional PascalCase FQNs while
35 // disambiguating arbitrary logical IDs whose lossy normalization can
36 // collide (`db-a`, `db_a`, and `db.a`, for example).
37 const canonical = value
38 .split("/")
39 .every((segment) => /^[A-Z][a-z0-9]*$/.test(segment));
40 return canonical ? normalized : `${normalized}_${fnv1a64(value)}`;
41};