@rness/cli 0.3.0 → 0.5.0
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.
- package/README.md +177 -7
- package/dist/bin/rness.js +32 -33
- package/dist/bin/rness.js.map +1 -1
- package/dist/chunk-WSGPDTPQ.js +3857 -0
- package/dist/chunk-WSGPDTPQ.js.map +1 -0
- package/dist/index.js +61 -37
- package/dist/index.js.map +1 -1
- package/package.json +16 -7
- package/scaffold/.github/workflows/validate.yml +2 -1
- package/scaffold/README.md +1 -1
- package/scaffold/WORKSPACE.md +7 -5
- package/scaffold/pnpm-workspace.yaml +4 -0
- package/dist/chunk-4KNZT4G4.js +0 -791
- package/dist/chunk-4KNZT4G4.js.map +0 -1
package/README.md
CHANGED
|
@@ -6,6 +6,8 @@ Not an agent — no LLM loop.
|
|
|
6
6
|
|
|
7
7
|
## Install
|
|
8
8
|
|
|
9
|
+
npm create rness # prompts for the organization, then the repositories for your workspace
|
|
10
|
+
npm create rness acme # the organization github.com/acme, no first prompt
|
|
9
11
|
npm i -g @rness/cli # the command is `rness`
|
|
10
12
|
npx @rness/cli --help
|
|
11
13
|
|
|
@@ -14,14 +16,182 @@ Inside a workspace, every `rness` delegates to the copy pinned in
|
|
|
14
16
|
|
|
15
17
|
## Commands
|
|
16
18
|
|
|
17
|
-
rness
|
|
18
|
-
rness
|
|
19
|
-
rness sync [--scope <name>] [--check] [--pull] -y
|
|
19
|
+
rness create [<org>] [--repos a,b] [--pm npm|pnpm|yarn|bun] [--ssh|--https] [--skip-install] -y
|
|
20
|
+
rness add <repo> [--scopes apps/web,packages/ui] [--ssh|--https] -y
|
|
21
|
+
rness sync [--all] [--scope <name>] [--check] [--pull] -y
|
|
22
|
+
rness upgrade [<version>] -y
|
|
23
|
+
rness login [--setup-git|--no-setup-git]
|
|
24
|
+
rness logout
|
|
25
|
+
rness context [--scope <name>] [--json]
|
|
26
|
+
rness validate
|
|
20
27
|
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
28
|
+
`create` never runs inside a workspace. `add`, `sync` and `create` ask for
|
|
29
|
+
confirmation in a terminal; pass `-y`/`--yes` in scripts. `sync --check`
|
|
30
|
+
writes nothing and exits 1 when a block is out of date — use it in CI.
|
|
31
|
+
|
|
32
|
+
### Log in
|
|
33
|
+
|
|
34
|
+
rness login # shows a code and https://github.com/login/device
|
|
35
|
+
rness logout
|
|
36
|
+
|
|
37
|
+
`rness login` connects rness to your GitHub account (OAuth device flow: you
|
|
38
|
+
approve a code in a browser, on any machine). Logged in, `create` lists the
|
|
39
|
+
private repositories you can access, offers your organizations to choose
|
|
40
|
+
from, and says as whom it looks at one (`member acme (as you)`). The
|
|
41
|
+
`create` wizard offers the login itself when it would otherwise list
|
|
42
|
+
anonymously.
|
|
43
|
+
|
|
44
|
+
- The login is one file, `~/.config/rness/auth.json` (`$XDG_CONFIG_HOME`,
|
|
45
|
+
`%APPDATA%` on Windows), readable by you only. The access token lives 8
|
|
46
|
+
hours and is renewed on its own. `GITHUB_TOKEN`, then `GH_TOKEN`, win over
|
|
47
|
+
it — CI needs no login.
|
|
48
|
+
- rness asks for `repo` and `read:org`: GitHub has no read-only scope for
|
|
49
|
+
private repositories. It only lists and clones.
|
|
50
|
+
- A new workspace has to reach GitHub before teammates can join it. Logged
|
|
51
|
+
in, the `create` wizard offers to do it: it creates the private repository
|
|
52
|
+
`<org>/.rness` and pushes the context with `git`. Declined, refused by
|
|
53
|
+
GitHub, anonymous or with `--yes`, it prints the two manual steps instead
|
|
54
|
+
— create the empty repository on github.com, then `git remote add origin …
|
|
55
|
+
&& git push`. No other tool is ever needed.
|
|
56
|
+
- An organization that restricts OAuth apps hides its private repositories
|
|
57
|
+
until an owner approves "Rness"; `create` says so, with the link.
|
|
58
|
+
- Over HTTPS, rness's own clones and pulls carry the login — through the
|
|
59
|
+
environment of that one git command, never in a URL or `.git/config`. For
|
|
60
|
+
your own `git pull` and `git push`, `login` offers to make rness git's
|
|
61
|
+
credential helper for github.com (`--setup-git`, `--no-setup-git`);
|
|
62
|
+
`logout` undoes it. It needs a global install (`npm i -g @rness/cli`): a
|
|
63
|
+
copy run through `npx` lives in a cache. Over SSH none of this is needed.
|
|
64
|
+
The helper names `node` by its absolute path: after a Node upgrade through
|
|
65
|
+
a version manager (mise, nvm), run `rness login --setup-git` again.
|
|
66
|
+
- `rness logout` forgets the login; revoke the authorization itself in
|
|
67
|
+
GitHub's settings (the command prints the link).
|
|
68
|
+
|
|
69
|
+
### SSH or HTTPS
|
|
70
|
+
|
|
71
|
+
`create` and `add` test your SSH access to github.com once
|
|
72
|
+
(`ssh -T git@github.com`) and write `git@github.com:` URLs when GitHub accepts
|
|
73
|
+
your key, `https://github.com/` ones otherwise; `--ssh` and `--https` decide
|
|
74
|
+
without the test. In a terminal `ssh` may ask for your key's passphrase;
|
|
75
|
+
without one (`--yes`, CI) it never prompts, so a key that needs a passphrase
|
|
76
|
+
counts as no access unless an agent holds it.
|
|
77
|
+
|
|
78
|
+
`rness.json` is authoritative: a URL written there is cloned as written, never
|
|
79
|
+
converted. In a workspace whose catalogue clones over SSH, `create` (joining)
|
|
80
|
+
and `sync` stop before the first clone when the SSH test fails and say how to
|
|
81
|
+
set up a key; `add` offers "Clone <name> over HTTPS instead?" (or `--https`),
|
|
82
|
+
which writes an HTTPS URL for that repository only.
|
|
83
|
+
|
|
84
|
+
Without an agent, a protected key is asked for again by every `git clone`.
|
|
85
|
+
Load it once per session: `ssh-add --apple-use-keychain ~/.ssh/id_ed25519` on
|
|
86
|
+
macOS, `ssh-add ~/.ssh/id_ed25519` elsewhere.
|
|
87
|
+
|
|
88
|
+
### Colour
|
|
89
|
+
|
|
90
|
+
In a terminal `create`, `login`, `add`, `sync` and `upgrade` run as one
|
|
91
|
+
session: an intro, a line per finished step, spinners, a "Next" box, an
|
|
92
|
+
outro — in the same gutter as the questions. A spinner never animates while
|
|
93
|
+
git might ask for a passphrase: rness first tests SSH unattended, and clones
|
|
94
|
+
animate only when that passed. The help and the banner are coloured. Through a pipe, in CI, or with `NO_COLOR=1`, the output is plain text —
|
|
95
|
+
the same bytes as before 0.5.0; `FORCE_COLOR=1` paints it anyway. No
|
|
96
|
+
dependency does this: `util.styleText`, and a banner kept as a constant.
|
|
97
|
+
|
|
98
|
+
### Upgrade
|
|
99
|
+
|
|
100
|
+
rness upgrade # the latest release; `rness upgrade 0.5.0` for another
|
|
101
|
+
npx @rness/cli@latest upgrade # from a workspace pinned below 0.5.0
|
|
102
|
+
|
|
103
|
+
The version is written in one place, `.rness/package.json`. `upgrade` pins it
|
|
104
|
+
there (exact, the rest of the file untouched), installs with the workspace's
|
|
105
|
+
package manager, then syncs through the new copy; a failed install restores
|
|
106
|
+
the file. Commit `.rness`; teammates pull and install in `.rness`. Until they
|
|
107
|
+
do, every command warns that the workspace pins one version and holds
|
|
108
|
+
another. It is never delegated to the pinned copy, which is what it replaces
|
|
109
|
+
— so a workspace pinned below 0.5.0, whose copy has no such command, starts
|
|
110
|
+
with the `npx` form.
|
|
111
|
+
|
|
112
|
+
An upgrade touches `.rness` only: a generated block is current when its hash
|
|
113
|
+
is, whatever wrote it, so no `AGENTS.md` of the organization changes unless
|
|
114
|
+
its content does.
|
|
115
|
+
|
|
116
|
+
Exit codes: 0 success, 1 failure, 2 usage — or a refusal without a TTY.
|
|
117
|
+
`RNESS_DEBUG=1` adds stack traces; `RNESS_NO_DELEGATE=1` skips the delegation.
|
|
118
|
+
|
|
119
|
+
## 0.5.0 — the organization is the workspace; rness.json is its catalogue
|
|
120
|
+
|
|
121
|
+
- `create <org>` names the organization, not a directory any more (`--org
|
|
122
|
+
<org>` and the prompt "What is your GitHub organization named?" do the
|
|
123
|
+
same). The workspace directory is `./<org>`, with the organization's exact
|
|
124
|
+
name; `--dir` is removed. With `npm create`, flags go after `--`:
|
|
125
|
+
`npm create rness acme -- --yes`.
|
|
126
|
+
- SSH first: `create` and `add` write `git@github.com:` URLs when
|
|
127
|
+
`ssh -T git@github.com` accepts your key, HTTPS ones otherwise (0.4.0
|
|
128
|
+
wrote HTTPS unless `--ssh`). `--https` is new. A private `.rness` you reach
|
|
129
|
+
over SSH is now found when joining. See "SSH or HTTPS" above.
|
|
130
|
+
- `create` does not offer repositories whose name starts with a dot
|
|
131
|
+
(`.github`, …).
|
|
132
|
+
- Colour, a banner and progress lines in a terminal (see "Colour" above);
|
|
133
|
+
nothing changes for scripts.
|
|
134
|
+
- `rness login` / `rness logout` are new: private repositories are listed,
|
|
135
|
+
and cloned over HTTPS with the login (see "Log in" above). Without a login
|
|
136
|
+
the note reads `rness login lists the private ones you can access`.
|
|
137
|
+
- `rness upgrade` is new (see "Upgrade" above). From 0.4.0:
|
|
138
|
+
`npx @rness/cli@latest upgrade`.
|
|
139
|
+
- The header of a generated block no longer names the CLI version
|
|
140
|
+
(`<!-- rness · scope: … -->`), and `sync` decides by the hash like
|
|
141
|
+
`validate`: upgrading rewrites no `AGENTS.md`. Blocks written by 0.2–0.4
|
|
142
|
+
stay as they are until their content changes. A 0.4.0 CLI calls the new
|
|
143
|
+
header stale — upgrade every copy together.
|
|
144
|
+
- The scaffold's CI workflow reads the version from `package.json` instead of
|
|
145
|
+
naming it; `upgrade` migrates the old line.
|
|
146
|
+
- `.rness/rness.json` is the organization's catalogue — every repository
|
|
147
|
+
rness knows about, shared by the team. Your workspace is the part of it
|
|
148
|
+
you cloned into `org/`; two teammates can clone different repositories,
|
|
149
|
+
and nothing but `org/` records the choice. A choice never removes a
|
|
150
|
+
repository from the catalogue.
|
|
151
|
+
- `create` lists the organization's repositories to search and pick from,
|
|
152
|
+
with every catalogue repository pre-selected when joining (a catalogue
|
|
153
|
+
repository the listing does not return is still offered, marked
|
|
154
|
+
`in .rness`). A picked catalogue repository is cloned; a picked new one is
|
|
155
|
+
added to the catalogue, as `rness add` does. Without a picker, `--repos`
|
|
156
|
+
is the selection; a join without `--repos` clones the whole catalogue. A
|
|
157
|
+
cancelled or declined prompt writes nothing and exits 0.
|
|
158
|
+
- The listing needs no credentials. Without a `GITHUB_TOKEN` (or `GH_TOKEN`)
|
|
159
|
+
only public repositories are listed — and a personal account always lists
|
|
160
|
+
only its public ones; add the others later with `rness add <repo>`.
|
|
161
|
+
- `rness sync` works on your clones: it writes the blocks of the repositories
|
|
162
|
+
in `org/`, never of `rness.json` as a whole. In a terminal it asks "Do you
|
|
163
|
+
want to sync as well?" with the catalogue repositories you have not cloned
|
|
164
|
+
("Select all", or pick some); what you pick is cloned first. With `--yes`,
|
|
165
|
+
or `--check`, nothing is cloned and one `not cloned:` line names them
|
|
166
|
+
(`--check` does not fail on it). `rness sync --all` clones them all without
|
|
167
|
+
asking. A clone `rness.json` does not know gets no block and a
|
|
168
|
+
`not in rness.json:` line pointing at `rness add`.
|
|
169
|
+
- A workspace pinned to 0.4.x clones every catalogue repository on sync —
|
|
170
|
+
`create` runs the pinned copy's sync after joining.
|
|
171
|
+
- Joining a workspace whose `.rness` pins an older `@rness/cli` than the one
|
|
172
|
+
you run says so, and that `rness upgrade` moves it.
|
|
173
|
+
- Repository and scope names take what GitHub allows, in lowercase: letters,
|
|
174
|
+
digits, `.`, `_` and `-` (`my_lib`, `angular.js`). A name that differs only
|
|
175
|
+
by case is declared in lowercase. A 0.4.0 CLI rejects a `rness.json` that
|
|
176
|
+
holds a `.` or a `_` in a name — upgrade every copy together.
|
|
177
|
+
- Organization names follow GitHub's rule — letters, digits and single
|
|
178
|
+
hyphens, not at either end, at most 39 characters — in `--org` and in
|
|
179
|
+
`rness.json`'s `"org"`; the case is kept as typed.
|
|
180
|
+
- `"org"` in `rness.json` now accepts uppercase letters: a 0.4.0 CLI rejects
|
|
181
|
+
a workspace whose `"org"` has any, so upgrade every copy together.
|
|
182
|
+
|
|
183
|
+
## 0.4.0 — create, add, the shims
|
|
184
|
+
|
|
185
|
+
- `npm create rness <org>` starts a new workspace for `github.com/<org>` or
|
|
186
|
+
joins its existing `.rness`.
|
|
187
|
+
- `rness add <repo>` clones (or adopts) a repository under `org/`, declares
|
|
188
|
+
it and any `--scopes` sub-directories, then syncs.
|
|
189
|
+
- `create-rness` and `@rness/create` are two-file shims pinned to the exact
|
|
190
|
+
same version as `@rness/cli`, so the short `npm create` commands run this
|
|
191
|
+
CLI.
|
|
192
|
+
- A new workspace's scaffold ships a `pnpm-workspace.yaml`
|
|
193
|
+
(`minimumReleaseAgeExclude: ['@rness/cli']`) — pnpm 12 otherwise refuses a
|
|
194
|
+
version published less than 24h earlier.
|
|
25
195
|
|
|
26
196
|
## 0.3.0 — what changed for a 0.2.0 workspace
|
|
27
197
|
|
package/dist/bin/rness.js
CHANGED
|
@@ -1,38 +1,15 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
VERSION,
|
|
4
|
-
|
|
4
|
+
driftWarning,
|
|
5
|
+
findDelegate,
|
|
5
6
|
reportError,
|
|
6
7
|
run
|
|
7
|
-
} from "../chunk-
|
|
8
|
+
} from "../chunk-WSGPDTPQ.js";
|
|
8
9
|
|
|
9
10
|
// src/bin/rness.ts
|
|
10
11
|
import { pathToFileURL } from "url";
|
|
11
12
|
|
|
12
|
-
// src/core/delegate.ts
|
|
13
|
-
import { readFile } from "fs/promises";
|
|
14
|
-
import { join } from "path";
|
|
15
|
-
async function findDelegate(cwd, ownVersion) {
|
|
16
|
-
let root;
|
|
17
|
-
let rnessDir;
|
|
18
|
-
try {
|
|
19
|
-
const ws = await findWorkspace(cwd);
|
|
20
|
-
root = ws.root;
|
|
21
|
-
rnessDir = ws.rnessDir;
|
|
22
|
-
} catch {
|
|
23
|
-
return null;
|
|
24
|
-
}
|
|
25
|
-
const pkgDir = join(rnessDir, "node_modules", "@rness", "cli");
|
|
26
|
-
let version;
|
|
27
|
-
try {
|
|
28
|
-
version = JSON.parse(await readFile(join(pkgDir, "package.json"), "utf8")).version;
|
|
29
|
-
} catch {
|
|
30
|
-
return null;
|
|
31
|
-
}
|
|
32
|
-
if (typeof version !== "string" || version === ownVersion) return null;
|
|
33
|
-
return { entry: join(pkgDir, "dist", "index.js"), version, root };
|
|
34
|
-
}
|
|
35
|
-
|
|
36
13
|
// src/core/node-version.ts
|
|
37
14
|
var MIN_NODE_MAJOR = 24;
|
|
38
15
|
function nodeMajor(version) {
|
|
@@ -50,18 +27,39 @@ process.stdout.on("error", (e) => {
|
|
|
50
27
|
});
|
|
51
28
|
async function main() {
|
|
52
29
|
if (!isSupportedNode(process.versions.node)) {
|
|
53
|
-
process.stderr.write(
|
|
54
|
-
`)
|
|
30
|
+
process.stderr.write(
|
|
31
|
+
`rness needs Node ${MIN_NODE_MAJOR} or newer (running ${process.version})
|
|
32
|
+
`
|
|
33
|
+
);
|
|
55
34
|
return 1;
|
|
56
35
|
}
|
|
57
36
|
const argv = process.argv.slice(2);
|
|
58
|
-
const
|
|
37
|
+
const own = [
|
|
38
|
+
"create",
|
|
39
|
+
"upgrade",
|
|
40
|
+
"update",
|
|
41
|
+
"login",
|
|
42
|
+
"logout",
|
|
43
|
+
"git-credential"
|
|
44
|
+
].includes(argv[0] ?? "");
|
|
45
|
+
const noDelegate = process.env["RNESS_NO_DELEGATE"] === "1";
|
|
46
|
+
const skipDelegation = own || noDelegate;
|
|
47
|
+
const command = argv[0];
|
|
48
|
+
if (command !== void 0 && !command.startsWith("-") && !own && !noDelegate) {
|
|
49
|
+
const warning = await driftWarning(process.cwd());
|
|
50
|
+
if (warning !== null) process.stderr.write(`${warning}
|
|
51
|
+
`);
|
|
52
|
+
}
|
|
59
53
|
const delegate = skipDelegation ? null : await findDelegate(process.cwd(), VERSION);
|
|
60
54
|
if (delegate !== null) {
|
|
61
|
-
const broken = (reason) => new Error(
|
|
55
|
+
const broken = (reason) => new Error(
|
|
56
|
+
`@rness/cli ${delegate.version} pinned in ${delegate.root}/.rness is not installed correctly (${reason}); reinstall in .rness/`
|
|
57
|
+
);
|
|
62
58
|
if (process.env["RNESS_DEBUG"] === "1") {
|
|
63
|
-
process.stderr.write(
|
|
64
|
-
`)
|
|
59
|
+
process.stderr.write(
|
|
60
|
+
`rness: delegating to @rness/cli ${delegate.version} (${delegate.entry})
|
|
61
|
+
`
|
|
62
|
+
);
|
|
65
63
|
}
|
|
66
64
|
let mod;
|
|
67
65
|
try {
|
|
@@ -69,7 +67,8 @@ async function main() {
|
|
|
69
67
|
} catch (e) {
|
|
70
68
|
throw broken(e instanceof Error ? e.message : String(e));
|
|
71
69
|
}
|
|
72
|
-
if (typeof mod["run"] !== "function")
|
|
70
|
+
if (typeof mod["run"] !== "function")
|
|
71
|
+
throw broken("dist/index.js does not export run");
|
|
73
72
|
const delegateRun = mod["run"];
|
|
74
73
|
const code = await delegateRun(argv);
|
|
75
74
|
return typeof code === "number" ? code : 1;
|
package/dist/bin/rness.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/bin/rness.ts","../../src/core/
|
|
1
|
+
{"version":3,"sources":["../../src/bin/rness.ts","../../src/core/node-version.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { pathToFileURL } from 'node:url'\n\nimport { run } from '../cli.ts'\nimport { findDelegate } from '../core/delegate.ts'\nimport { MIN_NODE_MAJOR, isSupportedNode } from '../core/node-version.ts'\nimport { driftWarning } from '../core/pinned.ts'\nimport { reportError } from '../report.ts'\nimport { VERSION } from '../version.ts'\n\n// `rness context | head`: once the reader has its lines it closes the pipe and\n// every further write emits EPIPE on stdout. Nothing is left to deliver, so end\n// quietly with success. This is the one process.exit() in the code base — it\n// runs only when there is no output left to drain (see main() below).\nprocess.stdout.on('error', (e: NodeJS.ErrnoException) => {\n if (e.code === 'EPIPE') process.exit(0)\n throw e\n})\n\n// Set process.exitCode rather than calling process.exit(): process.exit()\n// terminates before Node drains an async stdout pipe, truncating piped output\n// at the ~64 KiB pipe buffer (breaks `rness context --json | jq`, `$(...)`).\nasync function main(): Promise<number> {\n if (!isSupportedNode(process.versions.node)) {\n process.stderr.write(\n `rness needs Node ${MIN_NODE_MAJOR} or newer (running ${process.version})\\n`\n )\n return 1\n }\n const argv = process.argv.slice(2)\n // `create` makes a workspace and `upgrade` replaces the pinned copy: both\n // are served by the copy the user invoked (spec 0006 §3). The login concerns\n // the machine, not a workspace — and git runs `git-credential` from inside\n // a clone, on every fetch: no delegation, and no warning there either.\n const own = [\n 'create',\n 'upgrade',\n 'update',\n 'login',\n 'logout',\n 'git-credential',\n ].includes(argv[0] ?? '')\n const noDelegate = process.env['RNESS_NO_DELEGATE'] === '1'\n const skipDelegation = own || noDelegate\n const command = argv[0]\n if (\n command !== undefined &&\n !command.startsWith('-') &&\n !own &&\n !noDelegate\n ) {\n const warning = await driftWarning(process.cwd())\n if (warning !== null) process.stderr.write(`${warning}\\n`)\n }\n const delegate = skipDelegation\n ? null\n : await findDelegate(process.cwd(), VERSION)\n if (delegate !== null) {\n const broken = (reason: string): Error =>\n new Error(\n `@rness/cli ${delegate.version} pinned in ${delegate.root}/.rness is not installed correctly (${reason}); reinstall in .rness/`\n )\n if (process.env['RNESS_DEBUG'] === '1') {\n process.stderr.write(\n `rness: delegating to @rness/cli ${delegate.version} (${delegate.entry})\\n`\n )\n }\n let mod: Record<string, unknown>\n try {\n mod = (await import(pathToFileURL(delegate.entry).href)) as Record<\n string,\n unknown\n >\n } catch (e) {\n throw broken(e instanceof Error ? e.message : String(e))\n }\n if (typeof mod['run'] !== 'function')\n throw broken('dist/index.js does not export run')\n const delegateRun = mod['run'] as (argv: string[]) => Promise<unknown>\n const code = await delegateRun(argv)\n return typeof code === 'number' ? code : 1\n }\n return run(argv)\n}\n\nmain()\n .then((code) => {\n process.exitCode = code\n })\n .catch((e: unknown) => {\n process.exitCode = reportError(e)\n })\n","export const MIN_NODE_MAJOR = 24\n\nexport function nodeMajor(version: string): number {\n const major = Number.parseInt(version.split('.')[0] ?? '', 10)\n return Number.isNaN(major) ? 0 : major\n}\n\nexport function isSupportedNode(version: string): boolean {\n return nodeMajor(version) >= MIN_NODE_MAJOR\n}\n"],"mappings":";;;;;;;;;;AACA,SAAS,qBAAqB;;;ACDvB,IAAM,iBAAiB;AAEvB,SAAS,UAAU,SAAyB;AACjD,QAAM,QAAQ,OAAO,SAAS,QAAQ,MAAM,GAAG,EAAE,CAAC,KAAK,IAAI,EAAE;AAC7D,SAAO,OAAO,MAAM,KAAK,IAAI,IAAI;AACnC;AAEO,SAAS,gBAAgB,SAA0B;AACxD,SAAO,UAAU,OAAO,KAAK;AAC/B;;;ADKA,QAAQ,OAAO,GAAG,SAAS,CAAC,MAA6B;AACvD,MAAI,EAAE,SAAS,QAAS,SAAQ,KAAK,CAAC;AACtC,QAAM;AACR,CAAC;AAKD,eAAe,OAAwB;AACrC,MAAI,CAAC,gBAAgB,QAAQ,SAAS,IAAI,GAAG;AAC3C,YAAQ,OAAO;AAAA,MACb,oBAAoB,cAAc,sBAAsB,QAAQ,OAAO;AAAA;AAAA,IACzE;AACA,WAAO;AAAA,EACT;AACA,QAAM,OAAO,QAAQ,KAAK,MAAM,CAAC;AAKjC,QAAM,MAAM;AAAA,IACV;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF,EAAE,SAAS,KAAK,CAAC,KAAK,EAAE;AACxB,QAAM,aAAa,QAAQ,IAAI,mBAAmB,MAAM;AACxD,QAAM,iBAAiB,OAAO;AAC9B,QAAM,UAAU,KAAK,CAAC;AACtB,MACE,YAAY,UACZ,CAAC,QAAQ,WAAW,GAAG,KACvB,CAAC,OACD,CAAC,YACD;AACA,UAAM,UAAU,MAAM,aAAa,QAAQ,IAAI,CAAC;AAChD,QAAI,YAAY,KAAM,SAAQ,OAAO,MAAM,GAAG,OAAO;AAAA,CAAI;AAAA,EAC3D;AACA,QAAM,WAAW,iBACb,OACA,MAAM,aAAa,QAAQ,IAAI,GAAG,OAAO;AAC7C,MAAI,aAAa,MAAM;AACrB,UAAM,SAAS,CAAC,WACd,IAAI;AAAA,MACF,cAAc,SAAS,OAAO,cAAc,SAAS,IAAI,uCAAuC,MAAM;AAAA,IACxG;AACF,QAAI,QAAQ,IAAI,aAAa,MAAM,KAAK;AACtC,cAAQ,OAAO;AAAA,QACb,mCAAmC,SAAS,OAAO,KAAK,SAAS,KAAK;AAAA;AAAA,MACxE;AAAA,IACF;AACA,QAAI;AACJ,QAAI;AACF,YAAO,MAAM,OAAO,cAAc,SAAS,KAAK,EAAE;AAAA,IAIpD,SAAS,GAAG;AACV,YAAM,OAAO,aAAa,QAAQ,EAAE,UAAU,OAAO,CAAC,CAAC;AAAA,IACzD;AACA,QAAI,OAAO,IAAI,KAAK,MAAM;AACxB,YAAM,OAAO,mCAAmC;AAClD,UAAM,cAAc,IAAI,KAAK;AAC7B,UAAM,OAAO,MAAM,YAAY,IAAI;AACnC,WAAO,OAAO,SAAS,WAAW,OAAO;AAAA,EAC3C;AACA,SAAO,IAAI,IAAI;AACjB;AAEA,KAAK,EACF,KAAK,CAAC,SAAS;AACd,UAAQ,WAAW;AACrB,CAAC,EACA,MAAM,CAAC,MAAe;AACrB,UAAQ,WAAW,YAAY,CAAC;AAClC,CAAC;","names":[]}
|