@secondlayer/cli 23.3.0 → 23.4.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/dist/cli.js +71 -95
- package/dist/cli.js.map +8 -8
- package/package.json +3 -3
package/dist/cli.js
CHANGED
|
@@ -29357,6 +29357,12 @@ function inspectSourceGitState(absPath) {
|
|
|
29357
29357
|
}
|
|
29358
29358
|
return { kind: "clean" };
|
|
29359
29359
|
}
|
|
29360
|
+
function uncommittedSourceWarning(state, file) {
|
|
29361
|
+
if (state.kind !== "untracked" && state.kind !== "modified")
|
|
29362
|
+
return;
|
|
29363
|
+
const reason = state.kind === "untracked" ? "not tracked by git" : "modified with uncommitted changes";
|
|
29364
|
+
return `${file} is ${reason}, so this deploy's only copy is the database row. Commit it to keep a copy.`;
|
|
29365
|
+
}
|
|
29360
29366
|
var init_git_status = () => {};
|
|
29361
29367
|
|
|
29362
29368
|
// src/lib/merge-print-subgraph.ts
|
|
@@ -29990,7 +29996,6 @@ import {
|
|
|
29990
29996
|
} from "node:fs";
|
|
29991
29997
|
import { basename, dirname as dirname5, extname, join as join7, relative, resolve as resolve5 } from "node:path";
|
|
29992
29998
|
import { fileURLToPath as fileURLToPath3 } from "node:url";
|
|
29993
|
-
import { confirm as confirm2 } from "@inquirer/prompts";
|
|
29994
29999
|
import {
|
|
29995
30000
|
generatePrintPayloadTypes,
|
|
29996
30001
|
generatePrintSchemaSubgraph as generatePrintSchemaSubgraph2,
|
|
@@ -30004,31 +30009,11 @@ import {
|
|
|
30004
30009
|
deriveVerification as deriveVerification2,
|
|
30005
30010
|
isDeterminismViolation
|
|
30006
30011
|
} from "@secondlayer/subgraphs/verification";
|
|
30007
|
-
async function
|
|
30008
|
-
|
|
30009
|
-
|
|
30010
|
-
|
|
30011
|
-
|
|
30012
|
-
const code = err?.code;
|
|
30013
|
-
const missingSdk = (code === "ERR_MODULE_NOT_FOUND" || msg.includes("ERR_MODULE_NOT_FOUND")) && msg.includes("@secondlayer/subgraphs");
|
|
30014
|
-
if (!missingSdk)
|
|
30015
|
-
throw err;
|
|
30016
|
-
warn("Missing dependency: @secondlayer/subgraphs");
|
|
30017
|
-
const install = await confirm2({
|
|
30018
|
-
message: "Install with `bun add @secondlayer/subgraphs`?",
|
|
30019
|
-
default: true
|
|
30020
|
-
});
|
|
30021
|
-
if (!install)
|
|
30022
|
-
throw err;
|
|
30023
|
-
await new Promise((res, rej) => {
|
|
30024
|
-
const child = spawn2("bun", ["add", "@secondlayer/subgraphs"], {
|
|
30025
|
-
stdio: "inherit"
|
|
30026
|
-
});
|
|
30027
|
-
child.on("error", rej);
|
|
30028
|
-
child.on("exit", (c) => c === 0 ? res() : rej(new Error(`bun add exit ${c}`)));
|
|
30029
|
-
});
|
|
30030
|
-
return await import(absPath);
|
|
30031
|
-
}
|
|
30012
|
+
async function loadSubgraphDefinition(source, fileName) {
|
|
30013
|
+
const { bundleSubgraphCode } = await import("@secondlayer/bundler");
|
|
30014
|
+
const bundled = await bundleSubgraphCode(source, { fileName });
|
|
30015
|
+
const url = `data:text/javascript;base64,${Buffer.from(bundled.handlerCode, "utf8").toString("base64")}`;
|
|
30016
|
+
return { mod: await import(url), bundled };
|
|
30032
30017
|
}
|
|
30033
30018
|
async function typecheckHandler(absPath) {
|
|
30034
30019
|
await new Promise((res, rej) => {
|
|
@@ -30055,6 +30040,15 @@ function parseStartBlockOption(value) {
|
|
|
30055
30040
|
}
|
|
30056
30041
|
return parsed;
|
|
30057
30042
|
}
|
|
30043
|
+
function genesisWarning(startBlock) {
|
|
30044
|
+
if (startBlock === undefined) {
|
|
30045
|
+
return "No startBlock: the first deploy backfills from genesis.";
|
|
30046
|
+
}
|
|
30047
|
+
if (startBlock <= 1) {
|
|
30048
|
+
return `startBlock ${startBlock}: the first deploy backfills all history from genesis.`;
|
|
30049
|
+
}
|
|
30050
|
+
return null;
|
|
30051
|
+
}
|
|
30058
30052
|
function collectPinnedPrintSources(sources) {
|
|
30059
30053
|
const out = [];
|
|
30060
30054
|
for (const [sourceName, raw] of Object.entries(sources ?? {})) {
|
|
@@ -30542,8 +30536,7 @@ Try --trait sip-010 or \`subgraphs scaffold ${opts.fromContract}\` for ABI calls
|
|
|
30542
30536
|
if (opts.fromContract) {
|
|
30543
30537
|
info(`Schema inferred from ${opts.fromContract} print events (${opts.tablePerTopic ? "table per topic" : "single wide table"})`);
|
|
30544
30538
|
}
|
|
30545
|
-
info(`Next:
|
|
30546
|
-
note(" deploy refuses an unstaged file unless you pass --allow-uncommitted: a staged copy is the one git can recover.");
|
|
30539
|
+
info(`Next: secondlayer subgraphs deploy subgraphs/${name}.ts`);
|
|
30547
30540
|
});
|
|
30548
30541
|
subgraphs.command("add <file>").description("Merge another contract's observed print sources into an existing subgraph file").requiredOption("--from-contract <contractId>", "Contract whose print schema to merge (requires network)").option("--table-per-topic", "One table per print topic instead of a single wide table for the added contract").addHelpText("after", `
|
|
30549
30542
|
Adds sources/schema/handlers for a second (or Nth) contract into an existing
|
|
@@ -30650,10 +30643,10 @@ Stopped watching.`);
|
|
|
30650
30643
|
});
|
|
30651
30644
|
await new Promise(() => {});
|
|
30652
30645
|
});
|
|
30653
|
-
subgraphs.command("deploy <file>").alias("update").description("Deploy a subgraph definition file (alias: update — deploy is create-or-update)").option("--start-block <n>", "Override the subgraph definition startBlock for this deploy").option("--tip-first", "Go live at chain tip immediately; history backfills in the background (handlers may only insert, upsert and delete; update, increment and row reads are refused)").option("--dry-run", "Validate and preview deploy without writing changes").option("-y, --yes", "Skip the reindex confirmation prompt").option("--strict", "Run `tsc --noEmit` against the handler before deploy (slower; catches TS type errors)").option("--allow-uncommitted", "
|
|
30654
|
-
|
|
30655
|
-
|
|
30656
|
-
--allow-uncommitted to
|
|
30646
|
+
subgraphs.command("deploy <file>").alias("update").description("Deploy a subgraph definition file (alias: update — deploy is create-or-update)").option("--start-block <n>", "Override the subgraph definition startBlock for this deploy").option("--tip-first", "Go live at chain tip immediately; history backfills in the background (handlers may only insert, upsert and delete; update, increment and row reads are refused)").option("--dry-run", "Validate and preview deploy without writing changes").option("-y, --yes", "Skip the reindex confirmation prompt").option("--strict", "Run `tsc --noEmit` against the handler before deploy (slower; catches TS type errors)").option("--allow-uncommitted", "Don't warn when the source file isn't committed in git").addHelpText("after", `
|
|
30647
|
+
If the source file isn't committed in git, deploy warns that the deployed
|
|
30648
|
+
definition's only copy is the row in the database. It never blocks; pass
|
|
30649
|
+
--allow-uncommitted to silence the warning.
|
|
30657
30650
|
|
|
30658
30651
|
Hosted: set SECONDLAYER_API_KEY and SECONDLAYER_API_URL=https://api.secondlayer.tools.
|
|
30659
30652
|
Hostable sources are event filters and contract_call/contract_deploy; anything else
|
|
@@ -30662,28 +30655,10 @@ deploy does not backfill from genesis.`).action(async (file, options) => {
|
|
|
30662
30655
|
try {
|
|
30663
30656
|
const absPath = resolve5(file);
|
|
30664
30657
|
if (!options.dryRun) {
|
|
30665
|
-
if (options.allowUncommitted) {
|
|
30666
|
-
|
|
30667
|
-
|
|
30668
|
-
|
|
30669
|
-
if (gitState.kind === "untracked" || gitState.kind === "modified") {
|
|
30670
|
-
const reason = gitState.kind === "untracked" ? "not tracked by git" : "modified with uncommitted changes";
|
|
30671
|
-
const message = `${file} is ${reason}. Deploy it and the only copy of this definition is a row in the database.`;
|
|
30672
|
-
if (process.stdin.isTTY) {
|
|
30673
|
-
warn(message);
|
|
30674
|
-
const confirmed = await confirm2({
|
|
30675
|
-
message: "Deploy anyway?",
|
|
30676
|
-
default: false
|
|
30677
|
-
});
|
|
30678
|
-
if (!confirmed) {
|
|
30679
|
-
info("Nothing was deployed.");
|
|
30680
|
-
process.exit(0);
|
|
30681
|
-
}
|
|
30682
|
-
} else {
|
|
30683
|
-
error(`${message} Stage it with \`git add ${file}\`, or pass --allow-uncommitted.`);
|
|
30684
|
-
process.exit(1);
|
|
30685
|
-
}
|
|
30686
|
-
}
|
|
30658
|
+
if (!options.allowUncommitted) {
|
|
30659
|
+
const advice = uncommittedSourceWarning(inspectSourceGitState(absPath), file);
|
|
30660
|
+
if (advice)
|
|
30661
|
+
warn(advice);
|
|
30687
30662
|
}
|
|
30688
30663
|
}
|
|
30689
30664
|
const config = await loadConfig2();
|
|
@@ -30697,18 +30672,28 @@ deploy does not backfill from genesis.`).action(async (file, options) => {
|
|
|
30697
30672
|
await typecheckHandler(absPath);
|
|
30698
30673
|
}
|
|
30699
30674
|
info(`Loading subgraph from ${absPath}`);
|
|
30700
|
-
const mod = await loadSubgraphWithDepCheck(absPath);
|
|
30701
|
-
const def = mod.default ?? mod;
|
|
30702
|
-
const effectiveDef = {
|
|
30703
|
-
...startBlock === undefined ? def : { ...def, startBlock },
|
|
30704
|
-
...options.tipFirst ? { backfillMode: "concurrent" } : {}
|
|
30705
|
-
};
|
|
30706
30675
|
const { validateSubgraphDefinition } = await import("@secondlayer/subgraphs/validate");
|
|
30707
30676
|
const { readFile } = await import("node:fs/promises");
|
|
30708
30677
|
const derived = config.network !== "local" ? await withDerivedAbis(await readFile(absPath, "utf8")) : undefined;
|
|
30709
30678
|
for (const name of Object.keys(derived?.abis ?? {})) {
|
|
30710
30679
|
info(`Using the deployed contract's abi for source "${name}"`);
|
|
30711
30680
|
}
|
|
30681
|
+
const source = derived?.source ?? await readFile(absPath, "utf8");
|
|
30682
|
+
const { mod, bundled } = await loadSubgraphDefinition(source, relative(process.cwd(), absPath));
|
|
30683
|
+
const def = mod.default ?? mod;
|
|
30684
|
+
const authored = {
|
|
30685
|
+
...def,
|
|
30686
|
+
sources: Object.fromEntries(Object.entries(def.sources ?? {}).map(([k, v]) => {
|
|
30687
|
+
if (!derived?.abis[k])
|
|
30688
|
+
return [k, v];
|
|
30689
|
+
const { abi: _abi, ...rest } = v;
|
|
30690
|
+
return [k, rest];
|
|
30691
|
+
}))
|
|
30692
|
+
};
|
|
30693
|
+
const effectiveDef = {
|
|
30694
|
+
...startBlock === undefined ? authored : { ...authored, startBlock },
|
|
30695
|
+
...options.tipFirst ? { backfillMode: "concurrent" } : {}
|
|
30696
|
+
};
|
|
30712
30697
|
const validated = validateSubgraphDefinition(derived && Object.keys(derived.abis).length > 0 ? {
|
|
30713
30698
|
...effectiveDef,
|
|
30714
30699
|
sources: Object.fromEntries(Object.entries(effectiveDef.sources).map(([k, v]) => [
|
|
@@ -30716,16 +30701,11 @@ deploy does not backfill from genesis.`).action(async (file, options) => {
|
|
|
30716
30701
|
derived.abis[k] ? { ...v, abi: derived.abis[k] } : v
|
|
30717
30702
|
]))
|
|
30718
30703
|
} : effectiveDef);
|
|
30719
|
-
|
|
30720
|
-
|
|
30721
|
-
|
|
30704
|
+
const genesis = genesisWarning(effectiveDef.startBlock);
|
|
30705
|
+
if (genesis)
|
|
30706
|
+
warn(genesis);
|
|
30722
30707
|
if (config.network !== "local") {
|
|
30723
30708
|
info(`${dryRun ? "Bundling for remote deploy dry run" : "Bundling for remote deploy"} (${config.network})...`);
|
|
30724
|
-
const source = derived?.source ?? await readFile(absPath, "utf8");
|
|
30725
|
-
const { bundleSubgraphCode } = await import("@secondlayer/bundler");
|
|
30726
|
-
const bundled = await bundleSubgraphCode(source, {
|
|
30727
|
-
fileName: relative(process.cwd(), absPath)
|
|
30728
|
-
});
|
|
30729
30709
|
const handlerCode = bundled.handlerCode;
|
|
30730
30710
|
const localVerification = checkDeterminism(effectiveDef, bundled.findings);
|
|
30731
30711
|
if (dryRun) {
|
|
@@ -30840,16 +30820,7 @@ deploy does not backfill from genesis.`).action(async (file, options) => {
|
|
|
30840
30820
|
await printDeployFooter();
|
|
30841
30821
|
}
|
|
30842
30822
|
} else {
|
|
30843
|
-
|
|
30844
|
-
try {
|
|
30845
|
-
const { bundleSubgraphCode } = await import("@secondlayer/bundler");
|
|
30846
|
-
findings = (await bundleSubgraphCode(await readFile(absPath, "utf8"), {
|
|
30847
|
-
fileName: relative(process.cwd(), absPath)
|
|
30848
|
-
})).findings;
|
|
30849
|
-
} catch {
|
|
30850
|
-
findings = undefined;
|
|
30851
|
-
}
|
|
30852
|
-
const verification = findings ? checkDeterminism(effectiveDef, findings) : undefined;
|
|
30823
|
+
const verification = checkDeterminism(effectiveDef, bundled.findings);
|
|
30853
30824
|
if (dryRun) {
|
|
30854
30825
|
printSubgraphDeployPreview(createSubgraphDeployPreview(validated), {
|
|
30855
30826
|
network: config.network,
|
|
@@ -31892,7 +31863,7 @@ var {
|
|
|
31892
31863
|
// package.json
|
|
31893
31864
|
var package_default = {
|
|
31894
31865
|
name: "@secondlayer/cli",
|
|
31895
|
-
version: "23.
|
|
31866
|
+
version: "23.4.1",
|
|
31896
31867
|
description: "Run a Stacks index on your own hardware — set it up, restore verified history, and keep it current.",
|
|
31897
31868
|
repository: {
|
|
31898
31869
|
type: "git",
|
|
@@ -31943,8 +31914,8 @@ var package_default = {
|
|
|
31943
31914
|
"@secondlayer/scaffold": "^1.6.3",
|
|
31944
31915
|
"@secondlayer/sdk": "^16.2.0",
|
|
31945
31916
|
"@secondlayer/shared": "^15.0.1",
|
|
31946
|
-
"@secondlayer/stacks": "^6.
|
|
31947
|
-
"@secondlayer/subgraphs": "^8.0.
|
|
31917
|
+
"@secondlayer/stacks": "^6.6.0",
|
|
31918
|
+
"@secondlayer/subgraphs": "^8.0.2",
|
|
31948
31919
|
"@secondlayer/verify": "^0.6.1",
|
|
31949
31920
|
esbuild: "^0.28.2",
|
|
31950
31921
|
"smol-toml": "^1.9.1",
|
|
@@ -35867,7 +35838,7 @@ is what makes minting possible without Bitcoin.`).action(async (opts) => {
|
|
|
35867
35838
|
const txid = await client.callContract({
|
|
35868
35839
|
contract,
|
|
35869
35840
|
functionName: "complete-deposit-wrapper",
|
|
35870
|
-
|
|
35841
|
+
args: [
|
|
35871
35842
|
Cl.bufferFromHex(depositTxid),
|
|
35872
35843
|
Cl.uint(0),
|
|
35873
35844
|
Cl.uint(amount),
|
|
@@ -36868,7 +36839,7 @@ init_api_url();
|
|
|
36868
36839
|
init_http();
|
|
36869
36840
|
import { hostname } from "node:os";
|
|
36870
36841
|
import { createInterface } from "node:readline";
|
|
36871
|
-
import { confirm as
|
|
36842
|
+
import { confirm as confirm2, input } from "@inquirer/prompts";
|
|
36872
36843
|
|
|
36873
36844
|
// src/lib/open-browser.ts
|
|
36874
36845
|
import { spawn as spawn3 } from "node:child_process";
|
|
@@ -36951,7 +36922,7 @@ async function shouldContinueLogin(target, options, deps = defaultLoginCheckDeps
|
|
|
36951
36922
|
return false;
|
|
36952
36923
|
}
|
|
36953
36924
|
try {
|
|
36954
|
-
const proceed = await
|
|
36925
|
+
const proceed = await confirm2({
|
|
36955
36926
|
message: "Log in as a different user?",
|
|
36956
36927
|
default: false
|
|
36957
36928
|
});
|
|
@@ -37120,18 +37091,24 @@ async function runLogout() {
|
|
|
37120
37091
|
info(`Not logged in (${target}).`);
|
|
37121
37092
|
return;
|
|
37122
37093
|
}
|
|
37123
|
-
|
|
37124
|
-
|
|
37125
|
-
|
|
37126
|
-
|
|
37127
|
-
|
|
37128
|
-
|
|
37129
|
-
|
|
37130
|
-
|
|
37094
|
+
const isSession = session.token.startsWith("ss-sl_");
|
|
37095
|
+
if (isSession) {
|
|
37096
|
+
try {
|
|
37097
|
+
await httpAt(target, "/api/auth/logout", {
|
|
37098
|
+
method: "POST",
|
|
37099
|
+
bearer: session.token
|
|
37100
|
+
});
|
|
37101
|
+
} catch (err) {
|
|
37102
|
+
if (err instanceof CliHttpError) {
|
|
37103
|
+
warn(`Server logout failed (${err.code}); clearing the local session anyway`);
|
|
37104
|
+
}
|
|
37131
37105
|
}
|
|
37132
37106
|
}
|
|
37133
37107
|
await clearSession(target);
|
|
37134
37108
|
success(`Logged out (${target}).`);
|
|
37109
|
+
if (!isSession) {
|
|
37110
|
+
info("Removed the saved key from this machine. The key stays active; revoke it on the Keys tab.");
|
|
37111
|
+
}
|
|
37135
37112
|
}
|
|
37136
37113
|
function registerLogoutCommand(program) {
|
|
37137
37114
|
program.command("logout").description("Sign this machine out of your Secondlayer account").action(() => runLogout());
|
|
@@ -37698,8 +37675,7 @@ program.hook("preAction", (thisCommand) => {
|
|
|
37698
37675
|
program.addHelpText("after", `
|
|
37699
37676
|
Quickstart:
|
|
37700
37677
|
$ secondlayer subgraphs create my-watcher --from-contract SP....my-contract
|
|
37701
|
-
$
|
|
37702
|
-
$ secondlayer subgraphs deploy subgraphs/my-watcher.ts # or --allow-uncommitted
|
|
37678
|
+
$ secondlayer subgraphs deploy subgraphs/my-watcher.ts
|
|
37703
37679
|
|
|
37704
37680
|
Self-host, from docker/oss in a checkout:
|
|
37705
37681
|
$ secondlayer init --network mainnet
|
|
@@ -37737,5 +37713,5 @@ registerCreditsCommand(program);
|
|
|
37737
37713
|
registerArchiveCommand(program);
|
|
37738
37714
|
program.parse();
|
|
37739
37715
|
|
|
37740
|
-
//# debugId=
|
|
37716
|
+
//# debugId=8047E4F45A72C72F64756E2164756E21
|
|
37741
37717
|
//# sourceMappingURL=cli.js.map
|