@artblocks/abx-cli 0.1.0-alpha.6 → 0.1.0-alpha.8
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/main.js +24 -23
- package/dist/main.js.map +1 -1
- package/dist/update-check.d.ts.map +1 -1
- package/dist/update-check.js +4 -1
- package/dist/update-check.js.map +1 -1
- package/package.json +6 -6
- package/skill/SKILL.md +4 -2
package/dist/main.js
CHANGED
|
@@ -70,7 +70,7 @@ const SCHEMA_CATALOG = 'Types: Bool·Select·Uint256Range·Int256Range·DecimalR
|
|
|
70
70
|
'Select needs options — key:Select[A|B|C]:Auth; a Range takes bounds — key:Uint256Range[0..100]:Auth. ' +
|
|
71
71
|
'A palette collectors set = palette:HexColor:TokenOwner';
|
|
72
72
|
import { uploadAndLocate } from './upload.js';
|
|
73
|
-
import { assertChainId, discoverDeployBlock, deployFactory, deploySeriesFactory, deploySeries, deployOneOfOne, deployRenderer, predictRenderer, predictSeedSource, encodeTag, encodeFieldRenderer, isCodeProject, loadDotEnv, makePublicClient, makeWalletClient, oneOfOneImageAbi, oneOfOneImageFactoryAbi, seriesImageAbi, seriesImageFactoryAbi, abxMetadataRendererAbi, predictClone, probeRpcEndpoints, prepareDeployOneOfOne, prepareDeploySeries, reconstructProject, saltFor, saltGuard, resolveChain, DEFAULT_CHAIN_KEY, normalizeAttributes, parseTraitPairs, METADATA_FIELD as F, METADATA_REPRESENTATION as R, } from '@artblocks/abx-sdk';
|
|
73
|
+
import { assertChainId, discoverDeployBlock, deployFactory, deploySeriesFactory, deploySeries, deployOneOfOne, deployRenderer, predictRenderer, predictSeedSource, encodeTag, encodeFieldRenderer, isCodeProject, loadDotEnv, makePublicClient, makeWalletClient, oneOfOneImageAbi, oneOfOneImageFactoryAbi, seriesImageAbi, seriesImageFactoryAbi, abxMetadataRendererAbi, predictClone, probeRpcEndpoints, prepareDeployOneOfOne, prepareDeploySeries, reconstructProject, saltFor, saltGuard, resolveChain, explorerUrl, DEFAULT_CHAIN_KEY, normalizeAttributes, parseTraitPairs, METADATA_FIELD as F, METADATA_REPRESENTATION as R, } from '@artblocks/abx-sdk';
|
|
74
74
|
import { SelfHostIndexer, SqliteStore } from '@artblocks/abx-indexer';
|
|
75
75
|
import { artContentHash, currentRenderArtifact, generateArt, resolveBaseUrl, startChainWatcher, startTokenApiServer, verifyProject, watchIntervalMs, DEFAULT_PORT, } from '@artblocks/abx-token-api';
|
|
76
76
|
import { ARWEAVE_FREE_UPLOAD_LIMIT, arweaveAddress, arweaveFunding, contentTypeFromPath, hashContent, resolveBackend, turboBalanceForAddress, turboUploadCostUsd, turboUploadWinc } from '@artblocks/abx-storage';
|
|
@@ -80,12 +80,10 @@ import { remoteAddProject, remoteRemoveProject } from './remote.js';
|
|
|
80
80
|
import { buildMigrationPlan, repinNodeCustody, verifyParity } from './migrate.js';
|
|
81
81
|
import { activeBackendId, arweaveKeyFilePath, backendResolution, ensureArweaveJwk, factoryAddress, seriesFactoryAddress, fixedPriceMinterAddress, loadArweaveJwk, loopbackBaseUrl, faucetHint, rendererAddress, storageOptions, storageSignerChoice, } from './config.js';
|
|
82
82
|
const CHAIN = process.env.ABX_CHAIN ?? DEFAULT_CHAIN_KEY;
|
|
83
|
-
// Block explorer base
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
};
|
|
88
|
-
const EXPLORER = EXPLORERS[resolveChain(CHAIN).id] ?? 'https://sepolia.etherscan.io';
|
|
83
|
+
// Block explorer base for the tx/address links the CLI prints. Derived from viem's chain metadata via
|
|
84
|
+
// the SDK (see explorerUrl) rather than a local table — this used to be a hand-maintained map, which is
|
|
85
|
+
// the same shape of bug that had the token-api dashboard sending every Base Sepolia link to Etherscan.
|
|
86
|
+
const EXPLORER = explorerUrl(resolveChain(CHAIN).id);
|
|
89
87
|
// Product dimensions — what you can launch. One concrete contract exists today
|
|
90
88
|
// (the 1/1 image); this table is the seam future implementations slot into, so
|
|
91
89
|
// `abx deploy --type <dimension>` is stable while the contracts grow under it.
|
|
@@ -155,7 +153,7 @@ async function main() {
|
|
|
155
153
|
return;
|
|
156
154
|
}
|
|
157
155
|
// Notify-only "you're behind" nudge (cached, opt-out, stderr — see update-check.ts). Awaited so
|
|
158
|
-
// the notice lands before command output, but it hits the network at most once
|
|
156
|
+
// the notice lands before command output, but it hits the network at most once every 6h and never
|
|
159
157
|
// throws, so it can't break or meaningfully slow a command. Skipped for the pure help path below.
|
|
160
158
|
await maybeNotifyUpdate(flags);
|
|
161
159
|
// SAFETY: --help / -h on ANY command is read-only — print usage, never execute.
|
|
@@ -449,7 +447,7 @@ function refuseMissingFactory(kind, envVar, reason) {
|
|
|
449
447
|
` To deploy your OWN trust anchor instead (private chains, sandboxes — platforms won't recognize its clones), ` +
|
|
450
448
|
`re-run with --bootstrap-factory.`);
|
|
451
449
|
}
|
|
452
|
-
async function ensureFactory(override, allowBootstrap = false) {
|
|
450
|
+
async function ensureFactory(override, allowBootstrap = false, quiet = false) {
|
|
453
451
|
// Resolve the canonical factory from the shipped manifest (flag → env → manifest); on a chain
|
|
454
452
|
// with no entry, deploy a fresh trust anchor and tell the operator how to reuse it.
|
|
455
453
|
const known = factoryAddress(override);
|
|
@@ -459,7 +457,10 @@ async function ensureFactory(override, allowBootstrap = false) {
|
|
|
459
457
|
const code = await publicClient.getCode({ address: known });
|
|
460
458
|
if (code && code !== '0x') {
|
|
461
459
|
if (await isCurrentFactory(publicClient, known)) {
|
|
462
|
-
|
|
460
|
+
// `quiet` suppresses only this happy-path line (the demo resolves the factory without making a
|
|
461
|
+
// teaching moment of it). Bootstrap/mismatch messages below always print — those matter.
|
|
462
|
+
if (!quiet)
|
|
463
|
+
info(`using canonical factory ${EXPLORER}/address/${known}`);
|
|
463
464
|
return known;
|
|
464
465
|
}
|
|
465
466
|
if (!allowBootstrap)
|
|
@@ -1038,7 +1039,13 @@ async function cmdDeploy(flags, serveAfter) {
|
|
|
1038
1039
|
if (signer)
|
|
1039
1040
|
await warnUnfunded(publicClient, signer);
|
|
1040
1041
|
}
|
|
1041
|
-
step
|
|
1042
|
+
// `deploy` surfaces the trust anchor as a step; the demo does NOT. It briefly opened on "only this
|
|
1043
|
+
// factory can make a token that IS an ABX token", which is simply false — anything that follows the
|
|
1044
|
+
// protocol's event spine is an ABX token, and the factory is one way to get there, not the
|
|
1045
|
+
// definition of the thing. Rather than restate it more carefully, the demo skips it: a first-timer
|
|
1046
|
+
// does not need a provenance lecture before they have made anything.
|
|
1047
|
+
if (!serveAfter)
|
|
1048
|
+
step('Trust anchor');
|
|
1042
1049
|
let factory;
|
|
1043
1050
|
if (dryRun) {
|
|
1044
1051
|
const existing = factoryAddress(flags.factory);
|
|
@@ -1051,16 +1058,7 @@ async function cmdDeploy(flags, serveAfter) {
|
|
|
1051
1058
|
info(`would reuse canonical factory ${factory}`);
|
|
1052
1059
|
}
|
|
1053
1060
|
else {
|
|
1054
|
-
factory = await ensureFactory(flags.factory, !!flags['bootstrap-factory']);
|
|
1055
|
-
}
|
|
1056
|
-
// The demo explains what it just did; `deploy` stays terse. The authenticity point is the least
|
|
1057
|
-
// obvious thing about ABX and the easiest to get wrong, so it's worth spelling out — but in plain
|
|
1058
|
-
// language, with the actual term parked in a dim aside for whoever wants to look it up.
|
|
1059
|
-
if (serveAfter) {
|
|
1060
|
-
console.log(` ${g('✦')} anyone can write a contract that ${bold('claims')} to be an ABX token`);
|
|
1061
|
-
console.log(` ${g('✦')} only this one factory can make a token that ${bold('is')} one`);
|
|
1062
|
-
info(dim('so "is this real?" is a yes/no question anyone can ask the chain — not a matter of trusting us'));
|
|
1063
|
-
info(dim(`the factory answers it on-chain: isAbxClone(yourToken) · ${EXPLORER}/address/${factory}`));
|
|
1061
|
+
factory = await ensureFactory(flags.factory, !!flags['bootstrap-factory'], serveAfter);
|
|
1064
1062
|
}
|
|
1065
1063
|
// --onchain-uri: resolve tokenURI/contractURI fully on-chain via the canonical renderer
|
|
1066
1064
|
// (the JSON is assembled from on-chain fields → no resolver needed, ever). The off-chain
|
|
@@ -1437,7 +1435,10 @@ async function cmdDeploy(flags, serveAfter) {
|
|
|
1437
1435
|
if (serveAfter) {
|
|
1438
1436
|
if (state.eventCount > 0)
|
|
1439
1437
|
ok(`read ${bold(String(state.eventCount))} events straight off ${CHAIN} in ${elapsedMs}ms — no API key, no company's server`);
|
|
1440
|
-
|
|
1438
|
+
// "verified real" overstated it in the same way the removed trust-anchor step did — factory
|
|
1439
|
+
// provenance is a fact about how this contract was made, not a verdict on whether a token counts
|
|
1440
|
+
// as ABX. Report the fact.
|
|
1441
|
+
info(`it says: "${state.name}" · owned by ${state.owner} · ${state.isCanonical ? g('made by the canonical factory') : dim('not factory-made')}`);
|
|
1441
1442
|
info(dim(`optional features switched on: ${state.extensions.map((e) => e.name.replace(/^abx\.extension\./, '')).join(' · ') || 'none'}`));
|
|
1442
1443
|
walkthroughSpine(state);
|
|
1443
1444
|
}
|
|
@@ -5498,7 +5499,7 @@ function help() {
|
|
|
5498
5499
|
${g('abx version')} print the installed CLI version
|
|
5499
5500
|
|
|
5500
5501
|
${dim('Run')} ${g('abx <command> --help')} ${dim('for per-command usage. --help / -h never executes — it only prints usage.')}
|
|
5501
|
-
${dim('abx checks npm for a newer release (
|
|
5502
|
+
${dim('abx checks npm for a newer release (every 6h, notify-only). Silence with')} ${g('ABX_NO_UPDATE_CHECK=1')} ${dim('or')} ${g('--no-update-check')}${dim('.')}
|
|
5502
5503
|
`);
|
|
5503
5504
|
}
|
|
5504
5505
|
/** Validate an explicit --salt (a 32-byte hex). Undefined when absent. */
|