@helix3/helix-cli 0.1.20-helix3.383 → 0.1.20-helix3.385
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 +2 -0
- package/dist/index.js +96 -0
- package/dist/index.js.map +1 -1
- package/dist/tsconfig.build.tsbuildinfo +1 -1
- package/dist/vehicle/mintAddOn.d.ts +84 -0
- package/dist/vehicle/mintAddOn.js +198 -0
- package/dist/vehicle/mintAddOn.js.map +1 -0
- package/dist/vehicle/mintVehicle.d.ts +146 -0
- package/dist/vehicle/mintVehicle.js +356 -0
- package/dist/vehicle/mintVehicle.js.map +1 -0
- package/dist/visualQa/command.js +1 -1
- package/dist/visualQa/command.js.map +1 -1
- package/dist/visualQa/contactSheet.d.ts +2 -0
- package/dist/visualQa/contactSheet.js +57 -15
- package/dist/visualQa/contactSheet.js.map +1 -1
- package/dist/visualQa/evidenceOverlay.d.ts +74 -0
- package/dist/visualQa/evidenceOverlay.js +268 -0
- package/dist/visualQa/evidenceOverlay.js.map +1 -0
- package/dist/visualQa/vehicle.js +31 -5
- package/dist/visualQa/vehicle.js.map +1 -1
- package/dist/visualQa/vehicleOccupants.d.ts +2 -1
- package/dist/visualQa/vehicleOccupants.js +10 -2
- package/dist/visualQa/vehicleOccupants.js.map +1 -1
- package/dist/visualQa/vehiclePenetration.d.ts +2 -0
- package/dist/visualQa/vehiclePenetration.js +1 -0
- package/dist/visualQa/vehiclePenetration.js.map +1 -1
- package/dist/visualQa/vehicleProbe.d.ts +1 -1
- package/dist/visualQa/vehicleProbe.js +14 -0
- package/dist/visualQa/vehicleProbe.js.map +1 -1
- package/docs/visual-qa.md +15 -10
- package/package.json +1 -1
- package/plugins/beamng-vehicle/bin/__pycache__/beamng_abs.cpython-312.pyc +0 -0
- package/plugins/beamng-vehicle/bin/__pycache__/beamng_audio.cpython-312.pyc +0 -0
- package/plugins/beamng-vehicle/bin/__pycache__/beamng_engine.cpython-312.pyc +0 -0
- package/plugins/beamng-vehicle/bin/__pycache__/beamng_expression.cpython-312.pyc +0 -0
- package/plugins/beamng-vehicle/bin/__pycache__/beamng_jbeam.cpython-312.pyc +0 -0
- package/plugins/beamng-vehicle/bin/__pycache__/beamng_materials.cpython-312.pyc +0 -0
- package/plugins/beamng-vehicle/bin/__pycache__/test_beamng_engine.cpython-312.pyc +0 -0
package/README.md
CHANGED
|
@@ -47,6 +47,8 @@ The token is stored in `~/.helix/credentials.json` (mode `600`). It's sent as
|
|
|
47
47
|
| `helix list` | List your worlds. |
|
|
48
48
|
| `helix vehicle simulate <dir\|vehicle-package.json> [--item <id>] [--spec <file>] [--offline] [--json]` | Drive the package offline with the platform's **own** engine instrument (the runtime `^0.3` serves today, cached by sha; offline = last cached, labelled) and judge 0-100 km/h, 0-60 mph, quarter mile, top speed, 100-0 km/h / 60-0 mph braking, skidpad g, turbo lag and the rest pose against the package `targets` and `--spec`. Exit `0` pass, `1` a figure out of tolerance, `2` could not simulate. See [docs/vehicle-simulate.md](docs/vehicle-simulate.md). |
|
|
49
49
|
| `helix vehicle validate <vehicle-package.json> [--glb <model.glb>] [--no-simulate] [--json]` | One-second local gate for a hand-authored Universal Vehicle, run before Package publication. Checks the package against the engine's own validator (vendored, pinned to an engine commit), the engine publish gate, the backend pin requirements, `groundToBodyOrigin` vs `wheelRadius + staticRideHeight`, and the `componentBuild` digest; with `--glb` also resolves the four wheel nodes, checks each wheel node's origin is at its hub (`WHEEL_PIVOT_NOT_AT_HUB`), the +X-left / +Z-forward frame, the vehicle publish budgets the articulation nodes and the add-on host manifest (`asset.extras.HELIX_vehicle`); drives packages that declare `targets` (`helix vehicle simulate`). Exit `0` no errors, `1` errors, `2` unreadable input. See [Vehicle validate](#vehicle-validate). |
|
|
50
|
+
| `helix vehicle publish <dir> --content-rating <r> [--item <id> --package-version <v> --reason <t>] [--json]` | Package-first vehicle publication: validate, upload the model and samples, seal a public Vehicle Package (root pins the model; `publish.json` `hostGrantExtensions` sealed beside it), make the Item from that exact Version, read back pin, identity, audio and the host board (sockets, tunable paths). Resumable; `--item` stages a new Version and moves the car. Exit `0`/`1`/`2`. See [docs/vehicle-publish.md](docs/vehicle-publish.md). |
|
|
51
|
+
| `helix vehicle addon publish <dir> --content-rating <r> [--json]` | Package-first vehicle add-on publication: the full `vehicle addon check`, seal a public addon Package (a tune-only part seals no model), make the Item, read back pin, backend fit and each host's add-on rail. Exit `0`/`1`/`2`. |
|
|
50
52
|
| `helix vehicle preview [<dir-or-package.json>] [--glb <model.glb>] [--addon <dir>]… [--item <id>] [--tolerance-cm <cm>] [--out <dir>] [--proxy-item <id>] [--json]` | Render a vehicle that is **not published yet** headless in the real runtime (hosted test grounds, Try Now through a published proxy vehicle whose car is swapped for your package + GLB, served from disk; nothing uploaded or recorded) and measure it: body-origin height against the declared `groundToBodyOrigin` (the number that locks at first mint), wheels on their hubs, arch clearance, rolling radius vs `wheelRadius`, steering, doors, seats. Prints a numeric summary with PASS/FAIL per check and writes frames, a contact sheet, `bundle.json` and `preview.json`. Boards with the candidate's own seat ids. With `--addon <dir>` (repeatable) it previews unpublished vehicle **add-ons** instead: fits each to the candidate car or a published car and measures the drawn geometry in world space against its anchor (wheels within 1 cm of each hub, socket/host-framed parts at their mount, not at the car's origin; tune-only ops read back from the live tuning). Exit `0` pass, `1` fail, `2` could not measure. See [docs/vehicle-preview.md](docs/vehicle-preview.md). |
|
|
51
53
|
| `helix continuum publish-glb <mesh.glb> --title <t> [--package-type asset\|character] [--offer marketplace\|world --price-lix <n> --content-rating <rating>]` | Seal a Package first; optional offer makes it ownable. See [Package-first GLB publication](#package-first-glb-publication). |
|
|
52
54
|
| `helix continuum make-item --package-id <id> --package-version <v> --manifest-cid <cid> --content-rating <rating> [--offer marketplace\|world --price-lix <n>]` | Project one exact sealed Package Version into an Item, with an optional first offer. |
|
package/dist/index.js
CHANGED
|
@@ -862,6 +862,102 @@ vehicleAddOnCommand
|
|
|
862
862
|
process.exitCode = 2;
|
|
863
863
|
}
|
|
864
864
|
});
|
|
865
|
+
// ── vehicle publication (Package-first): seal the Package, make the Item, read it back ─────────────────────────────
|
|
866
|
+
/** The deps `vehicle publish` / `vehicle addon publish` share: object upload, Package seal and make-item. */
|
|
867
|
+
async function vehicleMintDeps() {
|
|
868
|
+
const base = await vehicleContinuumDeps();
|
|
869
|
+
const { makeItemFromPackage } = await Promise.resolve().then(() => __importStar(require('./publications')));
|
|
870
|
+
const makeItem = async (input) => {
|
|
871
|
+
const receipt = await makeItemFromPackage({
|
|
872
|
+
packagePin: input.packagePin, intentId: input.intentId, contentRating: input.contentRating,
|
|
873
|
+
title: input.title, description: input.description, tags: input.tags,
|
|
874
|
+
}, base.creds);
|
|
875
|
+
return receipt;
|
|
876
|
+
};
|
|
877
|
+
return { ...base, makeItem };
|
|
878
|
+
}
|
|
879
|
+
vehicleCommand
|
|
880
|
+
.command('publish')
|
|
881
|
+
.description('Publish a vehicle package directory: validate (package, GLB, host manifest, audio), upload the model and samples, seal a '
|
|
882
|
+
+ 'public Vehicle Package whose root pins them, make the vehicle Item from that exact Version, and read it back (pin, package '
|
|
883
|
+
+ 'identity, mesh pin, every audio URL, and the host board: hostKind vehicle, sockets, tunable paths). Resumable from '
|
|
884
|
+
+ '<dir>/.helix-publish/ledger.json. With --item: seal a STAGED new Version of that car and move it (visual QA gates the move). '
|
|
885
|
+
+ 'Directory: vehicle-package.json + model.glb (asset.extras.HELIX_vehicle with sockets) + WAVs; optional publish.json '
|
|
886
|
+
+ '{ title, description, tags, version, contentRating, provenance, hostGrantExtensions }. '
|
|
887
|
+
+ 'Exit 0 = published and verified, 1 = a check or read-back failed, 2 = could not run')
|
|
888
|
+
.argument('<dir>', 'the vehicle package directory')
|
|
889
|
+
.option('--glb <file>', 'the drawn model, when the directory holds more than one .glb')
|
|
890
|
+
.option('--title <title>', 'Item and Package title (default: publish.json title, else the package displayName)')
|
|
891
|
+
.option('--description <text>', 'Item description')
|
|
892
|
+
.option('--tags <a,b,c>', 'Item tags')
|
|
893
|
+
.option('--content-rating <rating>', 'creator-attested rating for a new Item: everyone, teen, mature or adult (or publish.json contentRating)')
|
|
894
|
+
.option('--package-version <semver>', 'the Package Version to seal (default 1.0.0; required with --item)')
|
|
895
|
+
.option('--item <id>', 'publish a NEW VERSION of this existing vehicle Item instead of minting one')
|
|
896
|
+
.option('--reason <text>', 'with --item: the version move reason (1-500 chars, audited)')
|
|
897
|
+
.option('--out <dir>', 'ledger, sealed root, descriptor and receipts (default <dir>/.helix-publish)')
|
|
898
|
+
.option('--no-simulate', 'skip the drive (by default a package with `targets` is driven by the platform\'s engine instrument, exactly as `vehicle validate`, and every figure outside its tolerance refuses the publish)')
|
|
899
|
+
.option('--offline', 'drive with the last cached engine runtime; never fetch')
|
|
900
|
+
.option('--dry-run', 'validate and check audio only; nothing is uploaded')
|
|
901
|
+
.option('--json', 'print the machine-readable result')
|
|
902
|
+
.action(async (dir, opts) => {
|
|
903
|
+
try {
|
|
904
|
+
const mint = await Promise.resolve().then(() => __importStar(require('./vehicle/mintVehicle')));
|
|
905
|
+
const deps = opts.dryRun ? null : await vehicleMintDeps();
|
|
906
|
+
const creds = deps?.creds ?? requireAuth();
|
|
907
|
+
const unreachable = async () => { throw new Error('dry run: no network writes'); };
|
|
908
|
+
const result = await mint.mintVehicle({
|
|
909
|
+
dir, glb: opts.glb, title: opts.title, description: opts.description, tags: opts.tags ? (0, lib_1.parseTags)(opts.tags) : undefined,
|
|
910
|
+
contentRating: opts.contentRating, version: opts.packageVersion, itemId: opts.item, reason: opts.reason, out: opts.out, dryRun: opts.dryRun,
|
|
911
|
+
simulate: opts.simulate, offline: opts.offline,
|
|
912
|
+
}, creds, deps ? {
|
|
913
|
+
api: deps.api, objects: deps.objects, publishPackage: deps.publishPackage, makeItem: deps.makeItem,
|
|
914
|
+
onProgress: (m) => { if (!opts.json)
|
|
915
|
+
console.log(`· ${m}`); },
|
|
916
|
+
} : {
|
|
917
|
+
api: { request: unreachable }, objects: { putObjectFromFile: unreachable }, publishPackage: unreachable, makeItem: unreachable,
|
|
918
|
+
});
|
|
919
|
+
printVehicleJsonOr(opts.json, result, () => console.log(mint.formatVehicleMint(result)));
|
|
920
|
+
if (!result.ok)
|
|
921
|
+
process.exitCode = 1;
|
|
922
|
+
}
|
|
923
|
+
catch (error) {
|
|
924
|
+
process.stderr.write(`${error instanceof lib_1.ApiError ? error.render() : `✖ ${error instanceof Error ? error.message : String(error)}`}\n`);
|
|
925
|
+
process.exitCode = 2;
|
|
926
|
+
}
|
|
927
|
+
});
|
|
928
|
+
vehicleAddOnCommand
|
|
929
|
+
.command('publish')
|
|
930
|
+
.description('Publish a vehicle add-on directory: the full `vehicle addon check` (drive effect measured), upload the model, seal a public addon '
|
|
931
|
+
+ 'Package (root: the helix.vehicle-addon-definition/1 JSON; a tune-only part seals no model), make the add-on Item from that exact '
|
|
932
|
+
+ 'Version, and read it back: pinned, the backend fit lists every host, every host\'s add-on rail lists it. No offer is opened. '
|
|
933
|
+
+ 'Resumable from <dir>/.helix-publish/ledger.json. Exit 0 = published and verified, 1 = a check or read-back failed, 2 = could not run')
|
|
934
|
+
.argument('<dir>', 'the add-on directory (addon.json + model.glb; no model for a tune-only part)')
|
|
935
|
+
.option('--glb <file>', 'the add-on model, when the directory holds more than one .glb')
|
|
936
|
+
.option('--content-rating <rating>', 'creator-attested rating: everyone, teen, mature or adult (or addon.json contentRating)')
|
|
937
|
+
.option('--out <dir>', 'ledger, definition, descriptor and receipts (default <dir>/.helix-publish)')
|
|
938
|
+
.option('--no-measure', 'skip the drive-effect measurement')
|
|
939
|
+
.option('--dry-run', 'run the check only; nothing is uploaded')
|
|
940
|
+
.option('--json', 'print the machine-readable result')
|
|
941
|
+
.action(async (dir, opts) => {
|
|
942
|
+
try {
|
|
943
|
+
const addon = await Promise.resolve().then(() => __importStar(require('./vehicle/addon')));
|
|
944
|
+
const mint = await Promise.resolve().then(() => __importStar(require('./vehicle/mintAddOn')));
|
|
945
|
+
const deps = await vehicleMintDeps();
|
|
946
|
+
const result = await mint.mintVehicleAddOn({ dir, glb: opts.glb, contentRating: opts.contentRating, out: opts.out, dryRun: opts.dryRun }, deps.creds, {
|
|
947
|
+
api: deps.api, objects: deps.objects, publishPackage: deps.publishPackage, makeItem: deps.makeItem,
|
|
948
|
+
measureDrive: opts.measure === false ? undefined : await vehicleDriveMeasure(deps.creds.apiUrl),
|
|
949
|
+
onProgress: (m) => { if (!opts.json)
|
|
950
|
+
console.log(`· ${m}`); },
|
|
951
|
+
});
|
|
952
|
+
printVehicleJsonOr(opts.json, result, () => console.log(mint.formatAddOnMint(result, addon.formatAddOnReport(result.check))));
|
|
953
|
+
if (!result.ok)
|
|
954
|
+
process.exitCode = 1;
|
|
955
|
+
}
|
|
956
|
+
catch (error) {
|
|
957
|
+
process.stderr.write(`${error instanceof lib_1.ApiError ? error.render() : `✖ ${error instanceof Error ? error.message : String(error)}`}\n`);
|
|
958
|
+
process.exitCode = 2;
|
|
959
|
+
}
|
|
960
|
+
});
|
|
865
961
|
// Validate a token against the API, then persist it. Shared by the browser
|
|
866
962
|
// flow and the --token (CI/headless) path.
|
|
867
963
|
async function finishLogin(apiUrl, token) {
|