1import * as Schema from "effect/Schema";
2
3/**
4 * An npm package name, scoped or unscoped, under the rules npm applies to
5 * new packages: lowercase, URL-safe, at most 214 characters. Names end up
6 * in R2 keys, install URLs, and the markdown of comments and check runs,
7 * so nothing outside this set is ever accepted from a client.
8 */
9export const PackageName = Schema.String.pipe(
10 Schema.check(
11 Schema.isPattern(
12 /^(?:@[a-z0-9-*~][a-z0-9-*._~]*\/)?[a-z0-9-~][a-z0-9-._~]*$/,
13 ),
14 Schema.isMaxLength(214),
15 ),
16);
17
18/** A display group label for the install comment: `Alchemy`, `@alchemy.run`. */
19export const GroupName = Schema.String.pipe(
20 Schema.check(Schema.isPattern(/^[@A-Za-z0-9][A-Za-z0-9 ._@/-]{0,63}$/)),
21);
22
23/**
24 * One packed workspace package inside a `pkg pack` artifact.
25 *
26 * Everything here is data the CLI observed while packing. The registry never
27 * derives a tag from it: every tag comes from the GitHub Actions run that
28 * vouched for the manifest, and R2 verifies uploaded tarball bytes against
29 * the hash they are stored under.
30 */
31export const ManifestPackage = Schema.Struct({
32 name: PackageName,
33 /** Version from the package manifest at pack time. */
34 version: Schema.String,
35 /** Package directory relative to the workspace root, POSIX separators. */
36 dir: Schema.String,
37 group: GroupName,
38 /** Tarball file name inside the artifact directory. */
39 file: Schema.String,
40 /** Lowercase hex SHA-256 of the tarball bytes. */
41 sha256: Schema.String,
42 /** Tarball size in bytes. */
43 size: Schema.Number,
44});
45export type ManifestPackage = typeof ManifestPackage.Type;
46
47/** A display group in the install comment, in the order `pkg pack` listed it. */
48export const ManifestGroup = Schema.Struct({
49 name: GroupName,
50 /** Render the group collapsed in the install comment. */
51 collapsed: Schema.Boolean,
52});
53export type ManifestGroup = typeof ManifestGroup.Type;
54
55/**
56 * The `pkg-manifest.json` written next to the tarballs by `pkg pack` and read
57 * back by `pkg publish`.
58 */
59export const Manifest = Schema.Struct({
60 version: Schema.Literal(1),
61 groups: Schema.Array(ManifestGroup),
62 /** Registry origin the tarball dependencies were rewritten against. */
63 registry: Schema.String,
64 /**
65 * HEAD commit of the root repository at pack time. The registry requires
66 * it to be the head of the run that publishes, since that is the commit
67 * every tag names.
68 */
69 head: Schema.String,
70 packages: Schema.Array(ManifestPackage),
71});
72export type Manifest = typeof Manifest.Type;
73
74export const ManifestJson = Schema.fromJsonString(Manifest);
75
76export const MANIFEST_FILE = "pkg-manifest.json";