@augurworks/augur 0.15.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.
- package/CANVAS.md +858 -0
- package/INSTALL.md +603 -0
- package/LICENSE +27 -0
- package/README.md +150 -0
- package/TRADEMARKS.md +72 -0
- package/agents/README.md +65 -0
- package/agents/canon-extract.md +117 -0
- package/agents/canon.md +151 -0
- package/agents/canvas.md +88 -0
- package/agents/currency.md +74 -0
- package/agents/drafts.md +92 -0
- package/agents/identity.md +148 -0
- package/agents/prototype-contract.md +69 -0
- package/agents/publishing.md +324 -0
- package/agents/review-feedback.md +76 -0
- package/agents/space-json.md +132 -0
- package/agents/ui-skill.md +101 -0
- package/agents/working-marks.md +86 -0
- package/brand/augur-eye.svg +3 -0
- package/brand/augur-icon.svg +41 -0
- package/brand/augur-mark.svg +5 -0
- package/brand/lentianova-bulky.otf +0 -0
- package/brand/lentianova-median.otf +0 -0
- package/brand/lentianova.woff2 +0 -0
- package/build.js +8409 -0
- package/changelog.md +133 -0
- package/fonts/inter-latin-wght-normal.woff2 +0 -0
- package/package.json +57 -0
- package/pitis/PETS.md +121 -0
- package/pitis/README.md +117 -0
- package/pitis/index.html +266 -0
- package/pitis/piti.build.js +81 -0
- package/pitis/piti.js +929 -0
- package/pitis/roast-agent.md +185 -0
- package/realtime/src/index.js +119 -0
- package/realtime/wrangler.example.toml +44 -0
- package/scripts/adopt.mjs +106 -0
- package/scripts/board-snapshot.mjs +197 -0
- package/scripts/build-seed-pack.mjs +33 -0
- package/scripts/bundle-rekey.mjs +112 -0
- package/scripts/bundle-tenancy-rehearsal.mjs +781 -0
- package/scripts/canon-extract.mjs +578 -0
- package/scripts/canon.mjs +599 -0
- package/scripts/canvas-screen.mjs +333 -0
- package/scripts/check-local.mjs +136 -0
- package/scripts/clawd-art.mjs +75 -0
- package/scripts/clawd-canvas.mjs +741 -0
- package/scripts/cli.mjs +100 -0
- package/scripts/clone.mjs +422 -0
- package/scripts/close.mjs +30 -0
- package/scripts/connect.mjs +103 -0
- package/scripts/deploy.mjs +157 -0
- package/scripts/dev.mjs +54 -0
- package/scripts/doc-lint.mjs +143 -0
- package/scripts/export.mjs +300 -0
- package/scripts/fork.mjs +64 -0
- package/scripts/freeze.mjs +74 -0
- package/scripts/frontdoor-parity.mjs +180 -0
- package/scripts/hook.mjs +67 -0
- package/scripts/identity-rekey.mjs +112 -0
- package/scripts/init.mjs +122 -0
- package/scripts/land.mjs +40 -0
- package/scripts/lib/adapters.mjs +156 -0
- package/scripts/lib/board-snapshot.mjs +511 -0
- package/scripts/lib/draft.mjs +385 -0
- package/scripts/lib/graduate.mjs +276 -0
- package/scripts/lib/instance.mjs +74 -0
- package/scripts/lib/marks.mjs +107 -0
- package/scripts/lib/materialize.mjs +138 -0
- package/scripts/lib/merge3.mjs +124 -0
- package/scripts/lib/offline-posture.mjs +120 -0
- package/scripts/lib/offline-respawn.mjs +18 -0
- package/scripts/lib/offline-wrangler.mjs +78 -0
- package/scripts/lib/publish-compose.mjs +12 -0
- package/scripts/lib/publish-conflict.mjs +78 -0
- package/scripts/lib/publish-evidence.mjs +144 -0
- package/scripts/lib/refine-compare.mjs +140 -0
- package/scripts/lib/refine-ledger.mjs +150 -0
- package/scripts/lib/refine-png.mjs +149 -0
- package/scripts/lib/seed-pack-build.mjs +141 -0
- package/scripts/lib/state-compare.mjs +68 -0
- package/scripts/lib/store.mjs +122 -0
- package/scripts/login.mjs +84 -0
- package/scripts/mark.mjs +112 -0
- package/scripts/migrate-board-keys.mjs +164 -0
- package/scripts/migrate.mjs +265 -0
- package/scripts/no-foreign-vocabulary.mjs +216 -0
- package/scripts/no-product-names.mjs +157 -0
- package/scripts/no-tenant-globals.mjs +1134 -0
- package/scripts/offline.mjs +247 -0
- package/scripts/og.mjs +170 -0
- package/scripts/one-tenant-resolver.mjs +146 -0
- package/scripts/open.mjs +63 -0
- package/scripts/publish.mjs +1041 -0
- package/scripts/read.mjs +31 -0
- package/scripts/refine.mjs +455 -0
- package/scripts/release-drift.mjs +138 -0
- package/scripts/restore.mjs +322 -0
- package/scripts/review.mjs +125 -0
- package/scripts/save.mjs +21 -0
- package/scripts/shell-lint.mjs +189 -0
- package/scripts/ship.mjs +460 -0
- package/scripts/shoot.mjs +264 -0
- package/scripts/smoke-invite.mjs +113 -0
- package/scripts/state-inventory.mjs +223 -0
- package/scripts/status.mjs +177 -0
- package/scripts/sync.mjs +27 -0
- package/scripts/tenant-do-rehearsal.mjs +1314 -0
- package/scripts/ui-copy-lint.mjs +202 -0
- package/scripts/watch.mjs +32 -0
- package/scripts/wrangler-preflight.mjs +246 -0
- package/seed/CANON.md +43 -0
- package/seed/README.md +119 -0
- package/seed/prototype-status.json +9 -0
- package/seed/registry.json +88 -0
- package/seed/skills/starter-ui/SKILL.md +52 -0
- package/seed/skills/starter-ui/skill.json +11 -0
- package/seed/skills/starter-ui/starter-tokens.css +73 -0
- package/seed/skills/starter-ui/starter-ui.css +318 -0
- package/seed/skills/starter-ui/starter-ui.js +50 -0
- package/seed/space.json +5 -0
- package/seed/start-here/prototypes/connect-your-terminal/index.html +428 -0
- package/seed/start-here/prototypes/connect-your-terminal/preview.webp +0 -0
- package/seed/start-here/prototypes/sample-with-comments/index.html +172 -0
- package/seed/start-here/prototypes/sample-with-comments/preview.webp +0 -0
- package/seed/start-here/prototypes/set-up-your-design-system/index.html +353 -0
- package/seed/start-here/prototypes/set-up-your-design-system/preview.webp +0 -0
- package/seed/threads.json +52 -0
- package/seed/worked-examples/prototypes/field-readings/index.html +273 -0
- package/seed/worked-examples/prototypes/field-readings/preview.webp +0 -0
- package/seed/worked-examples/prototypes/slide-deck/index.html +214 -0
- package/seed/worked-examples/prototypes/slide-deck/preview.webp +0 -0
- package/seed/worked-examples/prototypes/specimen-viewer/index.html +203 -0
- package/seed/worked-examples/prototypes/specimen-viewer/preview.webp +0 -0
- package/src/_worker.js +12668 -0
- package/src/board-key.mjs +57 -0
- package/src/board-room.mjs +881 -0
- package/src/bundle-keys.mjs +138 -0
- package/src/canon/collect-in-browser.js +215 -0
- package/src/canon/emit.mjs +232 -0
- package/src/canon/observe.mjs +260 -0
- package/src/canon/schema.mjs +451 -0
- package/src/canvas/DSEG-LICENSE.txt +95 -0
- package/src/canvas/DSEG7Classic-Bold.woff2 +0 -0
- package/src/canvas/canvas.css +885 -0
- package/src/canvas/canvas.js +5780 -0
- package/src/canvas/capture.js +485 -0
- package/src/chrome/appchrome.mjs +568 -0
- package/src/currency.mjs +203 -0
- package/src/delete-confirmation.mjs +254 -0
- package/src/drafts/drafts.js +326 -0
- package/src/entry.js +58 -0
- package/src/galleries.mjs +400 -0
- package/src/health-cron.mjs +173 -0
- package/src/identity.json +1 -0
- package/src/kv-codec.mjs +135 -0
- package/src/kv-identity.mjs +259 -0
- package/src/mail.mjs +599 -0
- package/src/provenance.mjs +74 -0
- package/src/publish-compose.mjs +363 -0
- package/src/publish-fork.mjs +221 -0
- package/src/publish-units.mjs +44 -0
- package/src/purge.mjs +81 -0
- package/src/review/COMMENTING-UX.md +306 -0
- package/src/review/cat.png +0 -0
- package/src/review/comment-cursor.svg +7 -0
- package/src/review/comments.js +1738 -0
- package/src/room-ticket.mjs +96 -0
- package/src/roster-chip.mjs +32 -0
- package/src/seed-pack.mjs +261 -0
- package/src/state-inventory.mjs +249 -0
- package/src/sw-logic.mjs +48 -0
- package/src/tenant-cache.mjs +141 -0
- package/src/tenant-context.mjs +386 -0
- package/src/tenant-do.js +2940 -0
- package/src/tenant-host.mjs +144 -0
- package/src/tenant-quotas.mjs +140 -0
- package/src/unit-core.mjs +103 -0
- package/src/unit-object.mjs +338 -0
- package/templates/README.md +67 -0
- package/templates/shell/deploy.yml +145 -0
- package/templates/shell/engine-bump.yml +142 -0
- package/templates/shell/health.yml +233 -0
- package/templates/shell/kv-backup.yml +201 -0
- package/templates/shell/roster-update.yml +110 -0
- package/templates/shell/space-preflight.yml +35 -0
- package/templates/shell/space-rebake.yml +79 -0
- package/templates/shell/store-backup.yml +152 -0
- package/templates/shell/wrangler.example.toml +266 -0
- package/templates/space/publish.yml +91 -0
|
@@ -0,0 +1,177 @@
|
|
|
1
|
+
// status.mjs — "what is live, and is it what I have?"
|
|
2
|
+
//
|
|
3
|
+
// augur status every space this checkout can see
|
|
4
|
+
// … --fetch ask each remote for its current main first
|
|
5
|
+
//
|
|
6
|
+
// This is the command that would have ended a whole evening. Space content ships by
|
|
7
|
+
// publishing, not by pushing, so work can be committed, pushed, reviewed and still
|
|
8
|
+
// not be on the site — and nothing about the repo tells you that. This puts the
|
|
9
|
+
// three numbers side by side: what the store is serving, what your clone has, and
|
|
10
|
+
// what the remote has.
|
|
11
|
+
//
|
|
12
|
+
// Reads /_build.json (public, cache-busted) plus plain git in each space clone. No
|
|
13
|
+
// token needed.
|
|
14
|
+
|
|
15
|
+
import { execFileSync } from "node:child_process";
|
|
16
|
+
import { existsSync, readFileSync, readdirSync } from "node:fs";
|
|
17
|
+
import path from "node:path";
|
|
18
|
+
import { resolveOrigin, resolveToken, apiClient, buildStamp, ENGINE_ROOT } from "./lib/store.mjs";
|
|
19
|
+
import { fetchMarks, markLine } from "./lib/marks.mjs";
|
|
20
|
+
import { registryList, unitClient, draftsReport } from "./lib/draft.mjs";
|
|
21
|
+
|
|
22
|
+
const args = process.argv.slice(2);
|
|
23
|
+
const DO_FETCH = args.includes("--fetch");
|
|
24
|
+
const log = (msg) => console.error(`\x1b[36m[status]\x1b[0m ${msg}`);
|
|
25
|
+
|
|
26
|
+
const C = { dim: "\x1b[2m", red: "\x1b[31m", yellow: "\x1b[33m", green: "\x1b[32m", off: "\x1b[0m" };
|
|
27
|
+
|
|
28
|
+
const origin = resolveOrigin();
|
|
29
|
+
if (!origin) { log('no target origin — set AUGUR_ORIGIN, or add "siteOrigin" to space.json.'); process.exit(1); }
|
|
30
|
+
|
|
31
|
+
const git = (dir, ...a) => {
|
|
32
|
+
try {
|
|
33
|
+
return execFileSync("git", ["-C", dir, ...a], { encoding: "utf8", stdio: ["ignore", "pipe", "ignore"] }).trim();
|
|
34
|
+
} catch (e) { return ""; }
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
// Space clones, found the same way build.js and publish.mjs find them: siblings of
|
|
38
|
+
// the engine, the shell's spaces/ mount, or the cwd itself.
|
|
39
|
+
function findSpaceDirs() {
|
|
40
|
+
const roots = [];
|
|
41
|
+
if (process.env.GV_SPACES_ROOT) roots.push(process.env.GV_SPACES_ROOT);
|
|
42
|
+
roots.push(path.join(ENGINE_ROOT, ".."), path.join(ENGINE_ROOT, "spaces"));
|
|
43
|
+
const out = new Map();
|
|
44
|
+
if (existsSync(path.join(process.cwd(), "space.json"))) out.set(idOf(process.cwd()), process.cwd());
|
|
45
|
+
for (const root of roots) {
|
|
46
|
+
let entries = [];
|
|
47
|
+
try { entries = readdirSync(root, { withFileTypes: true }); } catch (e) { continue; }
|
|
48
|
+
for (const e of entries) {
|
|
49
|
+
if (!e.isDirectory() || e.name.startsWith(".")) continue;
|
|
50
|
+
const dir = path.join(root, e.name);
|
|
51
|
+
if (!existsSync(path.join(dir, "space.json"))) continue;
|
|
52
|
+
const id = idOf(dir);
|
|
53
|
+
if (!out.has(id)) out.set(id, dir);
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
return out;
|
|
57
|
+
}
|
|
58
|
+
function idOf(dir) {
|
|
59
|
+
try { return JSON.parse(readFileSync(path.join(dir, "space.json"), "utf8")).id || path.basename(dir); }
|
|
60
|
+
catch (e) { return path.basename(dir); }
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
const stamp = await buildStamp(origin);
|
|
64
|
+
const clones = findSpaceDirs();
|
|
65
|
+
const ids = [...new Set([...Object.keys(stamp.spaces || {}), ...clones.keys()])].sort();
|
|
66
|
+
|
|
67
|
+
console.log(`${C.dim}${origin}${C.off}`);
|
|
68
|
+
console.log("");
|
|
69
|
+
|
|
70
|
+
let problems = 0;
|
|
71
|
+
for (const id of ids) {
|
|
72
|
+
const liveInfo = (stamp.spaces || {})[id];
|
|
73
|
+
const dir = clones.get(id);
|
|
74
|
+
const head = dir ? git(dir, "rev-parse", "HEAD") : "";
|
|
75
|
+
const localDirty = dir ? git(dir, "status", "--porcelain").length > 0 : false;
|
|
76
|
+
if (dir && DO_FETCH) git(dir, "fetch", "--quiet", "origin");
|
|
77
|
+
const remote = dir ? git(dir, "rev-parse", "origin/main") : "";
|
|
78
|
+
// Direction matters and a plain inequality doesn't carry it: a clone can be
|
|
79
|
+
// ahead of the remote (work nobody else can see) or behind it (work you
|
|
80
|
+
// haven't got yet), and telling someone to pull when they need to push sends
|
|
81
|
+
// them the wrong way.
|
|
82
|
+
const [ahead, behind] = dir && remote
|
|
83
|
+
? git(dir, "rev-list", "--left-right", "--count", `${head}...${remote}`).split(/\s+/).map(Number)
|
|
84
|
+
: [0, 0];
|
|
85
|
+
|
|
86
|
+
const short = (s) => (s ? s.slice(0, 12) : "—");
|
|
87
|
+
const bits = [];
|
|
88
|
+
let verdict, colour;
|
|
89
|
+
|
|
90
|
+
if (!liveInfo) {
|
|
91
|
+
verdict = "never published"; colour = C.red; problems++;
|
|
92
|
+
} else if (liveInfo.dirty) {
|
|
93
|
+
verdict = "published from a working tree"; colour = C.red; problems++;
|
|
94
|
+
} else if (!dir) {
|
|
95
|
+
verdict = "live (no local clone to compare)"; colour = C.dim;
|
|
96
|
+
} else if (liveInfo.sha === head && !localDirty && !ahead && !behind) {
|
|
97
|
+
verdict = "live matches your clone"; colour = C.green;
|
|
98
|
+
} else if (localDirty) {
|
|
99
|
+
verdict = "uncommitted changes — run `augur ship`"; colour = C.yellow; problems++;
|
|
100
|
+
} else if (liveInfo.sha !== head && !behind) {
|
|
101
|
+
verdict = "your clone is AHEAD of live — run `augur ship`"; colour = C.yellow; problems++;
|
|
102
|
+
} else if (ahead) {
|
|
103
|
+
verdict = `${ahead} commit(s) only on this machine — run \`augur ship\``; colour = C.yellow; problems++;
|
|
104
|
+
} else if (behind) {
|
|
105
|
+
verdict = `${behind} commit(s) waiting on the remote — pull, then ship`; colour = C.yellow; problems++;
|
|
106
|
+
} else {
|
|
107
|
+
verdict = "live matches your clone"; colour = C.green;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
if (liveInfo) {
|
|
111
|
+
bits.push(`live ${short(liveInfo.sha)}${liveInfo.version ? ` v${liveInfo.version}` : ""}`);
|
|
112
|
+
if (liveInfo.publishedBy) bits.push(`by ${liveInfo.publishedBy}`);
|
|
113
|
+
}
|
|
114
|
+
if (dir) bits.push(`local ${short(head)}${localDirty ? "*" : ""}`);
|
|
115
|
+
if (remote && remote !== head) bits.push(`origin/main ${short(remote)}`);
|
|
116
|
+
|
|
117
|
+
console.log(` ${colour}${id.padEnd(16)}${verdict}${C.off}`);
|
|
118
|
+
console.log(` ${C.dim}${" ".repeat(16)}${bits.join(" · ")}${C.off}`);
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
const eng = stamp.engine || {};
|
|
122
|
+
console.log("");
|
|
123
|
+
console.log(` ${C.dim}engine chrome ${eng.sha ? eng.sha.slice(0, 12) : "—"}` +
|
|
124
|
+
`${eng.version ? ` (v${eng.version})` : ""}${eng.publishedAt ? ` · shipped ${eng.publishedAt}` : ""}${C.off}`);
|
|
125
|
+
|
|
126
|
+
// ── who is working where, right now ─────────────────────────────────────────
|
|
127
|
+
//
|
|
128
|
+
// `F-presence-marks`. The three numbers above answer "is what I have what is live"; they
|
|
129
|
+
// cannot answer "is somebody else in here", and that is the question that decides whether
|
|
130
|
+
// the next hour of work is going to be merged or forked.
|
|
131
|
+
//
|
|
132
|
+
// NEEDS A TOKEN and does not ask for one. `status` has always been the command that runs
|
|
133
|
+
// with nothing configured — the build stamp is public — so a missing credential quietly
|
|
134
|
+
// costs the marks section and nothing else. It affects the exit code in no way: marks
|
|
135
|
+
// refuse nothing, and a mark is not a problem.
|
|
136
|
+
const markToken = resolveToken(origin);
|
|
137
|
+
if (markToken) {
|
|
138
|
+
const marks = await fetchMarks(apiClient(origin, markToken));
|
|
139
|
+
if (marks.length) {
|
|
140
|
+
console.log("");
|
|
141
|
+
console.log(` ${C.dim}being worked on right now${C.off}`);
|
|
142
|
+
for (const m of marks) console.log(` ${C.dim} ${markLine(m)}${C.off}`);
|
|
143
|
+
}
|
|
144
|
+
} else {
|
|
145
|
+
// The one thing a fresh agent needs to know and has no other way to learn: this machine
|
|
146
|
+
// holds no token, and the way to get one is pairing, not a password. Same words as the
|
|
147
|
+
// instance's own /llms.txt. Costs nothing here — status never needed the token.
|
|
148
|
+
console.log("");
|
|
149
|
+
console.log(` ${C.dim}not paired with ${origin}. Publishing from here needs a token; get one without a password:${C.off}`);
|
|
150
|
+
console.log(` ${C.dim} augur connect --origin ${origin} (the owner approves a code in a signed-in browser)${C.off}`);
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
// ── drafts open on this machine (docs/drafts-that-land.md §4) ────────────────
|
|
154
|
+
// Read from the machine's registry, so it costs nothing; who else is on each unit is asked
|
|
155
|
+
// of the instance when a token is at hand, and the report stands without it.
|
|
156
|
+
{
|
|
157
|
+
const mine = registryList().filter((e) => !e.readOnly);
|
|
158
|
+
if (mine.length) {
|
|
159
|
+
console.log("");
|
|
160
|
+
console.log(` ${C.dim}drafts open on this machine${C.off}`);
|
|
161
|
+
const presence = {};
|
|
162
|
+
for (const unit of new Set(mine.map((e) => e.unit))) {
|
|
163
|
+
const e = mine.find((x) => x.unit === unit);
|
|
164
|
+
const tok = resolveToken(e.origin);
|
|
165
|
+
if (!tok) continue;
|
|
166
|
+
try {
|
|
167
|
+
const p = await unitClient({ origin: e.origin, token: tok, space: "", session: "" }).presence(unit);
|
|
168
|
+
if (p && p.drafts) presence[unit] = p.drafts;
|
|
169
|
+
} catch (e2) { /* the report stands without presence */ }
|
|
170
|
+
}
|
|
171
|
+
for (const line of draftsReport(mine, presence)) console.log(` ${C.dim} ${line}${C.off}`);
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
// Exit code is the answer, so this can gate a script: 0 = everything live is what
|
|
176
|
+
// its clone says it should be.
|
|
177
|
+
process.exit(problems ? 1 : 0);
|
package/scripts/sync.mjs
ADDED
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
// augur sync — fold what landed on main since this draft opened into the draft. One-sided
|
|
3
|
+
// changes are taken; a file changed on both sides is merged where the lines do not overlap
|
|
4
|
+
// and left to you where they do (theirs is written under .augur/theirs/). Nothing is guessed.
|
|
5
|
+
import { resolveOrigin, resolveToken } from "./lib/store.mjs";
|
|
6
|
+
import { readState, unitClient, doSync, THEIRS_DIR } from "./lib/draft.mjs";
|
|
7
|
+
|
|
8
|
+
const log = (m) => console.error(`\x1b[35m[sync]\x1b[0m ${m}`);
|
|
9
|
+
const die = (m) => { console.error(`\x1b[31m[sync]\x1b[0m ${m}`); process.exit(1); };
|
|
10
|
+
const dir = process.cwd();
|
|
11
|
+
const st = readState(dir);
|
|
12
|
+
if (!st) die("not a draft folder — run `augur open <prototype>` first.");
|
|
13
|
+
const origin = st.origin || resolveOrigin();
|
|
14
|
+
const token = resolveToken(origin);
|
|
15
|
+
if (!token) die("no publish token — run `augur connect` once.");
|
|
16
|
+
const client = unitClient({ origin, token, space: st.space, session: st.session });
|
|
17
|
+
const r = await doSync({ client, dir });
|
|
18
|
+
if (!r.ok) die(`sync refused: ${r.error || r.status}`);
|
|
19
|
+
for (const f of r.taken) log(`took theirs ${f}`);
|
|
20
|
+
for (const f of r.merged) log(`merged ${f}`);
|
|
21
|
+
for (const c of r.conflicts) {
|
|
22
|
+
log(`OVERLAP ${c.rel} — yours stays in place, theirs is at ${THEIRS_DIR}/${c.rel}`);
|
|
23
|
+
for (const h of c.hunks) log(` lines ${h.baseStart + 1}-${h.baseEnd}: yours ${JSON.stringify(h.mine.join("\n")).slice(0, 80)} · theirs ${JSON.stringify(h.theirs.join("\n")).slice(0, 80)}`);
|
|
24
|
+
}
|
|
25
|
+
log(`draft now based on revision ${r.mainRevision}${r.conflicts.length ? " — fold the overlaps in, check the draft address, then land" : " — check the draft address, then land"}`);
|
|
26
|
+
console.log(`${origin}${st.address}`);
|
|
27
|
+
if (r.conflicts.length) process.exit(2);
|