@lotics/cli 0.156.6 → 0.162.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/AGENTS.md +2 -2
- package/dist/render_page.js +299 -30
- package/dist/src/cli.js +930 -1765
- package/dist/src/client.d.ts +77 -330
- package/dist/src/client.js +48 -132
- package/docs/cli_reference.md +8 -6
- package/docs/knowledge_docs.md +5 -5
- package/package.json +1 -1
- package/dist/src/package_content_types.d.ts +0 -70
- package/dist/src/package_content_types.js +0 -12
package/dist/src/cli.js
CHANGED
|
@@ -26822,12 +26822,12 @@ var require_tokens = __commonJS({
|
|
|
26822
26822
|
});
|
|
26823
26823
|
}
|
|
26824
26824
|
exports2.assignCategoriesMapProp = assignCategoriesMapProp;
|
|
26825
|
-
function singleAssignCategoriesToksMap(
|
|
26826
|
-
utils_1.forEach(
|
|
26825
|
+
function singleAssignCategoriesToksMap(path14, nextNode) {
|
|
26826
|
+
utils_1.forEach(path14, function(pathNode) {
|
|
26827
26827
|
nextNode.categoryMatchesMap[pathNode.tokenTypeIdx] = true;
|
|
26828
26828
|
});
|
|
26829
26829
|
utils_1.forEach(nextNode.CATEGORIES, function(nextCategory) {
|
|
26830
|
-
var newPath =
|
|
26830
|
+
var newPath = path14.concat(nextNode);
|
|
26831
26831
|
if (!utils_1.contains(newPath, nextCategory)) {
|
|
26832
26832
|
singleAssignCategoriesToksMap(newPath, nextCategory);
|
|
26833
26833
|
}
|
|
@@ -28590,10 +28590,10 @@ var require_interpreter = __commonJS({
|
|
|
28590
28590
|
/** @class */
|
|
28591
28591
|
(function(_super) {
|
|
28592
28592
|
__extends(AbstractNextPossibleTokensWalker2, _super);
|
|
28593
|
-
function AbstractNextPossibleTokensWalker2(topProd,
|
|
28593
|
+
function AbstractNextPossibleTokensWalker2(topProd, path14) {
|
|
28594
28594
|
var _this = _super.call(this) || this;
|
|
28595
28595
|
_this.topProd = topProd;
|
|
28596
|
-
_this.path =
|
|
28596
|
+
_this.path = path14;
|
|
28597
28597
|
_this.possibleTokTypes = [];
|
|
28598
28598
|
_this.nextProductionName = "";
|
|
28599
28599
|
_this.nextProductionOccurrence = 0;
|
|
@@ -28647,9 +28647,9 @@ var require_interpreter = __commonJS({
|
|
|
28647
28647
|
/** @class */
|
|
28648
28648
|
(function(_super) {
|
|
28649
28649
|
__extends(NextAfterTokenWalker2, _super);
|
|
28650
|
-
function NextAfterTokenWalker2(topProd,
|
|
28651
|
-
var _this = _super.call(this, topProd,
|
|
28652
|
-
_this.path =
|
|
28650
|
+
function NextAfterTokenWalker2(topProd, path14) {
|
|
28651
|
+
var _this = _super.call(this, topProd, path14) || this;
|
|
28652
|
+
_this.path = path14;
|
|
28653
28653
|
_this.nextTerminalName = "";
|
|
28654
28654
|
_this.nextTerminalOccurrence = 0;
|
|
28655
28655
|
_this.nextTerminalName = _this.path.lastTok.name;
|
|
@@ -29346,10 +29346,10 @@ var require_lookahead = __commonJS({
|
|
|
29346
29346
|
}
|
|
29347
29347
|
return result;
|
|
29348
29348
|
}
|
|
29349
|
-
function pathToHashKeys(
|
|
29349
|
+
function pathToHashKeys(path14) {
|
|
29350
29350
|
var keys3 = [""];
|
|
29351
|
-
for (var i2 = 0; i2 <
|
|
29352
|
-
var tokType =
|
|
29351
|
+
for (var i2 = 0; i2 < path14.length; i2++) {
|
|
29352
|
+
var tokType = path14[i2];
|
|
29353
29353
|
var longerKeys = [];
|
|
29354
29354
|
for (var j = 0; j < keys3.length; j++) {
|
|
29355
29355
|
var currShorterKey = keys3[j];
|
|
@@ -29661,9 +29661,9 @@ var require_checks = __commonJS({
|
|
|
29661
29661
|
return errors2;
|
|
29662
29662
|
}
|
|
29663
29663
|
exports2.validateRuleIsOverridden = validateRuleIsOverridden;
|
|
29664
|
-
function validateNoLeftRecursion(topRule, currRule, errMsgProvider,
|
|
29665
|
-
if (
|
|
29666
|
-
|
|
29664
|
+
function validateNoLeftRecursion(topRule, currRule, errMsgProvider, path14) {
|
|
29665
|
+
if (path14 === void 0) {
|
|
29666
|
+
path14 = [];
|
|
29667
29667
|
}
|
|
29668
29668
|
var errors2 = [];
|
|
29669
29669
|
var nextNonTerminals = getFirstNoneTerminal(currRule.definition);
|
|
@@ -29676,15 +29676,15 @@ var require_checks = __commonJS({
|
|
|
29676
29676
|
errors2.push({
|
|
29677
29677
|
message: errMsgProvider.buildLeftRecursionError({
|
|
29678
29678
|
topLevelRule: topRule,
|
|
29679
|
-
leftRecursionPath:
|
|
29679
|
+
leftRecursionPath: path14
|
|
29680
29680
|
}),
|
|
29681
29681
|
type: parser_1.ParserDefinitionErrorType.LEFT_RECURSION,
|
|
29682
29682
|
ruleName
|
|
29683
29683
|
});
|
|
29684
29684
|
}
|
|
29685
|
-
var validNextSteps = utils2.difference(nextNonTerminals,
|
|
29685
|
+
var validNextSteps = utils2.difference(nextNonTerminals, path14.concat([topRule]));
|
|
29686
29686
|
var errorsFromNextSteps = utils2.map(validNextSteps, function(currRefRule) {
|
|
29687
|
-
var newPath = utils2.cloneArr(
|
|
29687
|
+
var newPath = utils2.cloneArr(path14);
|
|
29688
29688
|
newPath.push(currRefRule);
|
|
29689
29689
|
return validateNoLeftRecursion(topRule, currRefRule, errMsgProvider, newPath);
|
|
29690
29690
|
});
|
|
@@ -37293,8 +37293,8 @@ var require_utils4 = __commonJS({
|
|
|
37293
37293
|
var result = transform2[inputType][outputType](input);
|
|
37294
37294
|
return result;
|
|
37295
37295
|
};
|
|
37296
|
-
exports2.resolve = function(
|
|
37297
|
-
var parts =
|
|
37296
|
+
exports2.resolve = function(path14) {
|
|
37297
|
+
var parts = path14.split("/");
|
|
37298
37298
|
var result = [];
|
|
37299
37299
|
for (var index = 0; index < parts.length; index++) {
|
|
37300
37300
|
var part = parts[index];
|
|
@@ -43147,18 +43147,18 @@ var require_object = __commonJS({
|
|
|
43147
43147
|
var object2 = new ZipObject(name2, zipObjectContent, o);
|
|
43148
43148
|
this.files[name2] = object2;
|
|
43149
43149
|
};
|
|
43150
|
-
var parentFolder = function(
|
|
43151
|
-
if (
|
|
43152
|
-
|
|
43150
|
+
var parentFolder = function(path14) {
|
|
43151
|
+
if (path14.slice(-1) === "/") {
|
|
43152
|
+
path14 = path14.substring(0, path14.length - 1);
|
|
43153
43153
|
}
|
|
43154
|
-
var lastSlash =
|
|
43155
|
-
return lastSlash > 0 ?
|
|
43154
|
+
var lastSlash = path14.lastIndexOf("/");
|
|
43155
|
+
return lastSlash > 0 ? path14.substring(0, lastSlash) : "";
|
|
43156
43156
|
};
|
|
43157
|
-
var forceTrailingSlash = function(
|
|
43158
|
-
if (
|
|
43159
|
-
|
|
43157
|
+
var forceTrailingSlash = function(path14) {
|
|
43158
|
+
if (path14.slice(-1) !== "/") {
|
|
43159
|
+
path14 += "/";
|
|
43160
43160
|
}
|
|
43161
|
-
return
|
|
43161
|
+
return path14;
|
|
43162
43162
|
};
|
|
43163
43163
|
var folderAdd = function(name2, createFolders) {
|
|
43164
43164
|
createFolders = typeof createFolders !== "undefined" ? createFolders : defaults2.createFolders;
|
|
@@ -44160,9 +44160,9 @@ var require_lib4 = __commonJS({
|
|
|
44160
44160
|
// src/cli.ts
|
|
44161
44161
|
import dns from "node:dns";
|
|
44162
44162
|
import net2 from "node:net";
|
|
44163
|
-
import
|
|
44163
|
+
import fs14 from "node:fs";
|
|
44164
44164
|
import os4 from "node:os";
|
|
44165
|
-
import
|
|
44165
|
+
import path13 from "node:path";
|
|
44166
44166
|
import readline from "node:readline";
|
|
44167
44167
|
|
|
44168
44168
|
// ../shared/src/transport_error.ts
|
|
@@ -44356,8 +44356,8 @@ var LoticsClient = class {
|
|
|
44356
44356
|
}
|
|
44357
44357
|
return headers;
|
|
44358
44358
|
}
|
|
44359
|
-
async request(method,
|
|
44360
|
-
const url2 = `${this.baseUrl}${
|
|
44359
|
+
async request(method, path14, body) {
|
|
44360
|
+
const url2 = `${this.baseUrl}${path14}`;
|
|
44361
44361
|
const headers = this.buildHeaders();
|
|
44362
44362
|
const init = { method, headers };
|
|
44363
44363
|
if (body !== void 0) {
|
|
@@ -44400,8 +44400,8 @@ var LoticsClient = class {
|
|
|
44400
44400
|
async deleteWorkspace(id) {
|
|
44401
44401
|
return this.request("DELETE", `/v1/workspaces/${encodeURIComponent(id)}`);
|
|
44402
44402
|
}
|
|
44403
|
-
async login() {
|
|
44404
|
-
return this.request("POST", "/v1/cli/login");
|
|
44403
|
+
async login(body) {
|
|
44404
|
+
return this.request("POST", "/v1/cli/login", body ?? {});
|
|
44405
44405
|
}
|
|
44406
44406
|
async listTools() {
|
|
44407
44407
|
return this.request("GET", "/v1/tools");
|
|
@@ -44468,90 +44468,6 @@ var LoticsClient = class {
|
|
|
44468
44468
|
async createApp(body) {
|
|
44469
44469
|
return this.request("POST", "/v1/apps", body);
|
|
44470
44470
|
}
|
|
44471
|
-
/**
|
|
44472
|
-
* Install a package version into the current workspace — ONE endpoint,
|
|
44473
|
-
* kind-branched into a discriminated response (`kind`). An `app` package
|
|
44474
|
-
* scaffolds the data model / deploys / materializes and returns the installation
|
|
44475
|
-
* app (+ advisory knowledge warnings); a `content` package installs only its
|
|
44476
|
-
* doc corpus and returns the installation row. `bind_to` (content only)
|
|
44477
|
-
* resolves a name collision by adopting an existing same-named doc as
|
|
44478
|
-
* package-managed. `version` omitted installs the latest published version.
|
|
44479
|
-
*/
|
|
44480
|
-
async installPackage(package_id, body) {
|
|
44481
|
-
return this.request(
|
|
44482
|
-
"POST",
|
|
44483
|
-
`/v1/packages/${encodeURIComponent(package_id)}/installations`,
|
|
44484
|
-
body
|
|
44485
|
-
);
|
|
44486
|
-
}
|
|
44487
|
-
/**
|
|
44488
|
-
* Uninstall a standalone content package — delete the installation row. By
|
|
44489
|
-
* default the package-bound docs are ARCHIVED; `keep_content` retains them as
|
|
44490
|
-
* ordinary workspace docs. Admin-only. Backs `opctl uninstall`.
|
|
44491
|
-
*/
|
|
44492
|
-
async uninstallContentPackage(installation_id, opts = {}) {
|
|
44493
|
-
const qs = opts.keep_content ? "?keep_content=true" : "";
|
|
44494
|
-
return this.request(
|
|
44495
|
-
"DELETE",
|
|
44496
|
-
`/v1/content-installations/${encodeURIComponent(installation_id)}${qs}`
|
|
44497
|
-
);
|
|
44498
|
-
}
|
|
44499
|
-
/**
|
|
44500
|
-
* Preview upgrading a standalone content installation — the knowledge namespace's
|
|
44501
|
-
* per-alias `entries` (added/changed/removed/drifted + a `modified` flag) plus the
|
|
44502
|
-
* consent-requiring `templates` (a template the target changed whose live content
|
|
44503
|
-
* was locally edited; a clean one auto-updates and is absent). No writes.
|
|
44504
|
-
* Admin-only.
|
|
44505
|
-
*/
|
|
44506
|
-
async previewContentInstallationUpgrade(installation_id, opts = {}) {
|
|
44507
|
-
const qs = opts.version !== void 0 ? `?version=${opts.version}` : "";
|
|
44508
|
-
return this.request(
|
|
44509
|
-
"GET",
|
|
44510
|
-
`/v1/content-installations/${encodeURIComponent(installation_id)}/upgrade${qs}`
|
|
44511
|
-
);
|
|
44512
|
-
}
|
|
44513
|
-
/**
|
|
44514
|
-
* Apply a standalone content upgrade — propagate the target version's content per
|
|
44515
|
-
* the resolutions (`knowledge`: a modified change/removal or drift needs consent;
|
|
44516
|
-
* `templates`: a locally-edited changed template takes revert|keep), then advance
|
|
44517
|
-
* the pin + binding. Returns the updated installation row. Admin-only.
|
|
44518
|
-
*/
|
|
44519
|
-
async applyContentInstallationUpgrade(installation_id, body) {
|
|
44520
|
-
return this.request(
|
|
44521
|
-
"POST",
|
|
44522
|
-
`/v1/content-installations/${encodeURIComponent(installation_id)}/upgrade`,
|
|
44523
|
-
body
|
|
44524
|
-
);
|
|
44525
|
-
}
|
|
44526
|
-
/**
|
|
44527
|
-
* List a workspace's package-managed knowledge installations, each folded with
|
|
44528
|
-
* registry status (name, kind, official badge, latest version, update-available).
|
|
44529
|
-
* Member-accessible (workspace-scoped); backs the settings "Managed by" badge.
|
|
44530
|
-
*/
|
|
44531
|
-
async listContentInstallations(workspace_id) {
|
|
44532
|
-
return this.request(
|
|
44533
|
-
"GET",
|
|
44534
|
-
`/v1/workspaces/${encodeURIComponent(workspace_id)}/content-installations`
|
|
44535
|
-
);
|
|
44536
|
-
}
|
|
44537
|
-
/**
|
|
44538
|
-
* Uninstall a package installation (backs `opctl uninstall`). Does
|
|
44539
|
-
* everything DELETE does plus archives the installation's lifecycle
|
|
44540
|
-
* artifacts; with `archive_tables` it also archives the scaffolded entity
|
|
44541
|
-
* tables — refused server-side unless this installation created them
|
|
44542
|
-
* (provenance) and nothing else references them. Admin-only.
|
|
44543
|
-
*/
|
|
44544
|
-
async uninstallAppPackage(app_id, body) {
|
|
44545
|
-
return this.request("POST", `/v1/apps/${encodeURIComponent(app_id)}/uninstall`, body);
|
|
44546
|
-
}
|
|
44547
|
-
/**
|
|
44548
|
-
* Partial-merge a package installation's config (backs `opctl package config
|
|
44549
|
-
* --set`). Only the provided keys change; validated against the installed
|
|
44550
|
-
* contract. Returns the full effective config. Admin-only.
|
|
44551
|
-
*/
|
|
44552
|
-
async updateAppPackageConfig(app_id, body) {
|
|
44553
|
-
return this.request("PATCH", `/v1/apps/${encodeURIComponent(app_id)}/package-config`, body);
|
|
44554
|
-
}
|
|
44555
44471
|
/**
|
|
44556
44472
|
* Retire (or `undo` un-retire) a registry package (backs `lotics app
|
|
44557
44473
|
* unpublish` — the endpoint/audit action keep the `retire` name to avoid API
|
|
@@ -44562,83 +44478,75 @@ var LoticsClient = class {
|
|
|
44562
44478
|
async retirePackage(package_id, body) {
|
|
44563
44479
|
return this.request("POST", `/v1/packages/${encodeURIComponent(package_id)}/retire`, body);
|
|
44564
44480
|
}
|
|
44481
|
+
// --- Packages (registry reads + installations) ---
|
|
44482
|
+
// Authoring is server-side: apps via `POST /v1/apps/{id}/package-publish|release`,
|
|
44483
|
+
// content packages via the `publish_content`/`release_content` tools. There is no
|
|
44484
|
+
// client-side create-package / upload-bundle path.
|
|
44565
44485
|
/**
|
|
44566
|
-
*
|
|
44567
|
-
*
|
|
44568
|
-
*
|
|
44569
|
-
* app becomes a normal bespoke app and can no longer be upgraded. Returns the
|
|
44570
|
-
* resulting app.
|
|
44486
|
+
* The starters this organization can copy — Lotics-reviewed ones plus its own,
|
|
44487
|
+
* never a catalogue of everything published. The server returns exactly what
|
|
44488
|
+
* instantiate would accept, so the list cannot offer a refusal. Admin-only.
|
|
44571
44489
|
*/
|
|
44572
|
-
async
|
|
44573
|
-
return this.request("
|
|
44490
|
+
async listStarters() {
|
|
44491
|
+
return this.request("GET", "/v1/starters");
|
|
44574
44492
|
}
|
|
44575
44493
|
/**
|
|
44576
|
-
*
|
|
44577
|
-
*
|
|
44578
|
-
*
|
|
44579
|
-
*
|
|
44580
|
-
*
|
|
44581
|
-
*
|
|
44582
|
-
|
|
44583
|
-
|
|
44584
|
-
* Yank / unyank a published package version — refuses NEW installs/upgrades/
|
|
44585
|
-
* adopts targeting it; pinned installations keep running. Owner-org
|
|
44586
|
-
* admin-only. Backs `opctl package yank`.
|
|
44494
|
+
* Copy a starter into the current workspace.
|
|
44495
|
+
*
|
|
44496
|
+
* Server-side this scaffolds the schema, creates the templates, docs and
|
|
44497
|
+
* sample records, creates a BESPOKE app and materializes onto it — then stops.
|
|
44498
|
+
* It deploys nothing: a starter ships source only, and the source has to be
|
|
44499
|
+
* built where codegen can bake THIS workspace's field ids. `bundle_url` is a
|
|
44500
|
+
* presigned GET of that source, and finishing the job is the caller's half.
|
|
44501
|
+
* Admin-only.
|
|
44587
44502
|
*/
|
|
44588
|
-
async
|
|
44503
|
+
async instantiateStarter(starter_id, body) {
|
|
44589
44504
|
return this.request(
|
|
44590
44505
|
"POST",
|
|
44591
|
-
`/v1/
|
|
44592
|
-
{ yanked }
|
|
44593
|
-
);
|
|
44594
|
-
}
|
|
44595
|
-
async fleetUpgradePackage(package_id, body) {
|
|
44596
|
-
return this.request(
|
|
44597
|
-
"POST",
|
|
44598
|
-
`/v1/packages/${encodeURIComponent(package_id)}/fleet-upgrade`,
|
|
44506
|
+
`/v1/starters/${encodeURIComponent(starter_id)}/instantiate`,
|
|
44599
44507
|
body
|
|
44600
44508
|
);
|
|
44601
44509
|
}
|
|
44602
|
-
// --- Packages (registry reads + installations) ---
|
|
44603
|
-
// Authoring is server-side: apps via `POST /v1/apps/{id}/package-publish|release`,
|
|
44604
|
-
// content packages via the `publish_content`/`release_content` tools. There is no
|
|
44605
|
-
// client-side create-package / upload-bundle path.
|
|
44606
44510
|
/**
|
|
44607
|
-
*
|
|
44608
|
-
*
|
|
44511
|
+
* Which starter this app is the origin of. 404 when it has published none.
|
|
44512
|
+
*
|
|
44513
|
+
* The app row carries no pin, so this is the only app→starter direction there
|
|
44514
|
+
* is — provenance lives on the published version. Admin-only.
|
|
44609
44515
|
*/
|
|
44610
|
-
async
|
|
44611
|
-
return this.request("GET", `/v1/
|
|
44612
|
-
}
|
|
44613
|
-
/** Version history newest-first (no contract payloads) — backs `opctl package show`. Admin-only. */
|
|
44614
|
-
async listPackageVersions(package_id) {
|
|
44615
|
-
return this.request("GET", `/v1/packages/${encodeURIComponent(package_id)}/versions`);
|
|
44516
|
+
async getAppOriginStarter(app_id) {
|
|
44517
|
+
return this.request("GET", `/v1/apps/${encodeURIComponent(app_id)}/origin-starter`);
|
|
44616
44518
|
}
|
|
44617
44519
|
/**
|
|
44618
|
-
*
|
|
44619
|
-
*
|
|
44620
|
-
*
|
|
44621
|
-
*
|
|
44622
|
-
*
|
|
44520
|
+
* Capture live records from this workspace as a starter's sample data.
|
|
44521
|
+
*
|
|
44522
|
+
* The alias-keyed shape is produced SERVER-side, because the contract alias
|
|
44523
|
+
* space is minted by extract and exists nowhere a project can read it. Pure
|
|
44524
|
+
* read — the caller writes the returned files into the project and reviews
|
|
44525
|
+
* them, which matters: these rows are copied verbatim into every workspace
|
|
44526
|
+
* that takes the starter. Admin-only.
|
|
44623
44527
|
*/
|
|
44624
|
-
async
|
|
44528
|
+
async captureStarterFixtures(app_id, opts = {}) {
|
|
44529
|
+
const params = new URLSearchParams();
|
|
44530
|
+
if (opts.entities !== void 0 && opts.entities.length > 0) {
|
|
44531
|
+
params.set("entities", opts.entities.join(","));
|
|
44532
|
+
}
|
|
44533
|
+
if (opts.limit !== void 0) params.set("limit", String(opts.limit));
|
|
44534
|
+
const qs = params.toString();
|
|
44625
44535
|
return this.request(
|
|
44626
|
-
"
|
|
44627
|
-
`/v1/apps/${encodeURIComponent(app_id)}/
|
|
44628
|
-
body
|
|
44536
|
+
"GET",
|
|
44537
|
+
`/v1/apps/${encodeURIComponent(app_id)}/fixtures-capture${qs ? `?${qs}` : ""}`
|
|
44629
44538
|
);
|
|
44630
44539
|
}
|
|
44631
44540
|
/**
|
|
44632
|
-
*
|
|
44633
|
-
*
|
|
44634
|
-
* report — with no writes. Admin-only.
|
|
44541
|
+
* Fetch a registry starter's metadata (`latest_version` and the Lotics-backed
|
|
44542
|
+
* `is_official` trust badge). Admin-only; cross-tenant by id.
|
|
44635
44543
|
*/
|
|
44636
|
-
async
|
|
44637
|
-
|
|
44638
|
-
|
|
44639
|
-
|
|
44640
|
-
|
|
44641
|
-
);
|
|
44544
|
+
async getPackage(package_id) {
|
|
44545
|
+
return this.request("GET", `/v1/packages/${encodeURIComponent(package_id)}`);
|
|
44546
|
+
}
|
|
44547
|
+
/** Version history newest-first (no contract payloads) — backs `opctl package show`. Admin-only. */
|
|
44548
|
+
async listPackageVersions(package_id) {
|
|
44549
|
+
return this.request("GET", `/v1/packages/${encodeURIComponent(package_id)}/versions`);
|
|
44642
44550
|
}
|
|
44643
44551
|
/**
|
|
44644
44552
|
* Workspace-wide dangling-reference sweep — active app/workflow artifacts
|
|
@@ -44648,14 +44556,6 @@ var LoticsClient = class {
|
|
|
44648
44556
|
async getWorkspaceDanglingReferences() {
|
|
44649
44557
|
return this.request("GET", "/v1/workspaces/dangling-references");
|
|
44650
44558
|
}
|
|
44651
|
-
/**
|
|
44652
|
-
* Health check for a package installation — version pin vs. registry latest,
|
|
44653
|
-
* binding drift, and locally modified core artifacts. Read-only; backs
|
|
44654
|
-
* `opctl package doctor`. Admin-only.
|
|
44655
|
-
*/
|
|
44656
|
-
async getPackageHealth(app_id) {
|
|
44657
|
-
return this.request("GET", `/v1/apps/${encodeURIComponent(app_id)}/package-health`);
|
|
44658
|
-
}
|
|
44659
44559
|
/**
|
|
44660
44560
|
* Preview a release — the dry run behind `opctl app release`. Runs the
|
|
44661
44561
|
* binding-aware extract of the origin (aliases stable through the app's current
|
|
@@ -44671,9 +44571,6 @@ var LoticsClient = class {
|
|
|
44671
44571
|
if (opts.knowledge !== void 0 && opts.knowledge.length > 0) {
|
|
44672
44572
|
params.set("knowledge", JSON.stringify(opts.knowledge));
|
|
44673
44573
|
}
|
|
44674
|
-
if (opts.config !== void 0) {
|
|
44675
|
-
params.set("config", JSON.stringify(opts.config));
|
|
44676
|
-
}
|
|
44677
44574
|
const query = params.toString();
|
|
44678
44575
|
return this.request(
|
|
44679
44576
|
"GET",
|
|
@@ -44706,9 +44603,6 @@ var LoticsClient = class {
|
|
|
44706
44603
|
if (opts.knowledge !== void 0 && opts.knowledge.length > 0) {
|
|
44707
44604
|
params.set("knowledge", JSON.stringify(opts.knowledge));
|
|
44708
44605
|
}
|
|
44709
|
-
if (opts.config !== void 0 && opts.config.length > 0) {
|
|
44710
|
-
params.set("config", JSON.stringify(opts.config));
|
|
44711
|
-
}
|
|
44712
44606
|
if (opts.renames !== void 0 && opts.renames.length > 0) {
|
|
44713
44607
|
params.set("renames", JSON.stringify(opts.renames));
|
|
44714
44608
|
}
|
|
@@ -44812,10 +44706,6 @@ var LoticsClient = class {
|
|
|
44812
44706
|
const qs = group_id ? `?group_id=${encodeURIComponent(group_id)}` : "";
|
|
44813
44707
|
return this.request("GET", `/v1/apps/${encodeURIComponent(app_id)}/members${qs}`);
|
|
44814
44708
|
}
|
|
44815
|
-
/** A package installation's alias→id maps (fields/options/roles) — the app's runtime F/OPT resolution. */
|
|
44816
|
-
async appBinding(app_id) {
|
|
44817
|
-
return this.request("GET", `/v1/apps/${encodeURIComponent(app_id)}/binding`);
|
|
44818
|
-
}
|
|
44819
44709
|
/**
|
|
44820
44710
|
* Resolve the full option set (key, label, color) of a named query's select
|
|
44821
44711
|
* columns — the picker companion to `appQuery`. Mirrors
|
|
@@ -45955,12 +45845,23 @@ var COMMANDS = [
|
|
|
45955
45845
|
]
|
|
45956
45846
|
},
|
|
45957
45847
|
{
|
|
45958
|
-
verbs: ["
|
|
45959
|
-
help: [
|
|
45960
|
-
|
|
45961
|
-
|
|
45962
|
-
|
|
45963
|
-
|
|
45848
|
+
verbs: ["starter"],
|
|
45849
|
+
help: [
|
|
45850
|
+
" lotics starter list Starters you can copy into this workspace",
|
|
45851
|
+
" lotics starter show <starter_id> What one carries: tables, docs, templates, sample data",
|
|
45852
|
+
" lotics starter init <starter_id> [path]",
|
|
45853
|
+
" Copy it in \u2014 schema, templates, knowledge docs,",
|
|
45854
|
+
" sample records and an editable app project. A COPY:",
|
|
45855
|
+
" everything it creates is yours outright, with no",
|
|
45856
|
+
" link back and nothing to upgrade. Builds and deploys",
|
|
45857
|
+
" locally, so it needs node + a few minutes.",
|
|
45858
|
+
" --no-sample-data skips the sample records;",
|
|
45859
|
+
" --adopt allows a workspace that is not empty",
|
|
45860
|
+
" lotics starter fixtures capture --entity <alias> --limit <n>",
|
|
45861
|
+
" (authoring) Write reviewable sample records into the",
|
|
45862
|
+
" app project. READ WHAT IT WROTE before committing \u2014",
|
|
45863
|
+
" these rows ship to everyone who copies the starter"
|
|
45864
|
+
]
|
|
45964
45865
|
},
|
|
45965
45866
|
{
|
|
45966
45867
|
verbs: ["docs"],
|
|
@@ -46214,36 +46115,10 @@ import { tmpdir } from "node:os";
|
|
|
46214
46115
|
// src/starter_template.ts
|
|
46215
46116
|
var STARTER_REACT_NATIVE_VERSION = "0.85.3";
|
|
46216
46117
|
var VITEST_SETUP_FILENAME = "vitest.setup.ts";
|
|
46217
|
-
var VITEST_SETUP_CONTENT =
|
|
46218
|
-
|
|
46219
|
-
//
|
|
46220
|
-
|
|
46221
|
-
// a network call over the host bridge). Under vitest/jsdom there is no host, so
|
|
46222
|
-
// that call throws while a test is still COLLECTING \u2014 failing every test that
|
|
46223
|
-
// imports the app graph, even pure logic tests. getAppBinding is the network
|
|
46224
|
-
// boundary; mock it (and only it) so the module graph evaluates in tests.
|
|
46225
|
-
//
|
|
46226
|
-
// The stub returns an ECHO binding: any alias resolves to a synthetic,
|
|
46227
|
-
// self-identifying id (fld:test:<entity>.<field>, opt:test:\u2026, grp:test:\u2026). Echo,
|
|
46228
|
-
// not empty maps \u2014 app_fields's bound() throws on a missing key, so empty maps
|
|
46229
|
-
// would just re-break collection; and a ':test:' id can never be confused with a
|
|
46230
|
-
// real fld_\u2026/opt_\u2026/grp_\u2026 id, so a test that depends on a concrete binding fails
|
|
46231
|
-
// loud instead of silently reading undefined.
|
|
46232
|
-
vi.mock("@lotics/app-sdk", async (importOriginal) => {
|
|
46233
|
-
const actual = await importOriginal<typeof import("@lotics/app-sdk")>();
|
|
46234
|
-
const echoIds = (prefix: string): Record<string, string> =>
|
|
46235
|
-
new Proxy(
|
|
46236
|
-
{},
|
|
46237
|
-
{
|
|
46238
|
-
get: (_target, key) => (typeof key === "string" ? \`\${prefix}:test:\${key}\` : undefined),
|
|
46239
|
-
},
|
|
46240
|
-
) as Record<string, string>;
|
|
46241
|
-
return {
|
|
46242
|
-
...actual,
|
|
46243
|
-
getAppBinding: () =>
|
|
46244
|
-
Promise.resolve({ fields: echoIds("fld"), options: echoIds("opt"), roles: echoIds("grp") }),
|
|
46245
|
-
};
|
|
46246
|
-
});
|
|
46118
|
+
var VITEST_SETUP_CONTENT = `// Runs before every test file (wired by vite.config.ts \`test.setupFiles\`).
|
|
46119
|
+
// Empty by default \u2014 put global test setup here: custom matchers, a fetch stub,
|
|
46120
|
+
// timezone pinning, anything your suite needs before it collects.
|
|
46121
|
+
export {};
|
|
46247
46122
|
`;
|
|
46248
46123
|
function buildStarterTemplate(args) {
|
|
46249
46124
|
const uiVersion = args.ui_version;
|
|
@@ -46472,7 +46347,7 @@ export default defineConfig({
|
|
|
46472
46347
|
},
|
|
46473
46348
|
test: {
|
|
46474
46349
|
environment: "jsdom",
|
|
46475
|
-
//
|
|
46350
|
+
// Global test setup, run before every test file (empty until an author fills it)
|
|
46476
46351
|
// collects. A package-linked app's generated .lotics/app_fields.ts awaits it
|
|
46477
46352
|
// at module load; without the stub that network call throws under jsdom and
|
|
46478
46353
|
// every test that imports the app graph fails to collect. See vitest.setup.ts.
|
|
@@ -46987,7 +46862,6 @@ var SUPPORTED_OPS = /* @__PURE__ */ new Set([
|
|
|
46987
46862
|
"workflow",
|
|
46988
46863
|
"members",
|
|
46989
46864
|
"context",
|
|
46990
|
-
"binding",
|
|
46991
46865
|
"upload_url",
|
|
46992
46866
|
"upload_complete",
|
|
46993
46867
|
"agentRuns",
|
|
@@ -47008,11 +46882,10 @@ async function dispatchRpc(client, body, opts) {
|
|
|
47008
46882
|
}
|
|
47009
46883
|
switch (body.op) {
|
|
47010
46884
|
case "context": {
|
|
47011
|
-
const
|
|
46885
|
+
const who = await client.whoami();
|
|
47012
46886
|
return {
|
|
47013
46887
|
member_id: who.member_id,
|
|
47014
|
-
comments_enabled: opts?.commentsEnabled ?? false
|
|
47015
|
-
config: app.config ?? {}
|
|
46888
|
+
comments_enabled: opts?.commentsEnabled ?? false
|
|
47016
46889
|
};
|
|
47017
46890
|
}
|
|
47018
46891
|
case "query": {
|
|
@@ -47048,8 +46921,6 @@ async function dispatchRpc(client, body, opts) {
|
|
|
47048
46921
|
const p = body.payload;
|
|
47049
46922
|
return client.appMembers(body.app_id, p?.group);
|
|
47050
46923
|
}
|
|
47051
|
-
case "binding":
|
|
47052
|
-
return client.appBinding(body.app_id);
|
|
47053
46924
|
case "upload_url": {
|
|
47054
46925
|
const p = body.payload;
|
|
47055
46926
|
if (!p || typeof p.filename !== "string" || typeof p.mime_type !== "string" || typeof p.file_size !== "number") {
|
|
@@ -47534,6 +47405,18 @@ function createFileRelay(wrapperOrigin, now = Date.now) {
|
|
|
47534
47405
|
};
|
|
47535
47406
|
}
|
|
47536
47407
|
|
|
47408
|
+
// src/dev/rpc_label.ts
|
|
47409
|
+
function rpcLabel(op, payload) {
|
|
47410
|
+
const p = payload;
|
|
47411
|
+
const alias = typeof p?.alias === "string" && p.alias.length > 0 ? p.alias : null;
|
|
47412
|
+
if (!alias) return op;
|
|
47413
|
+
const isCount = op === "query" && p?.count === true;
|
|
47414
|
+
return `${op} ${alias}${isCount ? " (count)" : ""}`;
|
|
47415
|
+
}
|
|
47416
|
+
function concurrencyNote(concurrent) {
|
|
47417
|
+
return concurrent > 1 ? ` \xB7 ${concurrent} in flight` : "";
|
|
47418
|
+
}
|
|
47419
|
+
|
|
47537
47420
|
// src/dev/server.ts
|
|
47538
47421
|
var DEFAULT_PORT = 5174;
|
|
47539
47422
|
var DEFAULT_VITE_PORT = 5173;
|
|
@@ -47605,6 +47488,7 @@ async function startDevServer(args) {
|
|
|
47605
47488
|
"last-modified",
|
|
47606
47489
|
"content-disposition"
|
|
47607
47490
|
];
|
|
47491
|
+
let inFlight = 0;
|
|
47608
47492
|
const server = http.createServer(async (req, res) => {
|
|
47609
47493
|
const url2 = req.url ?? "/";
|
|
47610
47494
|
const pathname = url2.split("?")[0];
|
|
@@ -47617,9 +47501,19 @@ async function startDevServer(args) {
|
|
|
47617
47501
|
return;
|
|
47618
47502
|
}
|
|
47619
47503
|
if (req.method === "POST" && url2 === "/_rpc") {
|
|
47504
|
+
let counted = false;
|
|
47505
|
+
const release = () => {
|
|
47506
|
+
if (counted) {
|
|
47507
|
+
counted = false;
|
|
47508
|
+
inFlight--;
|
|
47509
|
+
}
|
|
47510
|
+
};
|
|
47620
47511
|
try {
|
|
47621
47512
|
const body = await readJson(req);
|
|
47622
47513
|
const startedAt2 = Date.now();
|
|
47514
|
+
inFlight++;
|
|
47515
|
+
counted = true;
|
|
47516
|
+
const concurrent = inFlight;
|
|
47623
47517
|
const result = await dispatchRpc(
|
|
47624
47518
|
args.client,
|
|
47625
47519
|
{
|
|
@@ -47628,9 +47522,9 @@ async function startDevServer(args) {
|
|
|
47628
47522
|
payload: body.payload
|
|
47629
47523
|
},
|
|
47630
47524
|
{ commentsEnabled: args.commentsEnabled }
|
|
47631
|
-
);
|
|
47525
|
+
).finally(release);
|
|
47632
47526
|
const ms = Date.now() - startedAt2;
|
|
47633
|
-
process.stderr.write(`[rpc] ${body.op} ${ms}ms
|
|
47527
|
+
process.stderr.write(`[rpc] ${rpcLabel(body.op, body.payload)} ${ms}ms${concurrencyNote(concurrent)}
|
|
47634
47528
|
`);
|
|
47635
47529
|
res.writeHead(200, { "Content-Type": "application/json" });
|
|
47636
47530
|
res.end(
|
|
@@ -47639,6 +47533,7 @@ async function startDevServer(args) {
|
|
|
47639
47533
|
)
|
|
47640
47534
|
);
|
|
47641
47535
|
} catch (err2) {
|
|
47536
|
+
release();
|
|
47642
47537
|
const message2 = err2 instanceof Error ? err2.message : String(err2);
|
|
47643
47538
|
process.stderr.write(`[rpc] ERROR ${message2}
|
|
47644
47539
|
`);
|
|
@@ -48261,7 +48156,7 @@ function codeWithoutComments(sourceText) {
|
|
|
48261
48156
|
return out.join("");
|
|
48262
48157
|
}
|
|
48263
48158
|
var ALIAS_CALL_HOOKS = {
|
|
48264
|
-
queries: ["useQuery", "usePaginatedQuery", "useInfiniteQuery", "useFieldOptions"],
|
|
48159
|
+
queries: ["useQuery", "usePaginatedQuery", "useInfiniteQuery", "useCount", "useFieldOptions"],
|
|
48265
48160
|
workflows: ["useWorkflow"],
|
|
48266
48161
|
agents: ["useAgentRun"]
|
|
48267
48162
|
};
|
|
@@ -48466,123 +48361,6 @@ export type AppOptions = typeof OPT;
|
|
|
48466
48361
|
`;
|
|
48467
48362
|
}
|
|
48468
48363
|
|
|
48469
|
-
// src/generate_package_fields.ts
|
|
48470
|
-
var HEADER2 = `// Auto-generated by 'lotics app codegen' and 'lotics app pull' (linked/published app).
|
|
48471
|
-
// DO NOT EDIT \u2014 regenerated from the installation's live binding.
|
|
48472
|
-
//
|
|
48473
|
-
// A package installation resolves F/OPT/ROLE at MODULE LOAD from its binding
|
|
48474
|
-
// (contract alias \u2192 THIS workspace's concrete id) via the SDK's \`binding\` RPC.
|
|
48475
|
-
// Top-level await: the module graph waits for the binding before any importer
|
|
48476
|
-
// evaluates, so every entry is a plain string.
|
|
48477
|
-
import { getAppBinding } from "@lotics/app-sdk";
|
|
48478
|
-
|
|
48479
|
-
const binding = await getAppBinding();
|
|
48480
|
-
|
|
48481
|
-
function bound(map: Record<string, string>, key: string, kind: string): string {
|
|
48482
|
-
const id = map[key];
|
|
48483
|
-
if (id === undefined) {
|
|
48484
|
-
throw new Error(
|
|
48485
|
-
\`app_fields: \${kind} "\${key}" is not in this installation's binding \u2014 \` +
|
|
48486
|
-
\`the generated app_fields.ts is stale relative to the installed contract version.\`,
|
|
48487
|
-
);
|
|
48488
|
-
}
|
|
48489
|
-
return id;
|
|
48490
|
-
}
|
|
48491
|
-
`;
|
|
48492
|
-
function parseBinding(binding) {
|
|
48493
|
-
const entities = [];
|
|
48494
|
-
const entityByAlias = /* @__PURE__ */ new Map();
|
|
48495
|
-
const fieldByKey = /* @__PURE__ */ new Map();
|
|
48496
|
-
for (const key of Object.keys(binding.fields)) {
|
|
48497
|
-
const dot = key.indexOf(".");
|
|
48498
|
-
if (dot <= 0 || dot >= key.length - 1) continue;
|
|
48499
|
-
const entityAlias = key.slice(0, dot);
|
|
48500
|
-
const fieldAlias = key.slice(dot + 1);
|
|
48501
|
-
let entity = entityByAlias.get(entityAlias);
|
|
48502
|
-
if (entity === void 0) {
|
|
48503
|
-
entity = { alias: entityAlias, fields: [] };
|
|
48504
|
-
entityByAlias.set(entityAlias, entity);
|
|
48505
|
-
entities.push(entity);
|
|
48506
|
-
}
|
|
48507
|
-
const field = { alias: fieldAlias, key, options: [] };
|
|
48508
|
-
entity.fields.push(field);
|
|
48509
|
-
fieldByKey.set(key, field);
|
|
48510
|
-
}
|
|
48511
|
-
for (const key of Object.keys(binding.options)) {
|
|
48512
|
-
const colon = key.indexOf(":");
|
|
48513
|
-
if (colon <= 0 || colon >= key.length - 1) continue;
|
|
48514
|
-
const fieldKey = key.slice(0, colon);
|
|
48515
|
-
const optionAlias = key.slice(colon + 1);
|
|
48516
|
-
const field = fieldByKey.get(fieldKey);
|
|
48517
|
-
if (field === void 0) continue;
|
|
48518
|
-
field.options.push({ alias: optionAlias, key });
|
|
48519
|
-
}
|
|
48520
|
-
return { entities, roles: Object.keys(binding.roles) };
|
|
48521
|
-
}
|
|
48522
|
-
function emitFieldMap2(entities) {
|
|
48523
|
-
if (entities.length === 0) return `export const F = {} as const;`;
|
|
48524
|
-
const blocks = entities.map((entity) => {
|
|
48525
|
-
const lines = entity.fields.map(
|
|
48526
|
-
(field) => ` ${propKey(field.alias)}: bound(binding.fields, ${JSON.stringify(field.key)}, "field"),`
|
|
48527
|
-
);
|
|
48528
|
-
return ` ${propKey(entity.alias.toUpperCase())}: {
|
|
48529
|
-
${lines.join("\n")}
|
|
48530
|
-
},`;
|
|
48531
|
-
});
|
|
48532
|
-
return `export const F = {
|
|
48533
|
-
${blocks.join("\n")}
|
|
48534
|
-
} as const;`;
|
|
48535
|
-
}
|
|
48536
|
-
function emitOptionMap2(entities) {
|
|
48537
|
-
const entityBlocks = [];
|
|
48538
|
-
for (const entity of entities) {
|
|
48539
|
-
const fieldBlocks = [];
|
|
48540
|
-
for (const field of entity.fields) {
|
|
48541
|
-
if (field.options.length === 0) continue;
|
|
48542
|
-
const lines = field.options.map(
|
|
48543
|
-
(option) => ` ${propKey(option.alias)}: bound(binding.options, ${JSON.stringify(option.key)}, "option"),`
|
|
48544
|
-
);
|
|
48545
|
-
fieldBlocks.push(` ${propKey(field.alias)}: {
|
|
48546
|
-
${lines.join("\n")}
|
|
48547
|
-
},`);
|
|
48548
|
-
}
|
|
48549
|
-
if (fieldBlocks.length === 0) continue;
|
|
48550
|
-
entityBlocks.push(` ${propKey(entity.alias.toUpperCase())}: {
|
|
48551
|
-
${fieldBlocks.join("\n")}
|
|
48552
|
-
},`);
|
|
48553
|
-
}
|
|
48554
|
-
if (entityBlocks.length === 0) return `export const OPT = {} as const;`;
|
|
48555
|
-
return `export const OPT = {
|
|
48556
|
-
${entityBlocks.join("\n")}
|
|
48557
|
-
} as const;`;
|
|
48558
|
-
}
|
|
48559
|
-
function emitRoleMap(roles) {
|
|
48560
|
-
if (roles.length === 0) return `export const ROLE = {} as const;`;
|
|
48561
|
-
const lines = roles.map(
|
|
48562
|
-
(role) => ` ${propKey(role)}: bound(binding.roles, ${JSON.stringify(role)}, "role"),`
|
|
48563
|
-
);
|
|
48564
|
-
return `export const ROLE = {
|
|
48565
|
-
${lines.join("\n")}
|
|
48566
|
-
} as const;`;
|
|
48567
|
-
}
|
|
48568
|
-
function generatePackageAppFields(binding) {
|
|
48569
|
-
const { entities, roles } = parseBinding(binding);
|
|
48570
|
-
return `${HEADER2}
|
|
48571
|
-
${emitFieldMap2(entities)}
|
|
48572
|
-
|
|
48573
|
-
${emitOptionMap2(entities)}
|
|
48574
|
-
|
|
48575
|
-
${emitRoleMap(roles)}
|
|
48576
|
-
|
|
48577
|
-
/** Field-id alias map: \`F[<ENTITY>][<field>]\` is this installation's \`fld_\u2026\` id. */
|
|
48578
|
-
export type AppFields = typeof F;
|
|
48579
|
-
/** Select-option alias map: \`OPT[<ENTITY>][<field>][<option>]\` is this installation's \`opt_\u2026\` id. */
|
|
48580
|
-
export type AppOptions = typeof OPT;
|
|
48581
|
-
/** Role alias map: \`ROLE[<role>]\` is this installation's \`grp_\u2026\` id. */
|
|
48582
|
-
export type AppRoles = typeof ROLE;
|
|
48583
|
-
`;
|
|
48584
|
-
}
|
|
48585
|
-
|
|
48586
48364
|
// src/app_workflow_check.ts
|
|
48587
48365
|
import fs7 from "node:fs";
|
|
48588
48366
|
import path9 from "node:path";
|
|
@@ -49357,10 +49135,10 @@ function mergeDefs(...defs) {
|
|
|
49357
49135
|
function cloneDef(schema) {
|
|
49358
49136
|
return mergeDefs(schema._zod.def);
|
|
49359
49137
|
}
|
|
49360
|
-
function getElementAtPath(obj,
|
|
49361
|
-
if (!
|
|
49138
|
+
function getElementAtPath(obj, path14) {
|
|
49139
|
+
if (!path14)
|
|
49362
49140
|
return obj;
|
|
49363
|
-
return
|
|
49141
|
+
return path14.reduce((acc, key) => acc?.[key], obj);
|
|
49364
49142
|
}
|
|
49365
49143
|
function promiseAllObject(promisesObj) {
|
|
49366
49144
|
const keys3 = Object.keys(promisesObj);
|
|
@@ -49769,11 +49547,11 @@ function explicitlyAborted(x2, startIndex = 0) {
|
|
|
49769
49547
|
}
|
|
49770
49548
|
return false;
|
|
49771
49549
|
}
|
|
49772
|
-
function prefixIssues(
|
|
49550
|
+
function prefixIssues(path14, issues) {
|
|
49773
49551
|
return issues.map((iss) => {
|
|
49774
49552
|
var _a4;
|
|
49775
49553
|
(_a4 = iss).path ?? (_a4.path = []);
|
|
49776
|
-
iss.path.unshift(
|
|
49554
|
+
iss.path.unshift(path14);
|
|
49777
49555
|
return iss;
|
|
49778
49556
|
});
|
|
49779
49557
|
}
|
|
@@ -49920,16 +49698,16 @@ function flattenError(error52, mapper = (issue2) => issue2.message) {
|
|
|
49920
49698
|
}
|
|
49921
49699
|
function formatError(error52, mapper = (issue2) => issue2.message) {
|
|
49922
49700
|
const fieldErrors = { _errors: [] };
|
|
49923
|
-
const processError = (error53,
|
|
49701
|
+
const processError = (error53, path14 = []) => {
|
|
49924
49702
|
for (const issue2 of error53.issues) {
|
|
49925
49703
|
if (issue2.code === "invalid_union" && issue2.errors.length) {
|
|
49926
|
-
issue2.errors.map((issues) => processError({ issues }, [...
|
|
49704
|
+
issue2.errors.map((issues) => processError({ issues }, [...path14, ...issue2.path]));
|
|
49927
49705
|
} else if (issue2.code === "invalid_key") {
|
|
49928
|
-
processError({ issues: issue2.issues }, [...
|
|
49706
|
+
processError({ issues: issue2.issues }, [...path14, ...issue2.path]);
|
|
49929
49707
|
} else if (issue2.code === "invalid_element") {
|
|
49930
|
-
processError({ issues: issue2.issues }, [...
|
|
49708
|
+
processError({ issues: issue2.issues }, [...path14, ...issue2.path]);
|
|
49931
49709
|
} else {
|
|
49932
|
-
const fullpath = [...
|
|
49710
|
+
const fullpath = [...path14, ...issue2.path];
|
|
49933
49711
|
if (fullpath.length === 0) {
|
|
49934
49712
|
fieldErrors._errors.push(mapper(issue2));
|
|
49935
49713
|
} else {
|
|
@@ -49956,17 +49734,17 @@ function formatError(error52, mapper = (issue2) => issue2.message) {
|
|
|
49956
49734
|
}
|
|
49957
49735
|
function treeifyError(error52, mapper = (issue2) => issue2.message) {
|
|
49958
49736
|
const result = { errors: [] };
|
|
49959
|
-
const processError = (error53,
|
|
49737
|
+
const processError = (error53, path14 = []) => {
|
|
49960
49738
|
var _a4, _b2;
|
|
49961
49739
|
for (const issue2 of error53.issues) {
|
|
49962
49740
|
if (issue2.code === "invalid_union" && issue2.errors.length) {
|
|
49963
|
-
issue2.errors.map((issues) => processError({ issues }, [...
|
|
49741
|
+
issue2.errors.map((issues) => processError({ issues }, [...path14, ...issue2.path]));
|
|
49964
49742
|
} else if (issue2.code === "invalid_key") {
|
|
49965
|
-
processError({ issues: issue2.issues }, [...
|
|
49743
|
+
processError({ issues: issue2.issues }, [...path14, ...issue2.path]);
|
|
49966
49744
|
} else if (issue2.code === "invalid_element") {
|
|
49967
|
-
processError({ issues: issue2.issues }, [...
|
|
49745
|
+
processError({ issues: issue2.issues }, [...path14, ...issue2.path]);
|
|
49968
49746
|
} else {
|
|
49969
|
-
const fullpath = [...
|
|
49747
|
+
const fullpath = [...path14, ...issue2.path];
|
|
49970
49748
|
if (fullpath.length === 0) {
|
|
49971
49749
|
result.errors.push(mapper(issue2));
|
|
49972
49750
|
continue;
|
|
@@ -49998,8 +49776,8 @@ function treeifyError(error52, mapper = (issue2) => issue2.message) {
|
|
|
49998
49776
|
}
|
|
49999
49777
|
function toDotPath(_path) {
|
|
50000
49778
|
const segs = [];
|
|
50001
|
-
const
|
|
50002
|
-
for (const seg of
|
|
49779
|
+
const path14 = _path.map((seg) => typeof seg === "object" ? seg.key : seg);
|
|
49780
|
+
for (const seg of path14) {
|
|
50003
49781
|
if (typeof seg === "number")
|
|
50004
49782
|
segs.push(`[${seg}]`);
|
|
50005
49783
|
else if (typeof seg === "symbol")
|
|
@@ -62691,13 +62469,13 @@ function resolveRef(ref2, ctx) {
|
|
|
62691
62469
|
if (!ref2.startsWith("#")) {
|
|
62692
62470
|
throw new Error("External $ref is not supported, only local refs (#/...) are allowed");
|
|
62693
62471
|
}
|
|
62694
|
-
const
|
|
62695
|
-
if (
|
|
62472
|
+
const path14 = ref2.slice(1).split("/").filter(Boolean);
|
|
62473
|
+
if (path14.length === 0) {
|
|
62696
62474
|
return ctx.rootSchema;
|
|
62697
62475
|
}
|
|
62698
62476
|
const defsKey = ctx.version === "draft-2020-12" ? "$defs" : "definitions";
|
|
62699
|
-
if (
|
|
62700
|
-
const key =
|
|
62477
|
+
if (path14[0] === defsKey) {
|
|
62478
|
+
const key = path14[1];
|
|
62701
62479
|
if (!key || !ctx.defs[key]) {
|
|
62702
62480
|
throw new Error(`Reference not found: ${ref2}`);
|
|
62703
62481
|
}
|
|
@@ -66049,15 +65827,21 @@ var appSchema = zod_default.object({
|
|
|
66049
65827
|
"Alias \u2192 agent declaration map. Each alias binds a streaming tool-loop agent the app runs via `useAgentRun(alias)` (an SSE stream), with declared tools, model, and typed inputs/outputs. Synced from the app's `lotics.agents` manifest on every deploy. The agent runs under the app's IAM principal; runs persist a flat history per session."
|
|
66050
65828
|
),
|
|
66051
65829
|
theme: appThemeSchema.nullable().optional().describe("Theme settings for the app"),
|
|
66052
|
-
|
|
66053
|
-
|
|
66054
|
-
|
|
66055
|
-
|
|
66056
|
-
|
|
66057
|
-
|
|
66058
|
-
|
|
66059
|
-
|
|
66060
|
-
|
|
65830
|
+
/**
|
|
65831
|
+
* The starter this app is the ORIGIN of, when it is one — list enrichment,
|
|
65832
|
+
* read from the registry rather than stored on the app.
|
|
65833
|
+
*
|
|
65834
|
+
* This is provenance in the only direction that exists under one-way copies:
|
|
65835
|
+
* an app can have PUBLISHED a starter, but an app that was COPIED FROM one
|
|
65836
|
+
* records nothing, because it owns everything it received outright. Null for
|
|
65837
|
+
* every app that has published nothing.
|
|
65838
|
+
*/
|
|
65839
|
+
starter_origin: zod_default.object({
|
|
65840
|
+
starter_id: zod_default.string(),
|
|
65841
|
+
/** The highest version published from this app. */
|
|
65842
|
+
version: zod_default.number().int(),
|
|
65843
|
+
is_official: zod_default.boolean()
|
|
65844
|
+
}).nullable().optional(),
|
|
66061
65845
|
created_at: zod_default.string().describe("Timestamp when app was created"),
|
|
66062
65846
|
updated_at: zod_default.string().describe("Timestamp of last update")
|
|
66063
65847
|
});
|
|
@@ -67407,9 +67191,9 @@ __export(expression_object_exports, {
|
|
|
67407
67191
|
pick: () => pick3,
|
|
67408
67192
|
values: () => values2
|
|
67409
67193
|
});
|
|
67410
|
-
function getNestedValue(obj,
|
|
67194
|
+
function getNestedValue(obj, path14) {
|
|
67411
67195
|
if (obj == null) return void 0;
|
|
67412
|
-
const parts =
|
|
67196
|
+
const parts = path14.split(".");
|
|
67413
67197
|
let value2 = obj;
|
|
67414
67198
|
for (const part of parts) {
|
|
67415
67199
|
if (value2 == null) return void 0;
|
|
@@ -67448,11 +67232,11 @@ function entries(obj) {
|
|
|
67448
67232
|
}
|
|
67449
67233
|
return Object.entries(obj);
|
|
67450
67234
|
}
|
|
67451
|
-
function get(obj,
|
|
67452
|
-
if (typeof
|
|
67235
|
+
function get(obj, path14, defaultValue) {
|
|
67236
|
+
if (typeof path14 !== "string") {
|
|
67453
67237
|
throw new Error("get: path must be a string");
|
|
67454
67238
|
}
|
|
67455
|
-
const value2 = getNestedValue(obj,
|
|
67239
|
+
const value2 = getNestedValue(obj, path14);
|
|
67456
67240
|
return value2 !== void 0 ? value2 : defaultValue;
|
|
67457
67241
|
}
|
|
67458
67242
|
function pick3(obj, fields) {
|
|
@@ -69335,17 +69119,17 @@ function readFromChanges(chain2) {
|
|
|
69335
69119
|
if (first3.kind === "bracket-number" || first3.kind === "bracket-expr") {
|
|
69336
69120
|
fail(first3.node, "changes is keyed by field name, not numeric index.");
|
|
69337
69121
|
}
|
|
69338
|
-
const
|
|
69122
|
+
const path14 = [{ at: "key", key: first3.key }];
|
|
69339
69123
|
for (const seg of segments.slice(1)) {
|
|
69340
69124
|
if (seg.kind === "bracket-number") {
|
|
69341
|
-
|
|
69125
|
+
path14.push({ at: "index", index: seg.index });
|
|
69342
69126
|
} else if (seg.kind === "bracket-expr") {
|
|
69343
|
-
|
|
69127
|
+
path14.push({ at: "index", index: seg.expr });
|
|
69344
69128
|
} else {
|
|
69345
|
-
|
|
69129
|
+
path14.push({ at: "key", key: seg.key });
|
|
69346
69130
|
}
|
|
69347
69131
|
}
|
|
69348
|
-
return { kind: "read", source: { from: "trigger_changes" }, path:
|
|
69132
|
+
return { kind: "read", source: { from: "trigger_changes" }, path: path14 };
|
|
69349
69133
|
});
|
|
69350
69134
|
}
|
|
69351
69135
|
var TRIGGER_RECORD_VIEWS = /* @__PURE__ */ new Map([
|
|
@@ -69363,17 +69147,17 @@ function readFromTrigger(chain2) {
|
|
|
69363
69147
|
return view === "trigger_changes" ? readFromChanges(lowered) : readFromRecord(view, lowered);
|
|
69364
69148
|
}
|
|
69365
69149
|
return wrapOptionalGuards(chain2, (segments) => {
|
|
69366
|
-
const
|
|
69150
|
+
const path14 = [];
|
|
69367
69151
|
for (const seg of segments) {
|
|
69368
69152
|
if (seg.kind === "bracket-number") {
|
|
69369
|
-
|
|
69153
|
+
path14.push({ at: "index", index: seg.index });
|
|
69370
69154
|
} else if (seg.kind === "bracket-expr") {
|
|
69371
|
-
|
|
69155
|
+
path14.push({ at: "index", index: seg.expr });
|
|
69372
69156
|
} else {
|
|
69373
|
-
|
|
69157
|
+
path14.push({ at: "key", key: seg.key });
|
|
69374
69158
|
}
|
|
69375
69159
|
}
|
|
69376
|
-
return { kind: "read", source: { from: "trigger" }, path:
|
|
69160
|
+
return { kind: "read", source: { from: "trigger" }, path: path14 };
|
|
69377
69161
|
});
|
|
69378
69162
|
}
|
|
69379
69163
|
function readFromRuntime(chain2) {
|
|
@@ -69395,17 +69179,17 @@ function readFromRuntime(chain2) {
|
|
|
69395
69179
|
const parked = PARKED_RUNTIME_KEYS.get(key);
|
|
69396
69180
|
if (parked) fail(first3.node, parked, parkedRuntimeKeyConstruct(key));
|
|
69397
69181
|
const source = { from: "runtime", key };
|
|
69398
|
-
const
|
|
69182
|
+
const path14 = [];
|
|
69399
69183
|
for (const seg of segments.slice(1)) {
|
|
69400
69184
|
if (seg.kind === "bracket-number") {
|
|
69401
|
-
|
|
69185
|
+
path14.push({ at: "index", index: seg.index });
|
|
69402
69186
|
} else if (seg.kind === "bracket-expr") {
|
|
69403
|
-
|
|
69187
|
+
path14.push({ at: "index", index: seg.expr });
|
|
69404
69188
|
} else {
|
|
69405
|
-
|
|
69189
|
+
path14.push({ at: "key", key: seg.key });
|
|
69406
69190
|
}
|
|
69407
69191
|
}
|
|
69408
|
-
return { kind: "read", source, path:
|
|
69192
|
+
return { kind: "read", source, path: path14 };
|
|
69409
69193
|
});
|
|
69410
69194
|
}
|
|
69411
69195
|
function readFromForeachItem(chain2) {
|
|
@@ -69441,17 +69225,17 @@ function readFromLexical(name2, chain2) {
|
|
|
69441
69225
|
}
|
|
69442
69226
|
function readFromStepOutput(stepId, chain2) {
|
|
69443
69227
|
return wrapOptionalGuards(chain2, (segments) => {
|
|
69444
|
-
const
|
|
69228
|
+
const path14 = [];
|
|
69445
69229
|
for (const seg of segments) {
|
|
69446
69230
|
if (seg.kind === "bracket-number") {
|
|
69447
|
-
|
|
69231
|
+
path14.push({ at: "index", index: seg.index });
|
|
69448
69232
|
} else if (seg.kind === "bracket-expr") {
|
|
69449
|
-
|
|
69233
|
+
path14.push({ at: "index", index: seg.expr });
|
|
69450
69234
|
} else {
|
|
69451
|
-
|
|
69235
|
+
path14.push({ at: "key", key: seg.key });
|
|
69452
69236
|
}
|
|
69453
69237
|
}
|
|
69454
|
-
return { kind: "read", source: { from: "step_output", step_id: stepId }, path:
|
|
69238
|
+
return { kind: "read", source: { from: "step_output", step_id: stepId }, path: path14 };
|
|
69455
69239
|
});
|
|
69456
69240
|
}
|
|
69457
69241
|
function classifyRecordPath(segs) {
|
|
@@ -71202,1081 +70986,6 @@ function checkWorkflowBodies(tsApi, aliases) {
|
|
|
71202
70986
|
}));
|
|
71203
70987
|
}
|
|
71204
70988
|
|
|
71205
|
-
// ../shared/src/schemas/table_fields.ts
|
|
71206
|
-
var tableFieldTypeNameSchema = zod_default.enum([
|
|
71207
|
-
"text",
|
|
71208
|
-
"number",
|
|
71209
|
-
"date",
|
|
71210
|
-
"boolean",
|
|
71211
|
-
"select",
|
|
71212
|
-
"select_member",
|
|
71213
|
-
"select_record_link",
|
|
71214
|
-
"files",
|
|
71215
|
-
"formula",
|
|
71216
|
-
"rollup",
|
|
71217
|
-
"lookup",
|
|
71218
|
-
"button",
|
|
71219
|
-
"autonumber"
|
|
71220
|
-
]);
|
|
71221
|
-
var tableFieldBaseSchema = zod_default.object({
|
|
71222
|
-
key: zod_default.string().describe("Unique field key"),
|
|
71223
|
-
name: zod_default.string().describe("Display name"),
|
|
71224
|
-
description: zod_default.string().describe("Field description"),
|
|
71225
|
-
confirm_before_update: zod_default.boolean().optional().describe("Show confirmation before AI updates")
|
|
71226
|
-
});
|
|
71227
|
-
var numberFormatSchema = zod_default.enum(["number", "currency", "percentage"]);
|
|
71228
|
-
var textFormatSchema = zod_default.enum(["text", "link", "markdown"]);
|
|
71229
|
-
var dateFormatSchema = zod_default.enum(["date", "datetime", "date_range", "datetime_range"]);
|
|
71230
|
-
var DEFAULT_VALUE_DESC = "Value pre-filled into a new record when none is supplied for this field. Applied on create only \u2014 existing records are never backfilled. null clears it.";
|
|
71231
|
-
var textDefaultValueSchema = zod_default.string().nullish().describe(DEFAULT_VALUE_DESC);
|
|
71232
|
-
var numberDefaultValueSchema = zod_default.number().nullish().describe(DEFAULT_VALUE_DESC);
|
|
71233
|
-
var booleanDefaultValueSchema = zod_default.boolean().nullish().describe(DEFAULT_VALUE_DESC);
|
|
71234
|
-
var dateDefaultValueSchema = zod_default.string().nullish().describe(`${DEFAULT_VALUE_DESC} A date string in the field's format.`);
|
|
71235
|
-
var selectDefaultValueSchema = zod_default.array(zod_default.string()).nullish().describe(`${DEFAULT_VALUE_DESC} Option key(s) \u2014 one for single-select.`);
|
|
71236
|
-
var memberDefaultValueSchema = zod_default.array(zod_default.string()).nullish().describe(`${DEFAULT_VALUE_DESC} Member ID(s) \u2014 one for single-select.`);
|
|
71237
|
-
var tableNumberFieldSchema = tableFieldBaseSchema.extend({
|
|
71238
|
-
type: zod_default.literal("number"),
|
|
71239
|
-
format: numberFormatSchema,
|
|
71240
|
-
currency: zod_default.string().optional().describe("ISO 4217 code"),
|
|
71241
|
-
default_value: numberDefaultValueSchema
|
|
71242
|
-
});
|
|
71243
|
-
var tableTextFieldSchema = tableFieldBaseSchema.extend({
|
|
71244
|
-
type: zod_default.literal("text"),
|
|
71245
|
-
unique: zod_default.boolean().optional().describe("Unique values required"),
|
|
71246
|
-
// it's `optional` only for backward compatibility
|
|
71247
|
-
format: textFormatSchema.optional(),
|
|
71248
|
-
default_value: textDefaultValueSchema
|
|
71249
|
-
});
|
|
71250
|
-
var tableDateFieldSchema = tableFieldBaseSchema.extend({
|
|
71251
|
-
type: zod_default.literal("date"),
|
|
71252
|
-
format: dateFormatSchema.optional(),
|
|
71253
|
-
timezone: zod_default.string().optional().describe("IANA timezone"),
|
|
71254
|
-
derive_from: zod_default.enum(["created_at", "updated_at"]).optional().describe(
|
|
71255
|
-
"Auto-populate from the row's system timestamp. `created_at` stamps once at insert time; `updated_at` re-stamps on every record edit. Derived fields are read-only \u2014 user-supplied values are silently ignored at write time, matching the formula/rollup/lookup pattern. Replaces the per-table after_create workflow pattern."
|
|
71256
|
-
),
|
|
71257
|
-
// A derived date is read-only, so derive_from and default_value are mutually
|
|
71258
|
-
// exclusive — enforced in validateFieldDefaultValue.
|
|
71259
|
-
default_value: dateDefaultValueSchema
|
|
71260
|
-
});
|
|
71261
|
-
var tableBooleanFieldSchema = tableFieldBaseSchema.extend({
|
|
71262
|
-
type: zod_default.literal("boolean"),
|
|
71263
|
-
default_value: booleanDefaultValueSchema
|
|
71264
|
-
});
|
|
71265
|
-
var tableSelectFieldOptionSchema = zod_default.object({
|
|
71266
|
-
key: zod_default.string(),
|
|
71267
|
-
name: zod_default.string(),
|
|
71268
|
-
color: optionColorSchema
|
|
71269
|
-
});
|
|
71270
|
-
var tableSelectFieldSchema = tableFieldBaseSchema.extend({
|
|
71271
|
-
type: zod_default.literal("select"),
|
|
71272
|
-
options: zod_default.array(tableSelectFieldOptionSchema),
|
|
71273
|
-
multi: zod_default.boolean().optional().describe("Allow multiple selections"),
|
|
71274
|
-
default_value: selectDefaultValueSchema
|
|
71275
|
-
});
|
|
71276
|
-
var tableSelectMemberFieldSchema = tableFieldBaseSchema.extend({
|
|
71277
|
-
type: zod_default.literal("select_member"),
|
|
71278
|
-
multi: zod_default.boolean().optional().describe("Allow multiple selections"),
|
|
71279
|
-
default_value: memberDefaultValueSchema
|
|
71280
|
-
});
|
|
71281
|
-
var recordLinkItemSchema = zod_default.object({
|
|
71282
|
-
id: zod_default.string(),
|
|
71283
|
-
display: zod_default.string()
|
|
71284
|
-
});
|
|
71285
|
-
var selectRecordLinkValueSchema = zod_default.array(recordLinkItemSchema);
|
|
71286
|
-
var tableSelectRecordLinkFieldInputSchema = tableFieldBaseSchema.extend({
|
|
71287
|
-
type: zod_default.literal("select_record_link"),
|
|
71288
|
-
table_id: zod_default.string().describe("Linked table ID"),
|
|
71289
|
-
display_field_keys: zod_default.array(zod_default.string()).optional().describe(
|
|
71290
|
-
"Field keys of the linked table shown as the link's display text and as the columns in the record picker. If omitted, auto-selects the first text field."
|
|
71291
|
-
),
|
|
71292
|
-
display_field_widths: zod_default.record(zod_default.string(), zod_default.number().int().positive()).optional().describe(
|
|
71293
|
-
"Per-column widths in pixels for the record picker, keyed by linked-table field key. Missing keys fall back to the default column width."
|
|
71294
|
-
),
|
|
71295
|
-
sync_both_ways: zod_default.boolean().optional().describe("Enable bidirectional link sync. If the target table has exactly one existing unpaired link field pointing back, pairs with it instead of creating a new field."),
|
|
71296
|
-
paired_field_display_field_keys: zod_default.array(zod_default.string()).optional().describe("Display fields for paired link"),
|
|
71297
|
-
paired_field_name: zod_default.string().optional().describe(
|
|
71298
|
-
"Name for the auto-created paired field on the target table when sync_both_ways=true. If omitted, falls back to the source table's name (auto-uniquified with a numeric suffix on collision). Rejected as a conflict if a field with this name already exists on the target."
|
|
71299
|
-
),
|
|
71300
|
-
cardinality: zod_default.enum(["one", "many"]).optional().describe(
|
|
71301
|
-
"How many linked records this field can hold. Default 'many' (multi-select). 'one' = single-select; this side holds exactly one link to the partner. Requires sync_both_ways/paired_field_key. Setting 'one' on both paired sides is rejected."
|
|
71302
|
-
)
|
|
71303
|
-
});
|
|
71304
|
-
var tableSelectRecordLinkFieldSchema = tableFieldBaseSchema.extend({
|
|
71305
|
-
type: zod_default.literal("select_record_link").describe("Field type for linking to records in another table"),
|
|
71306
|
-
table_id: zod_default.string().describe("ID of the target table that records can be linked to"),
|
|
71307
|
-
display_field_keys: zod_default.array(zod_default.string()).optional().default([]).describe(
|
|
71308
|
-
"Field keys of the linked table shown as the link's display text and as the columns in the record picker. If empty, the picker shows all fields."
|
|
71309
|
-
),
|
|
71310
|
-
display_field_widths: zod_default.record(zod_default.string(), zod_default.number().int().positive()).optional().describe(
|
|
71311
|
-
"Per-column widths in pixels for the record picker, keyed by linked-table field key. Missing keys fall back to the default column width."
|
|
71312
|
-
),
|
|
71313
|
-
paired_field_key: zod_default.string().optional().describe(
|
|
71314
|
-
"Key of the paired link field in the linked table. If set to a string, this indicates a bidirectional link where both tables can reference each other and data synchronizes in both directions. Both fields have paired_field_key pointing to each other. If set to null, explicitly disconnects the bidirectional link (clears paired_field_key on both sides). If undefined, no change is made to the existing paired_field_key."
|
|
71315
|
-
),
|
|
71316
|
-
cardinality: zod_default.enum(["one", "many"]).optional().describe(
|
|
71317
|
-
"How many linked records this field can hold. Default 'many' (multi-select). 'one' = single-select; this side holds exactly one link to the partner. Requires paired_field_key. Two paired sides cannot both be 'one'."
|
|
71318
|
-
)
|
|
71319
|
-
});
|
|
71320
|
-
var tableRollupFieldSchema = tableFieldBaseSchema.extend({
|
|
71321
|
-
type: zod_default.literal("rollup").describe(
|
|
71322
|
-
"Field type for aggregating values from linked records (sum, avg, filled, earliest, etc.)"
|
|
71323
|
-
),
|
|
71324
|
-
source_field_key: zod_default.string().describe("The field key of the select_record_link field to rollup from"),
|
|
71325
|
-
aggregate_option: aggregateOptionSchema.describe(
|
|
71326
|
-
"The field aggregation function to apply (e.g., sum, avg, filled, earliest)"
|
|
71327
|
-
),
|
|
71328
|
-
filter: tableRecordFiltersGroupNodeSchema.optional().describe(
|
|
71329
|
-
"Optional filter to apply to linked records before aggregation. Only records matching the filter conditions will be included in the rollup calculation."
|
|
71330
|
-
),
|
|
71331
|
-
aggregate_field_type: tableFieldTypeNameSchema.optional().describe(
|
|
71332
|
-
"What this rollup's CELL holds \u2014 'date' for earliest/latest, 'number' for every other operation (counts, sums, percentages). Derived from the operation, not from the aggregated field: a 'filled' count over a files column is a number. Server-derived at write time; ignored on input."
|
|
71333
|
-
),
|
|
71334
|
-
aggregate_field_format: zod_default.string().optional().describe(
|
|
71335
|
-
"The format of this rollup's own value. Operations that preserve the aggregated value's unit (sum/avg/median/min/max/range/earliest/latest) inherit the target field's format; counting operations are 'number', percentages 'percentage'. Server-derived at write time; ignored on input."
|
|
71336
|
-
),
|
|
71337
|
-
aggregate_field_currency: zod_default.string().optional().describe(
|
|
71338
|
-
"The currency code of this rollup's own value (e.g. 'USD', 'VND'), inherited from the aggregated field only when the operation preserves its unit \u2014 a COUNT of a currency column carries no currency. Server-derived at write time; ignored on input."
|
|
71339
|
-
)
|
|
71340
|
-
});
|
|
71341
|
-
var lookupOrderBySchema = zod_default.object({
|
|
71342
|
-
field_key: zod_default.string(),
|
|
71343
|
-
direction: zod_default.enum(["asc", "desc"])
|
|
71344
|
-
});
|
|
71345
|
-
var tableLookupFieldSchema = tableFieldBaseSchema.extend({
|
|
71346
|
-
type: zod_default.literal("lookup").describe("Field type for displaying values from fields in linked records"),
|
|
71347
|
-
source_field_key: zod_default.string().describe("The field key of the select_record_link field to lookup from"),
|
|
71348
|
-
lookup_field_key: zod_default.string().describe("The field key from the linked records to display"),
|
|
71349
|
-
lookup_field_type: tableFieldTypeNameSchema.optional().describe(
|
|
71350
|
-
"The type of the target lookup field (e.g. 'text', 'number', 'date'). Resolved from the linked table's field definition at read time."
|
|
71351
|
-
),
|
|
71352
|
-
lookup_field_format: zod_default.string().optional().describe(
|
|
71353
|
-
"The format of the target lookup field (e.g. 'currency', 'percentage', 'datetime'). Resolved from the linked table's field definition at read time."
|
|
71354
|
-
),
|
|
71355
|
-
lookup_field_currency: zod_default.string().optional().describe(
|
|
71356
|
-
"The currency code of the target lookup field (e.g. 'USD', 'VND'). Resolved from the linked table's field definition at read time."
|
|
71357
|
-
),
|
|
71358
|
-
lookup_field_options: zod_default.array(zod_default.object({ key: zod_default.string(), name: zod_default.string(), color: zod_default.string().optional() })).optional().describe(
|
|
71359
|
-
"Options for select-type lookup fields. Synced from the source select field's options."
|
|
71360
|
-
),
|
|
71361
|
-
order_by: lookupOrderBySchema.optional().describe(
|
|
71362
|
-
"When set, sort the linked records by this field on the linked table and return ONLY the picked field from the single extreme record (desc=latest, asc=earliest), as a one-element array. Omit to return every linked record's value as an array. field_key must be a field on the linked table."
|
|
71363
|
-
)
|
|
71364
|
-
});
|
|
71365
|
-
var tableFilesFieldSchema = tableFieldBaseSchema.extend({
|
|
71366
|
-
type: zod_default.literal("files").describe("Field type for file attachments (images, PDFs, documents)")
|
|
71367
|
-
});
|
|
71368
|
-
var formulaInputSchema = zod_default.object({
|
|
71369
|
-
expression: zod_default.string().describe(
|
|
71370
|
-
"JavaScript expression. Uses {Field Name} for field references."
|
|
71371
|
-
),
|
|
71372
|
-
format: zod_default.enum(["number", "currency", "percentage", "link"]).optional().describe(
|
|
71373
|
-
"Display format. 'number' / 'currency' / 'percentage' for numeric results; 'link' for text-output formulas that return a URL \u2014 renders the result as a clickable link."
|
|
71374
|
-
),
|
|
71375
|
-
currency: zod_default.string().optional().describe("ISO 4217 currency code, e.g. USD, VND, EUR")
|
|
71376
|
-
});
|
|
71377
|
-
var formulaSchema = formulaInputSchema.extend({
|
|
71378
|
-
output_type: zod_default.enum(["number", "text", "date", "datetime", "boolean"]).optional().describe("Output type of the formula. Inferred by the backend from the expression \u2014 read-only on input. `datetime` when the result carries a time of day (references a datetime field or a time-bearing helper)."),
|
|
71379
|
-
volatile: zod_default.boolean().optional().describe("Whether the formula's result depends on `now()` or other non-deterministic helpers. Inferred by the backend \u2014 read-only on input.")
|
|
71380
|
-
});
|
|
71381
|
-
var tableFormulaFieldSchema = tableFieldBaseSchema.extend({
|
|
71382
|
-
type: zod_default.literal("formula").describe("Field type for calculated values based on expressions"),
|
|
71383
|
-
formula: formulaSchema.describe("Formula configuration and expression")
|
|
71384
|
-
});
|
|
71385
|
-
var workflowMetadataSchema = zod_default.object({
|
|
71386
|
-
table_ids: zod_default.array(zod_default.string()).describe("IDs of the tables this workflow affects"),
|
|
71387
|
-
staged_for_app_id: zod_default.string().optional().describe(
|
|
71388
|
-
"Present while the row is a draft-staged fork for this app; cleared when the app publishes the binding. Marked rows left unbound are archived at publish/discard."
|
|
71389
|
-
)
|
|
71390
|
-
});
|
|
71391
|
-
var workflowSchema = zod_default.object({
|
|
71392
|
-
id: zod_default.string().describe("Unique identifier for the workflow"),
|
|
71393
|
-
name: zod_default.string().describe("Display name of the workflow"),
|
|
71394
|
-
description: zod_default.string().describe("Human-readable description of what this workflow does"),
|
|
71395
|
-
steps: zod_default.unknown().describe(
|
|
71396
|
-
"AST-valued step tree (tool calls, conditionals, loops)."
|
|
71397
|
-
),
|
|
71398
|
-
metadata: workflowMetadataSchema.nullable().optional().describe("Metadata for the workflow"),
|
|
71399
|
-
current_version: zod_default.number().int().describe("Current version number"),
|
|
71400
|
-
enabled: zod_default.boolean().describe("Whether this workflow is active"),
|
|
71401
|
-
workspace_id: zod_default.string().describe("ID of the workspace this workflow belongs to"),
|
|
71402
|
-
created_at: zod_default.string().describe("Timestamp when workflow was created"),
|
|
71403
|
-
updated_at: zod_default.string().describe("Timestamp of last update")
|
|
71404
|
-
});
|
|
71405
|
-
var tableButtonFieldSchema = tableFieldBaseSchema.extend({
|
|
71406
|
-
type: zod_default.literal("button").describe("Field type for action buttons"),
|
|
71407
|
-
text: zod_default.string().describe("Button label text displayed to users"),
|
|
71408
|
-
workflow_id: zod_default.string().nullable().optional().describe(
|
|
71409
|
-
"ID of the workflow the button presses trigger. Null means no action configured \u2014 pressing the button is a no-op. Button authoring is retired: existing bindings keep running, but nothing sets a new one."
|
|
71410
|
-
)
|
|
71411
|
-
});
|
|
71412
|
-
var tableAutonumberFieldSchema = tableFieldBaseSchema.extend({
|
|
71413
|
-
type: zod_default.literal("autonumber"),
|
|
71414
|
-
prefix: zod_default.string().optional().describe(
|
|
71415
|
-
"Literal prefix prepended to every display value (e.g. 'KH-' \u2192 'KH-001'). Ignored when `template` is set."
|
|
71416
|
-
),
|
|
71417
|
-
padding: zod_default.number().int().min(1).max(20).optional().describe(
|
|
71418
|
-
"Zero-pad the integer to this width. Default 1 (no padding). 3 \u2192 '001', '012', '123', '1234' (overflow uses the actual width). Ignored when `template` is set."
|
|
71419
|
-
),
|
|
71420
|
-
template: zod_default.string().optional().describe(
|
|
71421
|
-
"Format template with placeholder tokens evaluated at insert time. Tokens: {N} (raw integer), {N:W} (zero-padded to width W, e.g. {N:3} \u2192 001), {YEAR} (4-digit year), {YEAR:2} (2-digit year), {MONTH} (2-digit month), {DAY} (2-digit day). Date tokens use the workspace timezone. Example: 'HM-{YEAR}-{N:3}' yields 'HM-2026-001'. Stored as the composed string; subsequent template edits do NOT re-format existing rows (date tokens would lose the original creation date)."
|
|
71422
|
-
)
|
|
71423
|
-
});
|
|
71424
|
-
var tableFieldSchema = zod_default.discriminatedUnion("type", [
|
|
71425
|
-
tableNumberFieldSchema,
|
|
71426
|
-
tableTextFieldSchema,
|
|
71427
|
-
tableDateFieldSchema,
|
|
71428
|
-
tableBooleanFieldSchema,
|
|
71429
|
-
tableSelectFieldSchema,
|
|
71430
|
-
tableSelectMemberFieldSchema,
|
|
71431
|
-
tableSelectRecordLinkFieldSchema,
|
|
71432
|
-
tableRollupFieldSchema,
|
|
71433
|
-
tableLookupFieldSchema,
|
|
71434
|
-
tableFilesFieldSchema,
|
|
71435
|
-
tableFormulaFieldSchema,
|
|
71436
|
-
tableButtonFieldSchema,
|
|
71437
|
-
tableAutonumberFieldSchema
|
|
71438
|
-
]);
|
|
71439
|
-
var tableFieldInputSchema = zod_default.discriminatedUnion("type", [
|
|
71440
|
-
tableNumberFieldSchema,
|
|
71441
|
-
tableTextFieldSchema,
|
|
71442
|
-
tableDateFieldSchema,
|
|
71443
|
-
tableBooleanFieldSchema,
|
|
71444
|
-
tableSelectFieldSchema,
|
|
71445
|
-
tableSelectMemberFieldSchema,
|
|
71446
|
-
tableSelectRecordLinkFieldInputSchema,
|
|
71447
|
-
tableRollupFieldSchema,
|
|
71448
|
-
tableLookupFieldSchema,
|
|
71449
|
-
tableFilesFieldSchema,
|
|
71450
|
-
tableFormulaFieldSchema,
|
|
71451
|
-
tableButtonFieldSchema,
|
|
71452
|
-
tableAutonumberFieldSchema
|
|
71453
|
-
]);
|
|
71454
|
-
var tableFieldsSchema = zod_default.array(tableFieldSchema);
|
|
71455
|
-
var tableFieldCreateBaseSchema = zod_default.object({
|
|
71456
|
-
name: zod_default.string().describe("Display name"),
|
|
71457
|
-
description: zod_default.string().describe("Field description"),
|
|
71458
|
-
confirm_before_update: zod_default.boolean().optional().describe("Show confirmation before AI updates")
|
|
71459
|
-
});
|
|
71460
|
-
var tableSelectFieldOptionCreateSchema = zod_default.object({
|
|
71461
|
-
name: zod_default.string(),
|
|
71462
|
-
color: optionColorSchema
|
|
71463
|
-
});
|
|
71464
|
-
var tableFieldTypeConfigSchema = zod_default.discriminatedUnion("type", [
|
|
71465
|
-
zod_default.object({
|
|
71466
|
-
type: zod_default.literal("number"),
|
|
71467
|
-
format: numberFormatSchema.default("number"),
|
|
71468
|
-
currency: zod_default.string().optional().describe("ISO 4217 code"),
|
|
71469
|
-
default_value: numberDefaultValueSchema
|
|
71470
|
-
}),
|
|
71471
|
-
zod_default.object({
|
|
71472
|
-
type: zod_default.literal("text"),
|
|
71473
|
-
unique: zod_default.boolean().optional().describe("Unique values required"),
|
|
71474
|
-
format: textFormatSchema.default("text"),
|
|
71475
|
-
default_value: textDefaultValueSchema
|
|
71476
|
-
}),
|
|
71477
|
-
zod_default.object({
|
|
71478
|
-
type: zod_default.literal("date"),
|
|
71479
|
-
format: dateFormatSchema.optional(),
|
|
71480
|
-
timezone: zod_default.string().optional().describe("IANA timezone"),
|
|
71481
|
-
derive_from: zod_default.enum(["created_at", "updated_at"]).nullable().optional().describe("Auto-populate from row system timestamp; field becomes read-only. Only valid for date/datetime formats. Pass null to clear and revert to a manual date field."),
|
|
71482
|
-
default_value: dateDefaultValueSchema
|
|
71483
|
-
}),
|
|
71484
|
-
zod_default.object({
|
|
71485
|
-
type: zod_default.literal("boolean"),
|
|
71486
|
-
default_value: booleanDefaultValueSchema
|
|
71487
|
-
}),
|
|
71488
|
-
zod_default.object({
|
|
71489
|
-
type: zod_default.literal("select"),
|
|
71490
|
-
options: zod_default.array(tableSelectFieldOptionCreateSchema),
|
|
71491
|
-
multi: zod_default.boolean().optional().describe("Allow multiple selections"),
|
|
71492
|
-
default_value: selectDefaultValueSchema
|
|
71493
|
-
}),
|
|
71494
|
-
zod_default.object({
|
|
71495
|
-
type: zod_default.literal("select_member"),
|
|
71496
|
-
multi: zod_default.boolean().optional().describe("Allow multiple selections"),
|
|
71497
|
-
default_value: memberDefaultValueSchema
|
|
71498
|
-
}),
|
|
71499
|
-
zod_default.object({
|
|
71500
|
-
type: zod_default.literal("select_record_link"),
|
|
71501
|
-
table_id: zod_default.string().describe("Linked table ID"),
|
|
71502
|
-
display_field_keys: zod_default.array(zod_default.string()).optional().describe(
|
|
71503
|
-
"Field keys of the linked table shown as the link's display text and as the columns in the record picker. If omitted, auto-selects the first text field."
|
|
71504
|
-
),
|
|
71505
|
-
display_field_widths: zod_default.record(zod_default.string(), zod_default.number().int().positive()).optional().describe(
|
|
71506
|
-
"Per-column widths in pixels for the record picker, keyed by linked-table field key. Missing keys fall back to the default column width."
|
|
71507
|
-
),
|
|
71508
|
-
sync_both_ways: zod_default.boolean().optional().describe("Enable bidirectional link sync. If the target table has exactly one existing unpaired link field pointing back, pairs with it instead of creating a new field."),
|
|
71509
|
-
paired_field_display_field_keys: zod_default.array(zod_default.string()).optional().describe("Paired field display"),
|
|
71510
|
-
paired_field_name: zod_default.string().optional().describe(
|
|
71511
|
-
"Name for the auto-created paired field on the target table when sync_both_ways=true. Omit to default to the source table's name (auto-uniquified on collision). If supplied and a field with the same name already exists on the target, the create is rejected."
|
|
71512
|
-
),
|
|
71513
|
-
cardinality: zod_default.enum(["one", "many"]).optional().describe(
|
|
71514
|
-
"How many linked records this field can hold. Default 'many' (multi-select). 'one' = single-select; this side holds exactly one link to the partner. Requires sync_both_ways. Two paired sides cannot both be 'one'."
|
|
71515
|
-
)
|
|
71516
|
-
}),
|
|
71517
|
-
zod_default.object({
|
|
71518
|
-
type: zod_default.literal("rollup"),
|
|
71519
|
-
source_field_key: zod_default.string().describe("Source link field key"),
|
|
71520
|
-
aggregate_option: aggregateOptionSchema,
|
|
71521
|
-
filter: tableRecordFiltersGroupNodeSchema.optional().describe("Filter linked records")
|
|
71522
|
-
}),
|
|
71523
|
-
zod_default.object({
|
|
71524
|
-
type: zod_default.literal("lookup"),
|
|
71525
|
-
source_field_key: zod_default.string().describe("Source link field key"),
|
|
71526
|
-
lookup_field_key: zod_default.string().describe("Field to display"),
|
|
71527
|
-
order_by: lookupOrderBySchema.optional().describe("Ordered lookup: pick only the extreme linked record's field (desc=latest, asc=earliest)")
|
|
71528
|
-
}),
|
|
71529
|
-
zod_default.object({
|
|
71530
|
-
type: zod_default.literal("files")
|
|
71531
|
-
}),
|
|
71532
|
-
zod_default.object({
|
|
71533
|
-
type: zod_default.literal("formula"),
|
|
71534
|
-
formula: formulaInputSchema
|
|
71535
|
-
}),
|
|
71536
|
-
// `button` is deliberately absent: button fields are legacy — this union
|
|
71537
|
-
// shapes CREATE input only, and new buttons can no longer be created
|
|
71538
|
-
// (see LEGACY_FIELD_TYPES). Stored button fields still parse via the
|
|
71539
|
-
// stored-field union above, and update paths keep accepting text edits.
|
|
71540
|
-
zod_default.object({
|
|
71541
|
-
type: zod_default.literal("autonumber"),
|
|
71542
|
-
prefix: zod_default.string().optional().describe("Literal prefix prepended to display (ignored when template is set)"),
|
|
71543
|
-
padding: zod_default.number().int().min(1).max(20).optional().describe("Zero-pad the integer to this width (default 1) (ignored when template is set)"),
|
|
71544
|
-
template: zod_default.string().optional().describe(
|
|
71545
|
-
"Format template \u2014 tokens evaluate at insert time: {N}, {N:W} (padded), {YEAR}, {YEAR:2}, {MONTH}, {DAY}. Date tokens use workspace timezone. Example: 'HM-{YEAR}-{N:3}' \u2192 'HM-2026-001'."
|
|
71546
|
-
)
|
|
71547
|
-
})
|
|
71548
|
-
]);
|
|
71549
|
-
var tableFieldCreateInputSchema = zod_default.intersection(
|
|
71550
|
-
tableFieldCreateBaseSchema,
|
|
71551
|
-
tableFieldTypeConfigSchema
|
|
71552
|
-
);
|
|
71553
|
-
var fieldVisibilitySchema = zod_default.enum(["visible", "hidden"]).describe(
|
|
71554
|
-
"Field visibility state: 'visible' = shown to everyone, 'hidden' = not shown by default but members can toggle"
|
|
71555
|
-
);
|
|
71556
|
-
|
|
71557
|
-
// ../shared/src/schemas/field_config.ts
|
|
71558
|
-
var fieldConfigEntrySchema = zod_default.object({
|
|
71559
|
-
key: zod_default.string().min(1).describe("Field key"),
|
|
71560
|
-
visibility: fieldVisibilitySchema,
|
|
71561
|
-
width: zod_default.number().optional()
|
|
71562
|
-
});
|
|
71563
|
-
|
|
71564
|
-
// ../shared/src/schemas/iam.ts
|
|
71565
|
-
var jsonSchemaSchema = zod_default.string();
|
|
71566
|
-
var organizationSchema = zod_default.object({
|
|
71567
|
-
id: zod_default.string().describe("Unique identifier for the organization"),
|
|
71568
|
-
name: zod_default.string().describe("Display name of the organization"),
|
|
71569
|
-
slug: zod_default.string().nullable().describe("Slug for the organization")
|
|
71570
|
-
});
|
|
71571
|
-
var memberSchema = zod_default.object({
|
|
71572
|
-
member_id: zod_default.string().describe("Unique identifier for the member"),
|
|
71573
|
-
organization_id: zod_default.string().describe("Organization ID the member belongs to"),
|
|
71574
|
-
name: zod_default.string().describe("Display name of the member"),
|
|
71575
|
-
email_address: zod_default.string().describe(
|
|
71576
|
-
"What the member types to sign in: an email address for a self-managed member, an administrator-issued name (e.g. giamdoc.sunrise) for an admin-managed one. The latter is NOT an address and cannot receive mail \u2014 the field name predates the split."
|
|
71577
|
-
),
|
|
71578
|
-
role: zod_default.enum(["owner", "admin", "member"]).describe("Organization role"),
|
|
71579
|
-
image: zod_default.string().nullable().optional().describe("URL to the member's profile picture"),
|
|
71580
|
-
account_type: zod_default.enum(["self_managed", "admin_managed"]).describe(
|
|
71581
|
-
"How the account is credentialed. admin_managed means an admin chose the sign-in name and set the password; the account has NO email address at all, so nothing can be mailed to it until the member claims one they control."
|
|
71582
|
-
),
|
|
71583
|
-
archived: zod_default.boolean().optional().describe(
|
|
71584
|
-
"True when this person has been removed from the organization. The membership survives removal so records naming them keep resolving; it grants nothing. Optional because an older server omits it \u2014 absent means active."
|
|
71585
|
-
),
|
|
71586
|
-
joined_at: zod_default.string().optional().describe(
|
|
71587
|
-
"ISO timestamp of when this membership began. Optional because an older server omits it \u2014 absent means not told, never 'joined at the epoch'."
|
|
71588
|
-
)
|
|
71589
|
-
});
|
|
71590
|
-
var pendingInvitationSchema = zod_default.object({
|
|
71591
|
-
invitation_id: zod_default.string().describe("Unique identifier for the pending invitation"),
|
|
71592
|
-
organization_id: zod_default.string().describe("Organization the invitee will join on accept"),
|
|
71593
|
-
email: zod_default.string().describe("Email the invitation was sent to"),
|
|
71594
|
-
name: zod_default.string().nullable().describe("Admin-supplied display name (carried onto member.name on accept; invitee can override at accept time)"),
|
|
71595
|
-
role: zod_default.enum(["owner", "admin", "member"]).describe("Role the invitee will receive on accept"),
|
|
71596
|
-
expires_at: zod_default.string().describe("ISO timestamp when the invitation expires")
|
|
71597
|
-
});
|
|
71598
|
-
var workspaceSchema = zod_default.object({
|
|
71599
|
-
id: zod_default.string().describe("Unique identifier for the workspace"),
|
|
71600
|
-
name: zod_default.string().describe("Display name of the workspace"),
|
|
71601
|
-
default_currency: zod_default.string().describe("Default currency code for the workspace"),
|
|
71602
|
-
timezone: zod_default.string().describe("IANA timezone name (e.g., 'America/New_York', 'Asia/Tokyo')"),
|
|
71603
|
-
organization_id: zod_default.string().describe("Organization ID this workspace belongs to"),
|
|
71604
|
-
created_at: zod_default.string().describe("Timestamp when workspace was created")
|
|
71605
|
-
});
|
|
71606
|
-
var memberGroupSchema = zod_default.object({
|
|
71607
|
-
id: zod_default.string().describe("Unique identifier for the member group"),
|
|
71608
|
-
name: zod_default.string().describe("Display name of the group"),
|
|
71609
|
-
description: zod_default.string().optional().describe("Optional description of the group's purpose"),
|
|
71610
|
-
member_ids: zod_default.array(zod_default.string()).describe("Array of member IDs in this group"),
|
|
71611
|
-
invitation_ids: zod_default.array(zod_default.string()).describe("Array of pending invitation IDs pre-granted membership; migrated to member_ids on accept"),
|
|
71612
|
-
organization_id: zod_default.string().describe("ID of the organization this group belongs to"),
|
|
71613
|
-
created_at: zod_default.string().describe("Timestamp when group was created"),
|
|
71614
|
-
created_by: zod_default.string().describe("Member ID of the user who created this group")
|
|
71615
|
-
});
|
|
71616
|
-
var principalGroupSchema = zod_default.object({
|
|
71617
|
-
id: zod_default.string().describe("Unique identifier for the member group"),
|
|
71618
|
-
name: zod_default.string().describe("Display name of the group"),
|
|
71619
|
-
description: zod_default.string().optional().describe("Optional description of the group's purpose"),
|
|
71620
|
-
member_count: zod_default.number().int().describe("Number of accepted members in the group"),
|
|
71621
|
-
invitation_count: zod_default.number().int().describe("Number of pending invitations pre-granted membership")
|
|
71622
|
-
});
|
|
71623
|
-
var PUBLIC_PRINCIPAL_ID = "public";
|
|
71624
|
-
var principalSchema = zod_default.discriminatedUnion("type", [
|
|
71625
|
-
zod_default.object({
|
|
71626
|
-
type: zod_default.literal("member").describe("Principal type: individual member"),
|
|
71627
|
-
id: zod_default.string().describe("Member ID")
|
|
71628
|
-
}),
|
|
71629
|
-
zod_default.object({
|
|
71630
|
-
type: zod_default.literal("member_group").describe("Principal type: group of members"),
|
|
71631
|
-
id: zod_default.string().describe("Member group ID")
|
|
71632
|
-
}),
|
|
71633
|
-
zod_default.object({
|
|
71634
|
-
type: zod_default.literal("organization").describe("Principal type: all members in organization"),
|
|
71635
|
-
id: zod_default.string().describe("Organization ID")
|
|
71636
|
-
}),
|
|
71637
|
-
zod_default.object({
|
|
71638
|
-
type: zod_default.literal("public").describe("Principal type: anyone, including unauthenticated visitors"),
|
|
71639
|
-
id: zod_default.literal(PUBLIC_PRINCIPAL_ID).describe("Always the `public` sentinel \u2014 no entity")
|
|
71640
|
-
}),
|
|
71641
|
-
// Pending invitation as principal: lets admins pre-grant group membership and
|
|
71642
|
-
// resource access before the invitee accepts. Never resolved as a Subject —
|
|
71643
|
-
// a pending invitee cannot authenticate, so these bindings stay dormant until
|
|
71644
|
-
// accept-time migration rewrites them to type:"member".
|
|
71645
|
-
zod_default.object({
|
|
71646
|
-
type: zod_default.literal("invitation").describe("Principal type: pending invitation (not yet accepted)"),
|
|
71647
|
-
id: zod_default.string().describe("Invitation ID")
|
|
71648
|
-
})
|
|
71649
|
-
]);
|
|
71650
|
-
var subjectSchema = zod_default.discriminatedUnion("type", [
|
|
71651
|
-
zod_default.object({
|
|
71652
|
-
type: zod_default.literal("member").describe("Subject type: authenticated member"),
|
|
71653
|
-
id: zod_default.string().describe("Member ID")
|
|
71654
|
-
}),
|
|
71655
|
-
zod_default.object({
|
|
71656
|
-
type: zod_default.literal("public").describe("Subject type: unauthenticated visitor")
|
|
71657
|
-
})
|
|
71658
|
-
]);
|
|
71659
|
-
var resourceTypeSchema = zod_default.enum(["table", "table_view", "app", "automation", "skill", "document_template", "instruction", "knowledge_doc"]);
|
|
71660
|
-
var accessPrincipalSchema = zod_default.discriminatedUnion("type", [
|
|
71661
|
-
zod_default.object({
|
|
71662
|
-
type: zod_default.literal("member").describe("Principal type: an individual member"),
|
|
71663
|
-
id: zod_default.string().describe("Member ID")
|
|
71664
|
-
}),
|
|
71665
|
-
zod_default.object({
|
|
71666
|
-
type: zod_default.literal("member_group").describe("Principal type: a member group"),
|
|
71667
|
-
id: zod_default.string().describe("Group ID")
|
|
71668
|
-
}),
|
|
71669
|
-
zod_default.object({
|
|
71670
|
-
type: zod_default.literal("organization").describe("Principal type: everyone in the organization"),
|
|
71671
|
-
id: zod_default.string().describe("Organization ID")
|
|
71672
|
-
})
|
|
71673
|
-
]);
|
|
71674
|
-
var resourceAccessSchema = zod_default.object({
|
|
71675
|
-
resource_id: zod_default.string().describe("ID of the resource these principals can reach"),
|
|
71676
|
-
principals: zod_default.array(accessPrincipalSchema).describe("Members, groups and the organization that have been granted access")
|
|
71677
|
-
});
|
|
71678
|
-
var resourceRoleBindingSchema = zod_default.object({
|
|
71679
|
-
id: zod_default.string().describe("Unique identifier for the role binding"),
|
|
71680
|
-
principal: principalSchema.describe(
|
|
71681
|
-
"Who this role binding applies to (member, group, or organization)"
|
|
71682
|
-
),
|
|
71683
|
-
resource_type: resourceTypeSchema.describe("Type of resource being accessed"),
|
|
71684
|
-
resource_id: zod_default.string().describe("ID of the specific resource"),
|
|
71685
|
-
role: zod_default.string().describe("Role name (e.g., 'viewer', 'editor', 'manager', 'user')")
|
|
71686
|
-
});
|
|
71687
|
-
|
|
71688
|
-
// ../shared/src/schemas/table_records.ts
|
|
71689
|
-
var tableWorkflowEventSchema = zod_default.enum([
|
|
71690
|
-
"before_create",
|
|
71691
|
-
"after_create",
|
|
71692
|
-
"before_update",
|
|
71693
|
-
"after_update",
|
|
71694
|
-
"before_delete",
|
|
71695
|
-
"after_delete"
|
|
71696
|
-
]);
|
|
71697
|
-
var tableWorkflowSchema = zod_default.object({
|
|
71698
|
-
id: zod_default.string().describe("Unique table-workflow binding ID (tbw_ prefix)"),
|
|
71699
|
-
name: zod_default.string().describe("Human-readable name"),
|
|
71700
|
-
description: zod_default.string().describe("Description of what this workflow does"),
|
|
71701
|
-
enabled: zod_default.boolean().describe("Whether this workflow is active"),
|
|
71702
|
-
event: tableWorkflowEventSchema.describe(
|
|
71703
|
-
"Lifecycle event that fires this workflow. before_* runs synchronously and may reject the mutation; after_* runs after commit and does not block."
|
|
71704
|
-
),
|
|
71705
|
-
workflow_id: zod_default.string().describe(
|
|
71706
|
-
"ID of the workflow row that owns this binding's steps. The workflow's steps_v2 is the source of truth for the AST."
|
|
71707
|
-
),
|
|
71708
|
-
// Recursive v2 expression AST. Lazy schema would crash the OpenAPI walker;
|
|
71709
|
-
// runtime is `unknown` and the casted Zod type preserves the compile-time
|
|
71710
|
-
// signature for callers. Write paths re-parse with the strict schema before
|
|
71711
|
-
// storage.
|
|
71712
|
-
if: zod_default.unknown().nullable().optional().describe(
|
|
71713
|
-
"Optional pre-execution gate. Evaluated against the trigger context (record / prev_record / changes / runtime); the workflow fires only when truthy. Skip gating means the workflow always fires."
|
|
71714
|
-
),
|
|
71715
|
-
created_at: zod_default.string().describe("When the binding was created"),
|
|
71716
|
-
updated_at: zod_default.string().describe("When the binding was last modified"),
|
|
71717
|
-
archived_at: zod_default.string().nullable().optional().describe(
|
|
71718
|
-
"Set when the binding was removed (soft-delete). An archived binding never fires and is hidden from active listings, but is restorable; null/absent = active."
|
|
71719
|
-
)
|
|
71720
|
-
});
|
|
71721
|
-
var tableWorkflowMessageSchema = zod_default.object({
|
|
71722
|
-
table_workflow_id: zod_default.string().describe("tbw_* binding that emitted the message."),
|
|
71723
|
-
workflow_name: zod_default.string().describe("Human name of the workflow at execution time."),
|
|
71724
|
-
event: tableWorkflowEventSchema.describe(
|
|
71725
|
-
"Lifecycle event that produced the message. Only before_* events can surface here."
|
|
71726
|
-
),
|
|
71727
|
-
record_id: zod_default.string().describe(
|
|
71728
|
-
"Record that triggered the workflow. Lets the UI scope the message to a specific row in bulk responses."
|
|
71729
|
-
),
|
|
71730
|
-
message: zod_default.string().describe("Author-provided text from the workflow's return.message.")
|
|
71731
|
-
});
|
|
71732
|
-
var tableSchema = zod_default.object({
|
|
71733
|
-
id: zod_default.string().describe("Unique identifier for the table"),
|
|
71734
|
-
workspace_id: zod_default.string().describe("ID of the workspace this table belongs to"),
|
|
71735
|
-
name: zod_default.string().describe("Display name of the table"),
|
|
71736
|
-
description: zod_default.string().describe("Description of the table's purpose"),
|
|
71737
|
-
position: zod_default.number().int().optional().nullable().describe("Display ordering index for the table. Lower numbers are shown first. "),
|
|
71738
|
-
fields: tableFieldsSchema.describe("Array of field definitions for this table"),
|
|
71739
|
-
workflows: zod_default.array(tableWorkflowSchema).optional().describe(
|
|
71740
|
-
"Workflows attached to this table that fire around record mutations. before_* run synchronously and may reject; after_* run after commit and do not block."
|
|
71741
|
-
),
|
|
71742
|
-
private_filters: tableRecordFiltersGroupNodeSchema.nullable().optional().describe("Row-level private filters AND'd to every query as a security boundary (admin bypass)"),
|
|
71743
|
-
colors: tableRecordColorsSchema.nullable().optional().describe("Color rules for styling records based on filter conditions"),
|
|
71744
|
-
approvers: zod_default.array(principalSchema).nullable().optional().describe(
|
|
71745
|
-
"Principals (members, groups, or the organization) who review locked-record change requests on this table. Null/empty = organization admins review. The requester never reviews their own request."
|
|
71746
|
-
),
|
|
71747
|
-
created_at: zod_default.string().describe("Timestamp when table was created")
|
|
71748
|
-
});
|
|
71749
|
-
var recordDataTemplateSchema = zod_default.object({
|
|
71750
|
-
id: zod_default.string().describe("Unique identifier for the record data template"),
|
|
71751
|
-
name: zod_default.string().describe("Display name of the record data template"),
|
|
71752
|
-
description: zod_default.string().describe("Description of the record data template"),
|
|
71753
|
-
table_id: zod_default.string().describe("ID of the table this record template belongs to"),
|
|
71754
|
-
data: zod_default.record(zod_default.string(), zod_default.unknown()).describe("The data of the record template. The key is the Field key.")
|
|
71755
|
-
});
|
|
71756
|
-
var tableRecordSchema = zod_default.object({
|
|
71757
|
-
id: zod_default.string().describe("Unique identifier for the record"),
|
|
71758
|
-
table_id: zod_default.string().describe("ID of the table this record belongs to"),
|
|
71759
|
-
workspace_id: zod_default.string().describe("ID of the workspace this record belongs to"),
|
|
71760
|
-
data: zod_default.record(zod_default.string(), zod_default.unknown()).describe("The data of the record. The key is the Field key."),
|
|
71761
|
-
locked: zod_default.boolean().optional().describe("Whether the entire record is locked from editing"),
|
|
71762
|
-
draft: zod_default.boolean().optional().describe("Whether the record is an unsubmitted draft \u2014 UI-only in-progress state, not yet a real row. Row-visibility scoping is enforced at submit, not while a draft is being filled in."),
|
|
71763
|
-
updated_at: zod_default.string().describe("Timestamp of last update"),
|
|
71764
|
-
created_at: zod_default.string().describe("Timestamp when record was created")
|
|
71765
|
-
});
|
|
71766
|
-
var viewSummaryEntrySchema = zod_default.object({
|
|
71767
|
-
operation: zod_default.string().describe("Operation to perform on the field"),
|
|
71768
|
-
field_key: zod_default.string().describe("Field key to display in the summary row")
|
|
71769
|
-
});
|
|
71770
|
-
var viewSummarySchema = zod_default.record(zod_default.string(), viewSummaryEntrySchema.nullable().optional()).nullable().optional().describe("Map of field keys to summary operations.");
|
|
71771
|
-
var visibleToEntrySchema = zod_default.object({
|
|
71772
|
-
type: zod_default.enum(["member", "group"]).describe("Principal kind that may see the view: an individual member or a member group"),
|
|
71773
|
-
id: zod_default.string().describe("Member ID (type=member) or member-group ID (type=group)")
|
|
71774
|
-
});
|
|
71775
|
-
var visibleToSchema = zod_default.array(visibleToEntrySchema).nullable();
|
|
71776
|
-
var tableViewSchema = zod_default.object({
|
|
71777
|
-
id: zod_default.string().describe("Unique identifier for the view"),
|
|
71778
|
-
table_id: zod_default.string().describe("ID of the table this view displays"),
|
|
71779
|
-
workspace_id: zod_default.string().describe("ID of the workspace this view belongs to"),
|
|
71780
|
-
name: zod_default.string().describe("Display name of the view"),
|
|
71781
|
-
description: zod_default.string().describe("Description of the view's purpose"),
|
|
71782
|
-
visible_to: visibleToSchema.optional().describe(
|
|
71783
|
-
"Sidebar declutter list (NOT access control). null/absent = every member with access to the parent table sees this view; a non-empty list of members/groups restricts who sees it in the explorer. [] is normalized to null on write."
|
|
71784
|
-
),
|
|
71785
|
-
position: zod_default.number().int().nullable().describe(
|
|
71786
|
-
"Display ordering index for the view. Lower numbers are shown first. Use incremental values with gaps (100, 200, 300) instead of consecutive numbers (1, 2, 3) to enable efficient reordering without updating multiple records. Example: To insert between 100 and 200, use 150."
|
|
71787
|
-
),
|
|
71788
|
-
frozen_columns: zod_default.number().int().nullable().optional().describe("Number of columns to freeze. Frozen columns are not scrollable."),
|
|
71789
|
-
summary: viewSummarySchema,
|
|
71790
|
-
default_record_data_template_id: zod_default.string().nullable().optional().describe("ID of the record template to use as the default record initial data"),
|
|
71791
|
-
field_config: zod_default.array(fieldConfigEntrySchema).describe(
|
|
71792
|
-
"Ordered array of field config entries. Order = display order, visibility = per-entry. Fields not listed are hidden."
|
|
71793
|
-
),
|
|
71794
|
-
sort: tableRecordSortSchema.nullable().describe("Sorting configuration for records in this view"),
|
|
71795
|
-
filters: tableRecordFiltersGroupNodeSchema.nullable().describe("Filter conditions applied to records in this view"),
|
|
71796
|
-
created_at: zod_default.string().describe("Timestamp when view was created")
|
|
71797
|
-
});
|
|
71798
|
-
var tableWithViewsSchema = tableSchema.extend({
|
|
71799
|
-
views: zod_default.array(tableViewSchema).describe("Array of views for this table")
|
|
71800
|
-
});
|
|
71801
|
-
var explorerViewSchema = zod_default.object({
|
|
71802
|
-
id: zod_default.string(),
|
|
71803
|
-
name: zod_default.string(),
|
|
71804
|
-
owner_member_id: zod_default.string(),
|
|
71805
|
-
// Per-view sidebar declutter list (NOT access control). null = every member
|
|
71806
|
-
// with table access sees this view; a non-empty member/group list restricts
|
|
71807
|
-
// it. Surfaced here so the table share dialog can render and edit each view's
|
|
71808
|
-
// audience without a second round-trip.
|
|
71809
|
-
visible_to: visibleToSchema.optional(),
|
|
71810
|
-
// Per-requesting-member sidebar preference: true if this member has hidden
|
|
71811
|
-
// the view. Hiding is UX-only — it never affects access or other members.
|
|
71812
|
-
hidden: zod_default.boolean()
|
|
71813
|
-
});
|
|
71814
|
-
var explorerTableSchema = zod_default.object({
|
|
71815
|
-
id: zod_default.string(),
|
|
71816
|
-
name: zod_default.string(),
|
|
71817
|
-
position: zod_default.number().int().nullable().optional(),
|
|
71818
|
-
views: zod_default.array(explorerViewSchema),
|
|
71819
|
-
owner_member_id: zod_default.string(),
|
|
71820
|
-
// Active package installations whose binding includes this table — the
|
|
71821
|
-
// sidebar marks these so members see the structure is app-managed before
|
|
71822
|
-
// they try to change it. Absent for unbound tables.
|
|
71823
|
-
package_apps: zod_default.array(zod_default.object({ id: zod_default.string(), name: zod_default.string() })).optional()
|
|
71824
|
-
});
|
|
71825
|
-
var documentTemplateTypeSchema = zod_default.enum(["html", "pdf-form", "excel", "word", "email"]).describe("Template type: 'html' for HTML templates, 'pdf-form' for fillable PDF forms, 'excel' for Excel templates, 'word' for Word templates, 'email' for email HTML templates");
|
|
71826
|
-
var documentTemplateSchema = zod_default.object({
|
|
71827
|
-
id: zod_default.string().describe("Unique identifier for the document template"),
|
|
71828
|
-
workspace_id: zod_default.string().describe("ID of the workspace this template belongs to"),
|
|
71829
|
-
name: zod_default.string().describe("Display name of the template"),
|
|
71830
|
-
description: zod_default.string().describe("What the template produces, shown under its name in the library"),
|
|
71831
|
-
type: documentTemplateTypeSchema,
|
|
71832
|
-
template: zod_default.string().describe("Template content with variable placeholders (e.g., {{customer_name}})"),
|
|
71833
|
-
format: zod_default.string().describe("Supported document formats.").optional(),
|
|
71834
|
-
orientation: zod_default.enum(["portrait", "landscape"]).describe("Page orientation for PDF generation").optional(),
|
|
71835
|
-
variables: zod_default.record(zod_default.string(), zod_default.unknown()).describe("Data to pass to the template."),
|
|
71836
|
-
current_version: zod_default.number().describe("Current version number of the template"),
|
|
71837
|
-
owner_member_id: zod_default.string().nullable().optional().describe("Member who created the template, from the IAM registry. Absent on write responses."),
|
|
71838
|
-
created_at: zod_default.string().describe("Timestamp when template was created"),
|
|
71839
|
-
template_url: zod_default.string().nullable().describe("Signed URL to download the template file (pdf-form/excel only)")
|
|
71840
|
-
});
|
|
71841
|
-
|
|
71842
|
-
// ../shared/src/schemas/packages.ts
|
|
71843
|
-
var contractAliasSchema = zod_default.string().regex(
|
|
71844
|
-
/^[a-z][a-z0-9_]*$/,
|
|
71845
|
-
"alias must be a lowercase slug: start with a letter, then letters/digits/underscores"
|
|
71846
|
-
);
|
|
71847
|
-
var runtimeAliasSchema = zod_default.string().min(1).max(200);
|
|
71848
|
-
var contractFieldBaseSchema = zod_default.object({
|
|
71849
|
-
alias: contractAliasSchema.describe("Stable local alias, unique within the entity"),
|
|
71850
|
-
// No braces: scaffold translates formula expressions from `{alias}` to the
|
|
71851
|
-
// platform's `{Field Label}` reference form, so a brace inside a label would
|
|
71852
|
-
// corrupt every formula that references the field.
|
|
71853
|
-
label: zod_default.string().min(1).regex(/^[^{}]*$/, "field labels cannot contain { or }").describe("Display label used as the field name at scaffold time"),
|
|
71854
|
-
description: zod_default.string().optional(),
|
|
71855
|
-
required: zod_default.boolean().optional().describe(
|
|
71856
|
-
"Advisory only: marks the field required for app-form/workflow UX. The table data model has no required constraint, so scaffold does NOT enforce it at the schema level \u2014 validation lives in the app/workflow layer."
|
|
71857
|
-
)
|
|
71858
|
-
});
|
|
71859
|
-
var contractSelectOptionSchema = zod_default.object({
|
|
71860
|
-
alias: contractAliasSchema.describe("Stable local alias, unique within the field"),
|
|
71861
|
-
label: zod_default.string().min(1).describe("Display label for the option"),
|
|
71862
|
-
color: optionColorSchema
|
|
71863
|
-
});
|
|
71864
|
-
var contractAutonumberConfigSchema = tableAutonumberFieldSchema.pick({
|
|
71865
|
-
prefix: true,
|
|
71866
|
-
padding: true,
|
|
71867
|
-
template: true
|
|
71868
|
-
});
|
|
71869
|
-
var contractTextFieldSchema = contractFieldBaseSchema.extend({
|
|
71870
|
-
type: zod_default.literal("text"),
|
|
71871
|
-
unique: zod_default.boolean().optional().describe("Unique values required"),
|
|
71872
|
-
format: textFormatSchema.optional()
|
|
71873
|
-
});
|
|
71874
|
-
var contractNumberFieldSchema = contractFieldBaseSchema.extend({
|
|
71875
|
-
type: zod_default.literal("number"),
|
|
71876
|
-
format: numberFormatSchema.optional(),
|
|
71877
|
-
currency: zod_default.string().optional().describe("ISO 4217 code")
|
|
71878
|
-
});
|
|
71879
|
-
var contractDateFieldSchema = contractFieldBaseSchema.extend({
|
|
71880
|
-
type: zod_default.literal("date"),
|
|
71881
|
-
format: dateFormatSchema.optional(),
|
|
71882
|
-
timezone: zod_default.string().optional().describe("IANA timezone"),
|
|
71883
|
-
derive_from: zod_default.enum(["created_at", "updated_at"]).optional().describe("Auto-populate from the row's system timestamp; the field becomes read-only.")
|
|
71884
|
-
});
|
|
71885
|
-
var contractBooleanFieldSchema = contractFieldBaseSchema.extend({
|
|
71886
|
-
type: zod_default.literal("boolean")
|
|
71887
|
-
});
|
|
71888
|
-
var contractSelectFieldSchema = contractFieldBaseSchema.extend({
|
|
71889
|
-
type: zod_default.literal("select"),
|
|
71890
|
-
options: zod_default.array(contractSelectOptionSchema).min(1),
|
|
71891
|
-
multi: zod_default.boolean().optional().describe("Allow multiple selections")
|
|
71892
|
-
});
|
|
71893
|
-
var contractSelectMemberFieldSchema = contractFieldBaseSchema.extend({
|
|
71894
|
-
type: zod_default.literal("select_member"),
|
|
71895
|
-
multi: zod_default.boolean().optional().describe("Allow multiple selections")
|
|
71896
|
-
});
|
|
71897
|
-
var contractSelectRecordLinkFieldSchema = contractFieldBaseSchema.extend({
|
|
71898
|
-
type: zod_default.literal("select_record_link"),
|
|
71899
|
-
target_entity: contractAliasSchema.describe("Alias of the entity this field links to"),
|
|
71900
|
-
sync_both_ways: zod_default.boolean().optional().describe("Create a paired link field on the target entity for bidirectional sync"),
|
|
71901
|
-
paired_field_alias: contractAliasSchema.optional().describe(
|
|
71902
|
-
"The pair edge of a bidirectional link: the field alias ON THE TARGET ENTITY that is this link's sync partner. Both sides of a pair carry it, each naming the other. Scaffold creates whichever side it reaches first WITH the pairing (the platform auto-creates the partner) and binds the partner alias to the auto-created field \u2014 without this edge the two contract fields would be created independently and collide with the auto-created partner."
|
|
71903
|
-
),
|
|
71904
|
-
cardinality: zod_default.enum(["one", "many"]).optional().describe("How many linked records this field holds. Default 'many'."),
|
|
71905
|
-
display_field_aliases: zod_default.array(contractAliasSchema).optional().describe("Field aliases on the target entity shown as the link's display text / picker columns")
|
|
71906
|
-
});
|
|
71907
|
-
var contractFilesFieldSchema = contractFieldBaseSchema.extend({
|
|
71908
|
-
type: zod_default.literal("files")
|
|
71909
|
-
});
|
|
71910
|
-
var contractFormulaFieldSchema = contractFieldBaseSchema.extend({
|
|
71911
|
-
type: zod_default.literal("formula"),
|
|
71912
|
-
formula: formulaInputSchema.describe(
|
|
71913
|
-
"Formula config. The expression references other fields on the SAME entity by alias in braces, e.g. `{quantity} * {unit_price}`."
|
|
71914
|
-
)
|
|
71915
|
-
});
|
|
71916
|
-
var contractRollupFieldSchema = contractFieldBaseSchema.extend({
|
|
71917
|
-
type: zod_default.literal("rollup"),
|
|
71918
|
-
source_field_alias: contractAliasSchema.describe(
|
|
71919
|
-
"Alias of a select_record_link field on this entity to roll up from"
|
|
71920
|
-
),
|
|
71921
|
-
aggregate_option: aggregateOptionSchema.describe(
|
|
71922
|
-
"Aggregation operation. Its `field_key` names a field alias on the linked entity."
|
|
71923
|
-
)
|
|
71924
|
-
});
|
|
71925
|
-
var contractLookupFieldSchema = contractFieldBaseSchema.extend({
|
|
71926
|
-
type: zod_default.literal("lookup"),
|
|
71927
|
-
source_field_alias: contractAliasSchema.describe(
|
|
71928
|
-
"Alias of a select_record_link field on this entity to look up through"
|
|
71929
|
-
),
|
|
71930
|
-
lookup_field_alias: contractAliasSchema.describe(
|
|
71931
|
-
"Alias of the field on the linked entity to display"
|
|
71932
|
-
),
|
|
71933
|
-
order_by: lookupOrderBySchema.optional().describe("Ordered lookup. Its `field_key` names a field alias on the linked entity.")
|
|
71934
|
-
});
|
|
71935
|
-
var contractAutonumberFieldSchema = contractFieldBaseSchema.extend({
|
|
71936
|
-
type: zod_default.literal("autonumber"),
|
|
71937
|
-
...contractAutonumberConfigSchema.shape
|
|
71938
|
-
});
|
|
71939
|
-
var contractFieldSchema = zod_default.discriminatedUnion("type", [
|
|
71940
|
-
contractTextFieldSchema,
|
|
71941
|
-
contractNumberFieldSchema,
|
|
71942
|
-
contractDateFieldSchema,
|
|
71943
|
-
contractBooleanFieldSchema,
|
|
71944
|
-
contractSelectFieldSchema,
|
|
71945
|
-
contractSelectMemberFieldSchema,
|
|
71946
|
-
contractSelectRecordLinkFieldSchema,
|
|
71947
|
-
contractFilesFieldSchema,
|
|
71948
|
-
contractFormulaFieldSchema,
|
|
71949
|
-
contractRollupFieldSchema,
|
|
71950
|
-
contractLookupFieldSchema,
|
|
71951
|
-
contractAutonumberFieldSchema
|
|
71952
|
-
]);
|
|
71953
|
-
var contractEntitySchema = zod_default.object({
|
|
71954
|
-
alias: contractAliasSchema.describe("Stable entity alias, unique within the contract"),
|
|
71955
|
-
label: zod_default.string().min(1).describe("Display label used as the table name at scaffold time"),
|
|
71956
|
-
description: zod_default.string().optional(),
|
|
71957
|
-
fields: zod_default.array(contractFieldSchema).min(1)
|
|
71958
|
-
});
|
|
71959
|
-
var contractRoleSchema = zod_default.object({
|
|
71960
|
-
alias: contractAliasSchema.describe("Stable role alias, bound to a workspace group at install"),
|
|
71961
|
-
label: zod_default.string().min(1)
|
|
71962
|
-
});
|
|
71963
|
-
var contractTemplateBaseSchema = zod_default.object({
|
|
71964
|
-
alias: contractAliasSchema.describe("Stable template alias, unique within the contract"),
|
|
71965
|
-
label: zod_default.string().min(1),
|
|
71966
|
-
content_sha256: zod_default.string().optional().describe(
|
|
71967
|
-
"sha256 (64-char lowercase hex) of the template content \u2014 inline: the utf-8 content string; file-backed: the bytes_ref bytes. The modified-detection reference. Optional in the schema so contracts published before template sha still parse; REQUIRED at publish (validatePackageContract)."
|
|
71968
|
-
)
|
|
71969
|
-
});
|
|
71970
|
-
var contractInlineTemplateSchema = (templateType) => contractTemplateBaseSchema.extend({
|
|
71971
|
-
type: zod_default.literal(templateType),
|
|
71972
|
-
content: zod_default.string().min(1).describe("Inline template content; placeholders reference field aliases")
|
|
71973
|
-
});
|
|
71974
|
-
var contractFileTemplateSchema = (templateType) => contractTemplateBaseSchema.extend({
|
|
71975
|
-
type: zod_default.literal(templateType),
|
|
71976
|
-
bytes_ref: zod_default.string().min(1).describe("Path of the backing file within the package bundle; markers reference field aliases")
|
|
71977
|
-
});
|
|
71978
|
-
var contractTemplateSchema = zod_default.discriminatedUnion("type", [
|
|
71979
|
-
contractInlineTemplateSchema("html"),
|
|
71980
|
-
contractInlineTemplateSchema("email"),
|
|
71981
|
-
contractFileTemplateSchema("excel"),
|
|
71982
|
-
contractFileTemplateSchema("word"),
|
|
71983
|
-
contractFileTemplateSchema("pdf-form")
|
|
71984
|
-
]);
|
|
71985
|
-
var contractFromTableNodeSchema = zod_default.object({
|
|
71986
|
-
kind: zod_default.literal("from_table"),
|
|
71987
|
-
from_entity: contractAliasSchema.describe("Entity alias this query reads from"),
|
|
71988
|
-
filter: tableRecordFiltersSchema.optional(),
|
|
71989
|
-
search: zod_default.string().optional(),
|
|
71990
|
-
sort: tableRecordSortSchema.optional(),
|
|
71991
|
-
limit: zod_default.number().optional()
|
|
71992
|
-
});
|
|
71993
|
-
var contractProjectNodeSchema = zod_default.object({
|
|
71994
|
-
kind: zod_default.literal("project"),
|
|
71995
|
-
from: zod_default.lazy(() => contractQueryNodeSchema),
|
|
71996
|
-
columns: zod_default.array(queryProjectionColumnSchema).min(1)
|
|
71997
|
-
});
|
|
71998
|
-
var contractFilterNodeSchema = zod_default.object({
|
|
71999
|
-
kind: zod_default.literal("filter"),
|
|
72000
|
-
from: zod_default.lazy(() => contractQueryNodeSchema),
|
|
72001
|
-
predicate: tableRecordFiltersSchema
|
|
72002
|
-
});
|
|
72003
|
-
var contractJoinNodeSchema = zod_default.object({
|
|
72004
|
-
kind: zod_default.literal("join"),
|
|
72005
|
-
left: zod_default.lazy(() => contractQueryNodeSchema),
|
|
72006
|
-
right: zod_default.lazy(() => contractQueryNodeSchema),
|
|
72007
|
-
on: queryJoinPredicateSchema,
|
|
72008
|
-
type: zod_default.enum(["inner", "left"])
|
|
72009
|
-
});
|
|
72010
|
-
var contractUnionNodeSchema = zod_default.object({
|
|
72011
|
-
kind: zod_default.literal("union"),
|
|
72012
|
-
sources: zod_default.array(zod_default.lazy(() => contractQueryNodeSchema)).min(2)
|
|
72013
|
-
});
|
|
72014
|
-
var contractGroupNodeSchema = zod_default.object({
|
|
72015
|
-
kind: zod_default.literal("group"),
|
|
72016
|
-
from: zod_default.lazy(() => contractQueryNodeSchema),
|
|
72017
|
-
by: zod_default.array(zod_default.string()),
|
|
72018
|
-
aggregates: zod_default.array(queryAggregateColumnSchema).min(1)
|
|
72019
|
-
});
|
|
72020
|
-
var contractWindowNodeSchema = zod_default.object({
|
|
72021
|
-
kind: zod_default.literal("window"),
|
|
72022
|
-
from: zod_default.lazy(() => contractQueryNodeSchema),
|
|
72023
|
-
partition_by: zod_default.array(zod_default.string()),
|
|
72024
|
-
order_by: tableRecordSortSchema,
|
|
72025
|
-
frame: queryWindowFrameSchema.optional(),
|
|
72026
|
-
aggregates: zod_default.array(queryAggregateColumnSchema).optional(),
|
|
72027
|
-
functions: zod_default.array(queryWindowFunctionColumnSchema).optional()
|
|
72028
|
-
});
|
|
72029
|
-
var contractSortNodeSchema = zod_default.object({
|
|
72030
|
-
kind: zod_default.literal("sort"),
|
|
72031
|
-
from: zod_default.lazy(() => contractQueryNodeSchema),
|
|
72032
|
-
by: tableRecordSortSchema
|
|
72033
|
-
});
|
|
72034
|
-
var contractLimitNodeSchema = zod_default.object({
|
|
72035
|
-
kind: zod_default.literal("limit"),
|
|
72036
|
-
from: zod_default.lazy(() => contractQueryNodeSchema),
|
|
72037
|
-
n: zod_default.number().int().positive(),
|
|
72038
|
-
offset: zod_default.number().int().nonnegative().optional()
|
|
72039
|
-
});
|
|
72040
|
-
var contractUnpivotNodeSchema = zod_default.object({
|
|
72041
|
-
kind: zod_default.literal("unpivot"),
|
|
72042
|
-
from: zod_default.lazy(() => contractQueryNodeSchema),
|
|
72043
|
-
passthrough: zod_default.array(queryUnpivotPassthroughColumnSchema),
|
|
72044
|
-
row_columns: zod_default.array(queryUnpivotRowColumnSchema).min(1),
|
|
72045
|
-
rows: zod_default.array(zod_default.record(zod_default.string(), querySourceSchema)).min(1)
|
|
72046
|
-
});
|
|
72047
|
-
var contractUnnestNodeSchema = zod_default.object({
|
|
72048
|
-
kind: zod_default.literal("unnest"),
|
|
72049
|
-
from: zod_default.lazy(() => contractQueryNodeSchema),
|
|
72050
|
-
source: zod_default.string(),
|
|
72051
|
-
output: zod_default.string(),
|
|
72052
|
-
display_output: zod_default.string().optional(),
|
|
72053
|
-
keep_empty: zod_default.boolean().optional()
|
|
72054
|
-
});
|
|
72055
|
-
var contractQueryNodeSchema = zod_default.lazy(
|
|
72056
|
-
() => zod_default.discriminatedUnion("kind", [
|
|
72057
|
-
contractFromTableNodeSchema,
|
|
72058
|
-
contractProjectNodeSchema,
|
|
72059
|
-
contractFilterNodeSchema,
|
|
72060
|
-
contractJoinNodeSchema,
|
|
72061
|
-
contractUnionNodeSchema,
|
|
72062
|
-
contractGroupNodeSchema,
|
|
72063
|
-
contractWindowNodeSchema,
|
|
72064
|
-
contractSortNodeSchema,
|
|
72065
|
-
contractLimitNodeSchema,
|
|
72066
|
-
contractUnpivotNodeSchema,
|
|
72067
|
-
contractUnnestNodeSchema
|
|
72068
|
-
])
|
|
72069
|
-
);
|
|
72070
|
-
var contractQuerySchema = zod_default.object({
|
|
72071
|
-
alias: runtimeAliasSchema.describe(
|
|
72072
|
-
"Stable query alias, unique within the contract \u2014 carried verbatim from the app (source invokes it at runtime)"
|
|
72073
|
-
),
|
|
72074
|
-
params: zod_default.record(zod_default.string(), appWorkflowInputSchema).optional().describe("Typed param schema. Keys are param names referenced as {{params.<name>}} in the ast."),
|
|
72075
|
-
ast: contractQueryNodeSchema
|
|
72076
|
-
});
|
|
72077
|
-
var contractLifecycleEventSchema = tableWorkflowEventSchema;
|
|
72078
|
-
var contractWorkflowTriggerSchema = zod_default.discriminatedUnion("type", [
|
|
72079
|
-
zod_default.object({ type: zod_default.literal("app") }),
|
|
72080
|
-
zod_default.object({
|
|
72081
|
-
type: zod_default.literal("entity_lifecycle"),
|
|
72082
|
-
entity: contractAliasSchema.describe("Alias of the entity whose lifecycle fires this workflow"),
|
|
72083
|
-
event: contractLifecycleEventSchema
|
|
72084
|
-
})
|
|
72085
|
-
]);
|
|
72086
|
-
var contractWorkflowSchema = zod_default.object({
|
|
72087
|
-
alias: runtimeAliasSchema.describe(
|
|
72088
|
-
"Stable workflow alias, unique within the contract \u2014 app-trigger aliases are carried verbatim from the app (source invokes them at runtime)"
|
|
72089
|
-
),
|
|
72090
|
-
trigger: contractWorkflowTriggerSchema,
|
|
72091
|
-
inputs: zod_default.record(zod_default.string(), appWorkflowInputSchema).optional().describe("Typed inputs. record_link `table_id` names an entity alias; member `group` a role alias."),
|
|
72092
|
-
outputs: zod_default.record(zod_default.string(), appWorkflowOutputSchema).optional().describe("Typed outputs. record_link `table_id` names an entity alias."),
|
|
72093
|
-
body: zod_default.string().min(1).describe("Alias-form JS-subset workflow source. Identifiers are resolved against the binding at materialize time.")
|
|
72094
|
-
});
|
|
72095
|
-
var contractAgentSchema = appAgentDeclarationSchema.extend({
|
|
72096
|
-
alias: runtimeAliasSchema.describe(
|
|
72097
|
-
"Stable agent alias, unique within the contract \u2014 carried verbatim from the app (source invokes it at runtime)"
|
|
72098
|
-
),
|
|
72099
|
-
knowledge_expects: zod_default.array(zod_default.string().min(1)).optional().describe(
|
|
72100
|
-
"Doc NAMES this agent must read that the package does NOT own \u2014 the installer's own docs. Resolved by name against the installing workspace: exactly one non-archived match binds, zero or several bind nothing and surface as an install warning, because doc names are not unique and picking one would be a guess. The agent installs either way."
|
|
72101
|
-
),
|
|
72102
|
-
knowledge_aliases: zod_default.array(contractAliasSchema).optional().describe(
|
|
72103
|
-
"Package knowledge docs this agent may read, by contract alias. Materialize resolves each against `binding.knowledge` to the installing workspace's own doc id and writes the agent's `knowledge_doc_ids`. Omit for an agent that reads no package knowledge \u2014 an agent whose declared set does not travel can read NOTHING, since a declared set bounds every read."
|
|
72104
|
-
)
|
|
72105
|
-
});
|
|
72106
|
-
var contractConfigBaseSchema = zod_default.object({
|
|
72107
|
-
alias: contractAliasSchema.describe("Stable config alias, unique within the contract"),
|
|
72108
|
-
label: zod_default.string().min(1),
|
|
72109
|
-
description: zod_default.string().optional()
|
|
72110
|
-
});
|
|
72111
|
-
var contractTextConfigSchema = contractConfigBaseSchema.extend({
|
|
72112
|
-
type: zod_default.literal("text"),
|
|
72113
|
-
default: zod_default.string()
|
|
72114
|
-
});
|
|
72115
|
-
var contractBooleanConfigSchema = contractConfigBaseSchema.extend({
|
|
72116
|
-
type: zod_default.literal("boolean"),
|
|
72117
|
-
default: zod_default.boolean()
|
|
72118
|
-
});
|
|
72119
|
-
var contractColorConfigSchema = contractConfigBaseSchema.extend({
|
|
72120
|
-
type: zod_default.literal("color"),
|
|
72121
|
-
default: optionColorSchema
|
|
72122
|
-
});
|
|
72123
|
-
var contractNumberConfigSchema = contractConfigBaseSchema.extend({
|
|
72124
|
-
type: zod_default.literal("number"),
|
|
72125
|
-
default: zod_default.number()
|
|
72126
|
-
});
|
|
72127
|
-
var contractSelectConfigSchema = contractConfigBaseSchema.extend({
|
|
72128
|
-
type: zod_default.literal("select"),
|
|
72129
|
-
options: zod_default.array(zod_default.object({ value: zod_default.string(), label: zod_default.string().min(1) })).min(1),
|
|
72130
|
-
default: zod_default.string()
|
|
72131
|
-
});
|
|
72132
|
-
var contractConfigEntrySchema = zod_default.discriminatedUnion("type", [
|
|
72133
|
-
contractTextConfigSchema,
|
|
72134
|
-
contractBooleanConfigSchema,
|
|
72135
|
-
contractColorConfigSchema,
|
|
72136
|
-
contractNumberConfigSchema,
|
|
72137
|
-
contractSelectConfigSchema
|
|
72138
|
-
]);
|
|
72139
|
-
var packageKindSchema = zod_default.enum(["app", "content"]);
|
|
72140
|
-
var contractKnowledgeEntrySchema = zod_default.object({
|
|
72141
|
-
name: zod_default.string().min(1).describe(
|
|
72142
|
-
"Display name \u2014 the runtime routing key an agent resolves the doc by; unique across the contract's knowledge"
|
|
72143
|
-
),
|
|
72144
|
-
description: zod_default.string().describe("Doc description (may be empty)"),
|
|
72145
|
-
// Optional so contracts published before tagging still parse; absent means
|
|
72146
|
-
// untagged. A curated corpus is exactly the case where classification is
|
|
72147
|
-
// authored deliberately, so install and upgrade have to carry it — otherwise
|
|
72148
|
-
// every installed corpus lands unlabelled and the customer re-tags it by hand.
|
|
72149
|
-
//
|
|
72150
|
-
// ABSENT IS NOT EMPTY, and that distinction is load-bearing on the wire: a
|
|
72151
|
-
// contract that says nothing about tags must leave the customer's own labels
|
|
72152
|
-
// alone, or a routine content upgrade silently strips classification the
|
|
72153
|
-
// workspace added. Every reader below branches on `undefined`, never on length.
|
|
72154
|
-
tags: zod_default.array(zod_default.string()).optional().describe("Labels for the doc; omitted leaves existing labels alone"),
|
|
72155
|
-
/**
|
|
72156
|
-
* LEGACY, read-only, removed in a later release.
|
|
72157
|
-
*
|
|
72158
|
-
* Content packages published while knowledge docs had folders carry a `path`,
|
|
72159
|
-
* and those contracts are stored verbatim in the workspaces that installed
|
|
72160
|
-
* them. Dropping the field would make an installed contract fail to parse and
|
|
72161
|
-
* would discard what the publisher declared, so it is still accepted and
|
|
72162
|
-
* mapped to `tags` on install/upgrade (a path's segments were always labels;
|
|
72163
|
-
* the hierarchy merely insisted on an order for them). Nothing EMITS it any
|
|
72164
|
-
* more — `content_bundle` writes `tags` — so it disappears from a package the
|
|
72165
|
-
* first time it is re-published.
|
|
72166
|
-
*/
|
|
72167
|
-
path: zod_default.string().optional().describe("Deprecated: pre-tagging folder. Mapped to tags on install."),
|
|
72168
|
-
content_ref: zod_default.string().min(1).describe("Path of the content file within the bundle \u2014 must be `knowledge/<alias>.md`"),
|
|
72169
|
-
content_sha256: zod_default.string().describe("sha256 (64-char lowercase hex) of the content bytes \u2014 the modified-detection reference")
|
|
72170
|
-
});
|
|
72171
|
-
var contractKnowledgeSchema = zod_default.record(contractAliasSchema, contractKnowledgeEntrySchema);
|
|
72172
|
-
var packageContractSchema = zod_default.object({
|
|
72173
|
-
entities: zod_default.array(contractEntitySchema).default([]),
|
|
72174
|
-
roles: zod_default.array(contractRoleSchema).default([]),
|
|
72175
|
-
templates: zod_default.array(contractTemplateSchema).default([]),
|
|
72176
|
-
queries: zod_default.array(contractQuerySchema).default([]),
|
|
72177
|
-
workflows: zod_default.array(contractWorkflowSchema).default([]),
|
|
72178
|
-
agents: zod_default.array(contractAgentSchema).default([]),
|
|
72179
|
-
config: zod_default.array(contractConfigEntrySchema).default([]),
|
|
72180
|
-
// Package-managed knowledge docs (alias → metadata + content sha). Defaults to
|
|
72181
|
-
// {} so contracts published before knowledge packaging still parse.
|
|
72182
|
-
knowledge: contractKnowledgeSchema.default({}),
|
|
72183
|
-
// Doc NAMES the package's agents route to but the package does not own —
|
|
72184
|
-
// install/health WARN (advisory) when a name has no doc in the workspace.
|
|
72185
|
-
// The first instance of the general cross-package "expects" contract.
|
|
72186
|
-
knowledge_expects: zod_default.array(zod_default.string()).default([])
|
|
72187
|
-
});
|
|
72188
|
-
var bindingMapSchema = zod_default.record(zod_default.string().min(1), zod_default.string().min(1));
|
|
72189
|
-
var bindingSchema = zod_default.object({
|
|
72190
|
-
entities: bindingMapSchema.default({}),
|
|
72191
|
-
fields: bindingMapSchema.default({}),
|
|
72192
|
-
options: bindingMapSchema.default({}),
|
|
72193
|
-
templates: bindingMapSchema.default({}),
|
|
72194
|
-
roles: bindingMapSchema.default({}),
|
|
72195
|
-
// Artifact registry, not a schema binding: the package-owned table-workflow
|
|
72196
|
-
// ROW id per entity_lifecycle workflow alias. Materialize matches/updates by
|
|
72197
|
-
// this id (a display name is forgeable and renameable), upgrade prunes by
|
|
72198
|
-
// it, and hashes look rows up through it. Excluded from BINDING_NAMESPACES:
|
|
72199
|
-
// a deleted row is a modified-core finding (fingerprints), never binding
|
|
72200
|
-
// drift, so validateBinding/applyDriftResolutions ignore it.
|
|
72201
|
-
workflows: bindingMapSchema.default({}),
|
|
72202
|
-
// The app's BUNDLED knowledge corpus: contract knowledge alias → the
|
|
72203
|
-
// workspace's concrete `kdc_` id. One row, one pin — the app installation IS
|
|
72204
|
-
// the anchor for its bundled docs (`package_content_installations` rows are
|
|
72205
|
-
// standalone content packages only). Excluded from BINDING_NAMESPACES: a
|
|
72206
|
-
// gone/edited doc is detected by the knowledge upgrade preview (live doc +
|
|
72207
|
-
// content-sha reads), never by validateBinding's live-id sweep.
|
|
72208
|
-
knowledge: bindingMapSchema.default({})
|
|
72209
|
-
});
|
|
72210
|
-
var BINDING_NAMESPACES = ["entities", "fields", "options", "templates", "roles"];
|
|
72211
|
-
var contentBindingMapSchema = zod_default.record(zod_default.string().min(1), zod_default.string().min(1));
|
|
72212
|
-
var packageContentBindingSchema = zod_default.object({
|
|
72213
|
-
knowledge: contentBindingMapSchema.default({}),
|
|
72214
|
-
templates: contentBindingMapSchema.default({})
|
|
72215
|
-
});
|
|
72216
|
-
var bindingDriftSchema = zod_default.object({
|
|
72217
|
-
namespace: zod_default.enum(BINDING_NAMESPACES),
|
|
72218
|
-
alias: zod_default.string(),
|
|
72219
|
-
id: zod_default.string().describe("The stale concrete id the alias was bound to")
|
|
72220
|
-
});
|
|
72221
|
-
var driftResolutionSchema = zod_default.union([
|
|
72222
|
-
zod_default.literal("recreate"),
|
|
72223
|
-
zod_default.object({ bind_to: zod_default.string().min(1) })
|
|
72224
|
-
]);
|
|
72225
|
-
var MODIFIED_ARTIFACT_KINDS = ["queries", "workflows", "agents", "template"];
|
|
72226
|
-
var modifiedArtifactSchema = zod_default.object({
|
|
72227
|
-
kind: zod_default.enum(MODIFIED_ARTIFACT_KINDS),
|
|
72228
|
-
alias: zod_default.string(),
|
|
72229
|
-
// Templates only: the OLD pinned contract carried no content_sha256, so the
|
|
72230
|
-
// preview cannot attribute the divergence from the target to a local edit vs.
|
|
72231
|
-
// the older upstream content — a one-time consent, converging once a
|
|
72232
|
-
// sha-carrying version is pinned. Surfaces can say "can't verify local edits
|
|
72233
|
-
// (older package version)".
|
|
72234
|
-
baseline_unknown: zod_default.boolean().optional()
|
|
72235
|
-
});
|
|
72236
|
-
var packageArtifactHashesSchema = zod_default.object({
|
|
72237
|
-
queries: zod_default.record(zod_default.string(), zod_default.string()),
|
|
72238
|
-
workflows: zod_default.record(zod_default.string(), zod_default.string()),
|
|
72239
|
-
agents: zod_default.record(zod_default.string(), zod_default.string())
|
|
72240
|
-
});
|
|
72241
|
-
var modificationResolutionSchema = zod_default.union([zod_default.literal("revert"), zod_default.literal("keep")]);
|
|
72242
|
-
var KNOWLEDGE_UPGRADE_CHANGES = ["added", "changed", "removed", "drifted"];
|
|
72243
|
-
var knowledgeUpgradeEntrySchema = zod_default.object({
|
|
72244
|
-
alias: zod_default.string(),
|
|
72245
|
-
name: zod_default.string().describe("The doc's display name \u2014 the target contract's name, or the live name for a drifted doc"),
|
|
72246
|
-
change: zod_default.enum(KNOWLEDGE_UPGRADE_CHANGES),
|
|
72247
|
-
/** `changed`/`removed` only: the live doc's content diverged from the OLD pinned sha. */
|
|
72248
|
-
modified: zod_default.boolean(),
|
|
72249
|
-
/** The bound live doc id; null for `added`, or for a `drifted` doc that is gone. */
|
|
72250
|
-
doc_id: zod_default.string().nullable()
|
|
72251
|
-
});
|
|
72252
|
-
function knowledgeEntryNeedsConsent(entry) {
|
|
72253
|
-
if (entry.change === "drifted") return true;
|
|
72254
|
-
if (entry.change === "changed" || entry.change === "removed") return entry.modified;
|
|
72255
|
-
return false;
|
|
72256
|
-
}
|
|
72257
|
-
var knowledgeResolutionSchema = zod_default.enum(["apply", "keep", "archive", "recreate", "unbind"]);
|
|
72258
|
-
var upgradeResolutionsSchema = zod_default.record(
|
|
72259
|
-
zod_default.string(),
|
|
72260
|
-
zod_default.union([driftResolutionSchema, modificationResolutionSchema, knowledgeResolutionSchema])
|
|
72261
|
-
);
|
|
72262
|
-
var knowledgeBindConsentSchema = zod_default.record(zod_default.string(), zod_default.string());
|
|
72263
|
-
var knowledgeUpgradeResolutionsSchema = zod_default.object({
|
|
72264
|
-
resolutions: zod_default.record(zod_default.string(), knowledgeResolutionSchema).default({}),
|
|
72265
|
-
bind_to: knowledgeBindConsentSchema.default({})
|
|
72266
|
-
});
|
|
72267
|
-
var knowledgeBoundRefSchema = zod_default.object({
|
|
72268
|
-
alias: zod_default.string(),
|
|
72269
|
-
name: zod_default.string(),
|
|
72270
|
-
/** The bound doc id; null when the bound doc is gone/archived (drift). */
|
|
72271
|
-
doc_id: zod_default.string().nullable()
|
|
72272
|
-
});
|
|
72273
|
-
var appInstallationConfigValueSchema = zod_default.union([zod_default.string(), zod_default.number(), zod_default.boolean()]);
|
|
72274
|
-
var appInstallationConfigSchema = zod_default.record(
|
|
72275
|
-
contractAliasSchema,
|
|
72276
|
-
appInstallationConfigValueSchema
|
|
72277
|
-
);
|
|
72278
|
-
var appInstallationProvenanceSchema = zod_default.enum(["install", "adopt"]);
|
|
72279
|
-
|
|
72280
70989
|
// ../shared/src/agent_instructions.ts
|
|
72281
70990
|
function agentFilePath(alias) {
|
|
72282
70991
|
return `src/agents/${alias}.md`;
|
|
@@ -72688,6 +71397,16 @@ function runNpm(args, cwd) {
|
|
|
72688
71397
|
});
|
|
72689
71398
|
});
|
|
72690
71399
|
}
|
|
71400
|
+
function npmInstallArgs(hasLockfile) {
|
|
71401
|
+
return [hasLockfile ? "ci" : "install", "--ignore-scripts"];
|
|
71402
|
+
}
|
|
71403
|
+
function runNpmInstall(cwd) {
|
|
71404
|
+
const hasLockfile = fs8.existsSync(path10.join(cwd, "package-lock.json"));
|
|
71405
|
+
console.error(
|
|
71406
|
+
hasLockfile ? "Installing npm dependencies (npm ci \u2014 the lockfile's exact tree, no install scripts)..." : "Installing npm dependencies (no lockfile yet \u2014 resolving ranges, no install scripts)..."
|
|
71407
|
+
);
|
|
71408
|
+
return runNpm(npmInstallArgs(hasLockfile), cwd);
|
|
71409
|
+
}
|
|
72691
71410
|
function readAppWorkspaceId(projectDir) {
|
|
72692
71411
|
try {
|
|
72693
71412
|
const pkgPath2 = path10.join(projectDir, "package.json");
|
|
@@ -72900,13 +71619,6 @@ function writeAppFields(projectDir, tables) {
|
|
|
72900
71619
|
fs8.writeFileSync(file2, generateAppFields(tables));
|
|
72901
71620
|
return file2;
|
|
72902
71621
|
}
|
|
72903
|
-
function writeBindingAppFields(projectDir, binding) {
|
|
72904
|
-
const dotLotics = path10.join(projectDir, ".lotics");
|
|
72905
|
-
fs8.mkdirSync(dotLotics, { recursive: true });
|
|
72906
|
-
const file2 = path10.join(dotLotics, "app_fields.ts");
|
|
72907
|
-
fs8.writeFileSync(file2, generatePackageAppFields(binding));
|
|
72908
|
-
return file2;
|
|
72909
|
-
}
|
|
72910
71622
|
async function writeGeneratedAppFields(client, projectDir, app, queries) {
|
|
72911
71623
|
if (client.viewAsMemberId) {
|
|
72912
71624
|
console.error(
|
|
@@ -72915,14 +71627,7 @@ async function writeGeneratedAppFields(client, projectDir, app, queries) {
|
|
|
72915
71627
|
return;
|
|
72916
71628
|
}
|
|
72917
71629
|
try {
|
|
72918
|
-
|
|
72919
|
-
const binding = await client.appBinding(app.app_id);
|
|
72920
|
-
const fieldsPath = writeBindingAppFields(projectDir, binding);
|
|
72921
|
-
const count = Object.keys(binding.fields).length;
|
|
72922
|
-
console.error(
|
|
72923
|
-
`Wrote ${fieldsPath} (binding form \u2014 linked to package ${app.package_id}; ${count} field alias${count === 1 ? "" : "es"} resolved per-install)`
|
|
72924
|
-
);
|
|
72925
|
-
} else {
|
|
71630
|
+
{
|
|
72926
71631
|
const tableIds = resolveCodegenTableIds(projectDir, queries);
|
|
72927
71632
|
const tables = await client.getWorkspaceSchema(tableIds);
|
|
72928
71633
|
const missing = tableIds.filter((id) => !tables.some((t) => t.id === id));
|
|
@@ -73044,19 +71749,14 @@ function ensureAppVitestSetup(projectDir) {
|
|
|
73044
71749
|
const setupPath = path10.join(projectDir, VITEST_SETUP_FILENAME);
|
|
73045
71750
|
if (!fs8.existsSync(setupPath)) {
|
|
73046
71751
|
fs8.writeFileSync(setupPath, VITEST_SETUP_CONTENT);
|
|
73047
|
-
console.error(`Wrote ${VITEST_SETUP_FILENAME} (
|
|
73048
|
-
} else if (!fs8.readFileSync(setupPath, "utf-8").includes("getAppBinding")) {
|
|
73049
|
-
console.error(
|
|
73050
|
-
`\u26A0 ${VITEST_SETUP_FILENAME} exists but does not stub getAppBinding \u2014 \`npm test\` will fail to collect any test that imports the app graph (the binding-form .lotics/app_fields.ts awaits a network call). Add the stub to it:
|
|
73051
|
-
${VITEST_SETUP_CONTENT}`
|
|
73052
|
-
);
|
|
71752
|
+
console.error(`Wrote ${VITEST_SETUP_FILENAME} (wired by vite.config.ts; empty until you fill it).`);
|
|
73053
71753
|
}
|
|
73054
71754
|
const viteConfigPath = path10.join(projectDir, "vite.config.ts");
|
|
73055
71755
|
if (!fs8.existsSync(viteConfigPath)) return;
|
|
73056
71756
|
const viteConfig = fs8.readFileSync(viteConfigPath, "utf-8");
|
|
73057
71757
|
if (/setupFiles\s*:/.test(viteConfig) && viteConfig.includes(VITEST_SETUP_FILENAME)) return;
|
|
73058
71758
|
console.error(
|
|
73059
|
-
`\u26A0 vite.config.ts does not wire ${VITEST_SETUP_FILENAME}
|
|
71759
|
+
`\u26A0 vite.config.ts does not wire ${VITEST_SETUP_FILENAME}. Nothing is broken by that \u2014 it is the slot for global test setup (matchers, stubs, timezone pinning). Add it to the \`test\` block when you need one:
|
|
73060
71760
|
setupFiles: ["./${VITEST_SETUP_FILENAME}"],`
|
|
73061
71761
|
);
|
|
73062
71762
|
}
|
|
@@ -73090,7 +71790,7 @@ async function appCodegen(args) {
|
|
|
73090
71790
|
await writeGeneratedAppFields(
|
|
73091
71791
|
args.client,
|
|
73092
71792
|
projectDir,
|
|
73093
|
-
{ app_id: meta3.app_id
|
|
71793
|
+
{ app_id: meta3.app_id },
|
|
73094
71794
|
meta3.queries ?? {}
|
|
73095
71795
|
);
|
|
73096
71796
|
} catch (err2) {
|
|
@@ -73209,8 +71909,7 @@ async function materializeScaffold(targetPath, files) {
|
|
|
73209
71909
|
}
|
|
73210
71910
|
console.error(`Scaffolded ${files.length} files into ${targetPath}`);
|
|
73211
71911
|
writeAppDts(targetPath, {});
|
|
73212
|
-
|
|
73213
|
-
await runNpm(["install"], targetPath);
|
|
71912
|
+
await runNpmInstall(targetPath);
|
|
73214
71913
|
writeAppDtsKitLinks(targetPath);
|
|
73215
71914
|
}
|
|
73216
71915
|
async function appCreate(client, args) {
|
|
@@ -73316,43 +72015,7 @@ function defaultPullTarget(appId, appName) {
|
|
|
73316
72015
|
}
|
|
73317
72016
|
return appDirName(appName);
|
|
73318
72017
|
}
|
|
73319
|
-
async function
|
|
73320
|
-
const app = await client.getApp(args.app_id);
|
|
73321
|
-
if (!app.current_version_id && args.version === void 0) {
|
|
73322
|
-
throw new Error(
|
|
73323
|
-
`App ${app.id} has no published version yet. Deploy from another machine first, or use 'lotics app create' to scaffold a new app.`
|
|
73324
|
-
);
|
|
73325
|
-
}
|
|
73326
|
-
const versionId = args.version ?? app.current_version_id;
|
|
73327
|
-
if (!versionId) throw new Error(`App ${app.id} has no version to pull.`);
|
|
73328
|
-
const version2 = await client.getAppVersion(app.id, versionId);
|
|
73329
|
-
const sourceUrl = await client.getAppVersionSourceUrl(app.id, version2.id);
|
|
73330
|
-
const targetPath = path10.resolve(args.targetPath ?? defaultPullTarget(app.id, app.name));
|
|
73331
|
-
fs8.mkdirSync(targetPath, { recursive: true });
|
|
73332
|
-
const prior = readPriorStamp(targetPath);
|
|
73333
|
-
const tmpFile = path10.join(tmpdir(), `lotics-app-${app.id}-${Date.now()}.tar.gz`);
|
|
73334
|
-
console.error(`Downloading source archive...`);
|
|
73335
|
-
await downloadToFile(sourceUrl, tmpFile);
|
|
73336
|
-
const keptLocal = [];
|
|
73337
|
-
const stagingDir = fs8.mkdtempSync(path10.join(tmpdir(), `lotics-pull-${app.id}-`));
|
|
73338
|
-
try {
|
|
73339
|
-
await runTar(["-xzf", tmpFile, "-C", stagingDir], stagingDir);
|
|
73340
|
-
console.error(`Extracting to ${targetPath}...`);
|
|
73341
|
-
keptLocal.push(
|
|
73342
|
-
...copyTree(stagingDir, targetPath, {
|
|
73343
|
-
overwrite: args.force === true,
|
|
73344
|
-
skip: [WORKFLOWS_DIR, AGENTS_DIR].map((d) => d.split(path10.sep).join("/"))
|
|
73345
|
-
})
|
|
73346
|
-
);
|
|
73347
|
-
} finally {
|
|
73348
|
-
if (fs8.existsSync(tmpFile)) fs8.unlinkSync(tmpFile);
|
|
73349
|
-
fs8.rmSync(stagingDir, { recursive: true, force: true });
|
|
73350
|
-
}
|
|
73351
|
-
const stamp = stampAfterPull({
|
|
73352
|
-
prior,
|
|
73353
|
-
pulled: { id: versionId, number: version2.version },
|
|
73354
|
-
keptCount: keptLocal.length
|
|
73355
|
-
});
|
|
72018
|
+
async function hydrateAppProject(client, targetPath, app, opts) {
|
|
73356
72019
|
stampPulledManifest(targetPath, {
|
|
73357
72020
|
app_id: app.id,
|
|
73358
72021
|
workspace_id: app.workspace_id,
|
|
@@ -73360,8 +72023,8 @@ async function appPull(client, args) {
|
|
|
73360
72023
|
// after pulling an OLD one would let the next deploy ship that old source as
|
|
73361
72024
|
// if it were built on the newest — the version guard exists to refuse
|
|
73362
72025
|
// exactly that, and it can only do so if this tells the truth.
|
|
73363
|
-
current_version_id: stamp.id,
|
|
73364
|
-
version_number: stamp.number,
|
|
72026
|
+
current_version_id: opts.stamp.id,
|
|
72027
|
+
version_number: opts.stamp.number,
|
|
73365
72028
|
workflows: app.workflows ?? {},
|
|
73366
72029
|
queries: app.queries ?? {},
|
|
73367
72030
|
agents: app.agents ?? {}
|
|
@@ -73373,14 +72036,14 @@ async function appPull(client, args) {
|
|
|
73373
72036
|
await writeGeneratedAppFields(
|
|
73374
72037
|
client,
|
|
73375
72038
|
targetPath,
|
|
73376
|
-
{ app_id: app.id
|
|
72039
|
+
{ app_id: app.id },
|
|
73377
72040
|
app.queries ?? {}
|
|
73378
72041
|
);
|
|
73379
72042
|
const workflows = app.workflows ?? {};
|
|
73380
72043
|
if (Object.keys(workflows).length > 0) {
|
|
73381
72044
|
const written = await writeWorkflowFiles(client, targetPath, app.id, app.name, workflows, {
|
|
73382
|
-
overwrite:
|
|
73383
|
-
kept:
|
|
72045
|
+
overwrite: opts.force === true,
|
|
72046
|
+
kept: opts.kept
|
|
73384
72047
|
});
|
|
73385
72048
|
if (written.length > 0) {
|
|
73386
72049
|
console.error(
|
|
@@ -73391,8 +72054,8 @@ async function appPull(client, args) {
|
|
|
73391
72054
|
const agents = app.agents ?? {};
|
|
73392
72055
|
if (Object.keys(agents).length > 0) {
|
|
73393
72056
|
const written = writeAgentFiles(targetPath, agents, {
|
|
73394
|
-
overwrite:
|
|
73395
|
-
kept:
|
|
72057
|
+
overwrite: opts.force === true,
|
|
72058
|
+
kept: opts.kept
|
|
73396
72059
|
});
|
|
73397
72060
|
for (const alias of written) {
|
|
73398
72061
|
const instructions = agents[alias]?.instructions;
|
|
@@ -73406,9 +72069,51 @@ async function appPull(client, args) {
|
|
|
73406
72069
|
);
|
|
73407
72070
|
}
|
|
73408
72071
|
}
|
|
73409
|
-
|
|
73410
|
-
await runNpm(["install"], targetPath);
|
|
72072
|
+
await runNpmInstall(targetPath);
|
|
73411
72073
|
writeAppDtsKitLinks(targetPath);
|
|
72074
|
+
}
|
|
72075
|
+
async function appPull(client, args) {
|
|
72076
|
+
const app = await client.getApp(args.app_id);
|
|
72077
|
+
if (!app.current_version_id && args.version === void 0) {
|
|
72078
|
+
throw new Error(
|
|
72079
|
+
`App ${app.id} has no published version yet. Deploy from another machine first, or use 'lotics app create' to scaffold a new app.`
|
|
72080
|
+
);
|
|
72081
|
+
}
|
|
72082
|
+
const versionId = args.version ?? app.current_version_id;
|
|
72083
|
+
if (!versionId) throw new Error(`App ${app.id} has no version to pull.`);
|
|
72084
|
+
const version2 = await client.getAppVersion(app.id, versionId);
|
|
72085
|
+
const sourceUrl = await client.getAppVersionSourceUrl(app.id, version2.id);
|
|
72086
|
+
const targetPath = path10.resolve(args.targetPath ?? defaultPullTarget(app.id, app.name));
|
|
72087
|
+
fs8.mkdirSync(targetPath, { recursive: true });
|
|
72088
|
+
const prior = readPriorStamp(targetPath);
|
|
72089
|
+
const tmpFile = path10.join(tmpdir(), `lotics-app-${app.id}-${Date.now()}.tar.gz`);
|
|
72090
|
+
console.error(`Downloading source archive...`);
|
|
72091
|
+
await downloadToFile(sourceUrl, tmpFile);
|
|
72092
|
+
const keptLocal = [];
|
|
72093
|
+
const stagingDir = fs8.mkdtempSync(path10.join(tmpdir(), `lotics-pull-${app.id}-`));
|
|
72094
|
+
try {
|
|
72095
|
+
await runTar(["-xzf", tmpFile, "-C", stagingDir], stagingDir);
|
|
72096
|
+
console.error(`Extracting to ${targetPath}...`);
|
|
72097
|
+
keptLocal.push(
|
|
72098
|
+
...copyTree(stagingDir, targetPath, {
|
|
72099
|
+
overwrite: args.force === true,
|
|
72100
|
+
skip: [WORKFLOWS_DIR, AGENTS_DIR].map((d) => d.split(path10.sep).join("/"))
|
|
72101
|
+
})
|
|
72102
|
+
);
|
|
72103
|
+
} finally {
|
|
72104
|
+
if (fs8.existsSync(tmpFile)) fs8.unlinkSync(tmpFile);
|
|
72105
|
+
fs8.rmSync(stagingDir, { recursive: true, force: true });
|
|
72106
|
+
}
|
|
72107
|
+
const stamp = stampAfterPull({
|
|
72108
|
+
prior,
|
|
72109
|
+
pulled: { id: versionId, number: version2.version },
|
|
72110
|
+
keptCount: keptLocal.length
|
|
72111
|
+
});
|
|
72112
|
+
await hydrateAppProject(client, targetPath, app, {
|
|
72113
|
+
stamp: { id: stamp.id, number: stamp.number },
|
|
72114
|
+
...args.force !== void 0 ? { force: args.force } : {},
|
|
72115
|
+
kept: keptLocal
|
|
72116
|
+
});
|
|
73412
72117
|
reportKeptLocalFiles(keptLocal, app.id, {
|
|
73413
72118
|
// `prior` is non-null whenever the stamp was held — `stampAfterPull` cannot
|
|
73414
72119
|
// hold against nothing — so the fallback only covers the un-held branch,
|
|
@@ -73466,7 +72171,7 @@ async function appDeploy(client, args) {
|
|
|
73466
72171
|
await writeGeneratedAppFields(
|
|
73467
72172
|
client,
|
|
73468
72173
|
projectDir,
|
|
73469
|
-
{ app_id: meta3.app_id
|
|
72174
|
+
{ app_id: meta3.app_id },
|
|
73470
72175
|
meta3.queries ?? {}
|
|
73471
72176
|
);
|
|
73472
72177
|
} catch (err2) {
|
|
@@ -73626,80 +72331,6 @@ async function readLiveQueries(client, appId) {
|
|
|
73626
72331
|
process.exit(1);
|
|
73627
72332
|
}
|
|
73628
72333
|
}
|
|
73629
|
-
async function installCommand(client, args) {
|
|
73630
|
-
const res = await client.installPackage(args.packageId, {});
|
|
73631
|
-
if (res.kind === "app") {
|
|
73632
|
-
const { app } = res;
|
|
73633
|
-
console.error(
|
|
73634
|
-
`Installed "${app.name}" (${app.id})` + (app.package_version !== null ? ` at v${app.package_version}` : "") + `.
|
|
73635
|
-
Open it from the workspace's app launcher.
|
|
73636
|
-
To work on it locally: lotics app pull ${app.id}
|
|
73637
|
-
To give it an address: lotics app subdomain <slug> (from inside that project)`
|
|
73638
|
-
);
|
|
73639
|
-
reportKnowledgeWarnings(res.knowledge_warnings);
|
|
73640
|
-
return;
|
|
73641
|
-
}
|
|
73642
|
-
console.error(
|
|
73643
|
-
`Installed content package (${res.installation.id}).
|
|
73644
|
-
Its documents and templates are now in this workspace.`
|
|
73645
|
-
);
|
|
73646
|
-
reportKnowledgeWarnings(res.warnings);
|
|
73647
|
-
}
|
|
73648
|
-
function reportKnowledgeWarnings(warnings) {
|
|
73649
|
-
const missing = warnings.missing_expected_docs;
|
|
73650
|
-
if (missing.length === 0) return;
|
|
73651
|
-
console.error(
|
|
73652
|
-
`
|
|
73653
|
-
\u26A0 ${missing.length} expected knowledge doc(s) are missing from this workspace:
|
|
73654
|
-
` + missing.map((name2) => ` \u2022 ${name2}`).join("\n") + `
|
|
73655
|
-
An agent declaring one of these reads nothing from it \u2014 the run still completes,
|
|
73656
|
-
answering from nowhere. Create them, then re-run the install.`
|
|
73657
|
-
);
|
|
73658
|
-
}
|
|
73659
|
-
async function upgradeCommand(client, args) {
|
|
73660
|
-
const projectDir = path10.resolve(args.projectDir ?? process.cwd());
|
|
73661
|
-
const meta3 = readAppMeta(projectDir);
|
|
73662
|
-
const plan = await client.previewPackageUpgrade(meta3.app_id, {});
|
|
73663
|
-
if (plan.from_version === plan.to_version) {
|
|
73664
|
-
console.error(`Already on v${plan.from_version} \u2014 nothing to take.`);
|
|
73665
|
-
return;
|
|
73666
|
-
}
|
|
73667
|
-
const blockers = [
|
|
73668
|
-
...plan.diff.breaking.map(
|
|
73669
|
-
(b) => ` \u2022 breaking: ${b.entity}.${b.alias} ${b.kind} ${b.from} \u2192 ${b.to}`
|
|
73670
|
-
),
|
|
73671
|
-
...plan.modified.map(
|
|
73672
|
-
(m) => ` \u2022 locally modified: ${m.kind} "${m.alias}"` + (m.baseline_unknown === true ? " (no baseline recorded \u2014 cannot tell what changed)" : "")
|
|
73673
|
-
),
|
|
73674
|
-
...plan.drift.map((d) => ` \u2022 drifted: ${d.namespace} "${d.alias}"`),
|
|
73675
|
-
// The FOURTH refusal source, and the one this originally missed. The server
|
|
73676
|
-
// throws a BadRequestError for every entry `knowledgeEntryNeedsConsent`
|
|
73677
|
-
// accepts, so leaving it out did not make those upgrades work — it swapped
|
|
73678
|
-
// the carefully-framed refusal for a raw wire 400. Read the canonical
|
|
73679
|
-
// predicate rather than re-deriving the rule: a hand-listed subset of a
|
|
73680
|
-
// server-side decision is how three of four got covered in the first place.
|
|
73681
|
-
...plan.knowledge.filter(knowledgeEntryNeedsConsent).map(
|
|
73682
|
-
(k) => ` \u2022 knowledge: "${k.alias}" (${k.change}${k.modified ? ", locally edited" : ""})`
|
|
73683
|
-
)
|
|
73684
|
-
];
|
|
73685
|
-
if (blockers.length > 0) {
|
|
73686
|
-
console.error(
|
|
73687
|
-
`v${plan.from_version} \u2192 v${plan.to_version} needs decisions this command will not make for you:
|
|
73688
|
-
` + blockers.join("\n") + `
|
|
73689
|
-
|
|
73690
|
-
Each one resolves by choosing what to KEEP, and guessing would discard
|
|
73691
|
-
work nobody asked to lose. Resolve them, or ask an operator to run the
|
|
73692
|
-
upgrade with explicit resolutions.`
|
|
73693
|
-
);
|
|
73694
|
-
process.exit(1);
|
|
73695
|
-
}
|
|
73696
|
-
const applied = await client.upgradePackage(meta3.app_id, { version: plan.to_version });
|
|
73697
|
-
console.error(
|
|
73698
|
-
`Upgraded to v${applied.package_version ?? plan.to_version}.` + (plan.changelog ? `
|
|
73699
|
-
${plan.changelog}` : "") + `
|
|
73700
|
-
Run \`lotics app pull\` to bring this checkout in step.`
|
|
73701
|
-
);
|
|
73702
|
-
}
|
|
73703
72334
|
async function appCheck(client, args = {}) {
|
|
73704
72335
|
const projectDir = path10.resolve(args.projectDir ?? process.cwd());
|
|
73705
72336
|
const meta3 = readAppMeta(projectDir);
|
|
@@ -74645,6 +73276,10 @@ function parseArgs(argv) {
|
|
|
74645
73276
|
printCreated: false,
|
|
74646
73277
|
cleanup: false,
|
|
74647
73278
|
prune: false,
|
|
73279
|
+
noSampleData: false,
|
|
73280
|
+
adopt: false,
|
|
73281
|
+
entity: [],
|
|
73282
|
+
limit: void 0,
|
|
74648
73283
|
version: false,
|
|
74649
73284
|
help: false
|
|
74650
73285
|
};
|
|
@@ -74749,6 +73384,20 @@ function parseArgs(argv) {
|
|
|
74749
73384
|
case "--cleanup":
|
|
74750
73385
|
flags.cleanup = true;
|
|
74751
73386
|
break;
|
|
73387
|
+
case "--no-sample-data":
|
|
73388
|
+
flags.noSampleData = true;
|
|
73389
|
+
break;
|
|
73390
|
+
case "--adopt":
|
|
73391
|
+
flags.adopt = true;
|
|
73392
|
+
break;
|
|
73393
|
+
// Comma-separated AND repeatable, like `--tags` above: an agent scripting
|
|
73394
|
+
// this reaches for whichever form it knows, and both accumulate.
|
|
73395
|
+
case "--entity":
|
|
73396
|
+
flags.entity = [...flags.entity, ...splitList(argv[++i2])];
|
|
73397
|
+
break;
|
|
73398
|
+
case "--limit":
|
|
73399
|
+
flags.limit = argv[++i2];
|
|
73400
|
+
break;
|
|
74752
73401
|
case "--prune":
|
|
74753
73402
|
flags.prune = true;
|
|
74754
73403
|
break;
|
|
@@ -74792,6 +73441,207 @@ function parseArgs(argv) {
|
|
|
74792
73441
|
return { command, subcommand, toolArgs, restArgs, flags, unknownFlag };
|
|
74793
73442
|
}
|
|
74794
73443
|
|
|
73444
|
+
// src/starter_commands.ts
|
|
73445
|
+
import fs9 from "node:fs";
|
|
73446
|
+
import path11 from "node:path";
|
|
73447
|
+
import { tmpdir as tmpdir2 } from "node:os";
|
|
73448
|
+
async function starterList(client) {
|
|
73449
|
+
const starters = await client.listStarters();
|
|
73450
|
+
if (starters.length === 0) {
|
|
73451
|
+
console.error(
|
|
73452
|
+
"No starters available to this organization.\n A starter is copyable when Lotics has reviewed it, or when your own organization published it."
|
|
73453
|
+
);
|
|
73454
|
+
return;
|
|
73455
|
+
}
|
|
73456
|
+
const width = Math.max(...starters.map((s) => s.id.length));
|
|
73457
|
+
console.error(`${starters.length} starter${starters.length === 1 ? "" : "s"}:
|
|
73458
|
+
`);
|
|
73459
|
+
for (const s of starters) {
|
|
73460
|
+
const tags = [
|
|
73461
|
+
s.is_official ? "official" : null,
|
|
73462
|
+
s.owned_by_caller === true ? "yours" : null
|
|
73463
|
+
].filter((t) => t !== null);
|
|
73464
|
+
console.log(
|
|
73465
|
+
` ${s.id.padEnd(width)} ${s.name}${tags.length > 0 ? ` [${tags.join(", ")}]` : ""}`
|
|
73466
|
+
);
|
|
73467
|
+
if (s.description) console.log(` ${" ".repeat(width)} ${s.description}`);
|
|
73468
|
+
}
|
|
73469
|
+
console.error(`
|
|
73470
|
+
lotics starter init <starter_id> Copy one into this workspace`);
|
|
73471
|
+
}
|
|
73472
|
+
async function starterShow(client, starter_id) {
|
|
73473
|
+
const starter = await client.getPackage(starter_id);
|
|
73474
|
+
console.log(`${starter.name} (${starter.id})`);
|
|
73475
|
+
if (starter.description) console.log(starter.description);
|
|
73476
|
+
console.log(
|
|
73477
|
+
`
|
|
73478
|
+
version ${starter.latest_version}
|
|
73479
|
+
trust ${starter.is_official ? "official \u2014 reviewed by Lotics" : starter.owned_by_caller === true ? "your organization's own" : "not copyable from this organization"}`
|
|
73480
|
+
);
|
|
73481
|
+
if (starter.retired_at !== null) {
|
|
73482
|
+
console.log(`retired ${starter.retired_at} \u2014 can no longer be copied`);
|
|
73483
|
+
}
|
|
73484
|
+
}
|
|
73485
|
+
function reportKnowledgeWarnings(warnings) {
|
|
73486
|
+
const missing = warnings.missing_expected_docs;
|
|
73487
|
+
if (missing.length === 0) return;
|
|
73488
|
+
console.error(
|
|
73489
|
+
`
|
|
73490
|
+
\u26A0 ${missing.length} knowledge doc(s) this starter's agents expect are missing here:
|
|
73491
|
+
` + missing.map((name2) => ` \u2022 ${name2}`).join("\n") + `
|
|
73492
|
+
An agent declaring one of these reads nothing from it \u2014 the run still completes,
|
|
73493
|
+
answering from nowhere. Create them with those names, or edit the agent.`
|
|
73494
|
+
);
|
|
73495
|
+
}
|
|
73496
|
+
async function starterInit(client, args) {
|
|
73497
|
+
const starter = await client.getPackage(args.starter_id);
|
|
73498
|
+
console.error(
|
|
73499
|
+
`Copying ${starter.name}${starter.is_official ? " (official)" : ""} into this workspace\u2026`
|
|
73500
|
+
);
|
|
73501
|
+
const result = await client.instantiateStarter(args.starter_id, {
|
|
73502
|
+
...args.noSampleData === true ? { no_sample_data: true } : {},
|
|
73503
|
+
...args.adopt === true ? { adopt: true } : {}
|
|
73504
|
+
});
|
|
73505
|
+
const entities = Object.keys(result.binding.entities ?? {}).length;
|
|
73506
|
+
const docs = Object.keys(result.binding.knowledge ?? {}).length;
|
|
73507
|
+
const templates = Object.keys(result.binding.templates ?? {}).length;
|
|
73508
|
+
const records = Object.values(result.sample_record_ids).reduce((n, ids) => n + ids.length, 0);
|
|
73509
|
+
console.error(
|
|
73510
|
+
` Created ${entities} table${entities === 1 ? "" : "s"}, ${templates} template${templates === 1 ? "" : "s"}, ${docs} knowledge doc${docs === 1 ? "" : "s"}, ${records} sample record${records === 1 ? "" : "s"}.`
|
|
73511
|
+
);
|
|
73512
|
+
reportKnowledgeWarnings(result.knowledge_warnings);
|
|
73513
|
+
if (result.app_id === null || result.bundle_url === null) {
|
|
73514
|
+
console.error(`
|
|
73515
|
+
Done. The documents and knowledge are yours to edit \u2014 nothing links back.`);
|
|
73516
|
+
return;
|
|
73517
|
+
}
|
|
73518
|
+
const targetPath = path11.resolve(args.targetPath ?? appDirName(starter.name));
|
|
73519
|
+
if (fs9.existsSync(targetPath) && fs9.readdirSync(targetPath).length > 0) {
|
|
73520
|
+
throw new Error(
|
|
73521
|
+
`Target directory ${targetPath} is not empty. The app (${result.app_id}) was created \u2014 pass an empty path and re-run, or finish it with "lotics app pull ${result.app_id}".`
|
|
73522
|
+
);
|
|
73523
|
+
}
|
|
73524
|
+
fs9.mkdirSync(targetPath, { recursive: true });
|
|
73525
|
+
console.error(`Downloading source\u2026`);
|
|
73526
|
+
const bundleFile = path11.join(tmpdir2(), `lotics-starter-${args.starter_id}-${process.pid}.tar.gz`);
|
|
73527
|
+
const wrapperDir = fs9.mkdtempSync(path11.join(tmpdir2(), `lotics-starter-`));
|
|
73528
|
+
try {
|
|
73529
|
+
await downloadToFile(result.bundle_url, bundleFile);
|
|
73530
|
+
await runTar(["-xzf", bundleFile, "-C", wrapperDir], wrapperDir);
|
|
73531
|
+
const sourceArchive = path11.join(wrapperDir, "source.tar.gz");
|
|
73532
|
+
if (!fs9.existsSync(sourceArchive)) {
|
|
73533
|
+
throw new Error(
|
|
73534
|
+
`Starter bundle carried no source.tar.gz \u2014 the app (${result.app_id}) exists but has no code. Report this to the starter's publisher.`
|
|
73535
|
+
);
|
|
73536
|
+
}
|
|
73537
|
+
await runTar(["-xzf", sourceArchive, "-C", targetPath], targetPath);
|
|
73538
|
+
} finally {
|
|
73539
|
+
if (fs9.existsSync(bundleFile)) fs9.unlinkSync(bundleFile);
|
|
73540
|
+
fs9.rmSync(wrapperDir, { recursive: true, force: true });
|
|
73541
|
+
}
|
|
73542
|
+
for (const dir of ["knowledge", "fixtures"]) {
|
|
73543
|
+
fs9.rmSync(path11.join(targetPath, dir), { recursive: true, force: true });
|
|
73544
|
+
}
|
|
73545
|
+
const app = await client.getApp(result.app_id);
|
|
73546
|
+
const kept = [];
|
|
73547
|
+
await hydrateAppProject(client, targetPath, app, {
|
|
73548
|
+
// Nothing is deployed yet; the build below is what mints v1.
|
|
73549
|
+
stamp: { id: null, number: null },
|
|
73550
|
+
kept
|
|
73551
|
+
});
|
|
73552
|
+
if (starter.owned_by_caller !== true) {
|
|
73553
|
+
console.error(
|
|
73554
|
+
`
|
|
73555
|
+
Building ${starter.name} \u2014 this runs its build on your machine (its package scripts
|
|
73556
|
+
and vite config are the publisher's code, executed as you).${starter.is_official ? " Lotics reviewed this starter." : ""}`
|
|
73557
|
+
);
|
|
73558
|
+
} else {
|
|
73559
|
+
console.error(`Building and deploying\u2026`);
|
|
73560
|
+
}
|
|
73561
|
+
await runNpm(["run", "build"], targetPath);
|
|
73562
|
+
await appDeploy(client, {
|
|
73563
|
+
projectDir: targetPath,
|
|
73564
|
+
message: `Copied from starter ${starter.name}`
|
|
73565
|
+
});
|
|
73566
|
+
let signInUrl = null;
|
|
73567
|
+
try {
|
|
73568
|
+
const link = await client.login({
|
|
73569
|
+
return_link: true,
|
|
73570
|
+
redirect_path: `/apps/${result.app_id}`
|
|
73571
|
+
});
|
|
73572
|
+
signInUrl = link.url ?? null;
|
|
73573
|
+
} catch (error52) {
|
|
73574
|
+
console.error(
|
|
73575
|
+
`
|
|
73576
|
+
(no sign-in link: ${error52 instanceof Error ? error52.message : String(error52)})
|
|
73577
|
+
The copy is complete either way \u2014 open it with "lotics auth web".`
|
|
73578
|
+
);
|
|
73579
|
+
signInUrl = null;
|
|
73580
|
+
}
|
|
73581
|
+
console.error(
|
|
73582
|
+
`
|
|
73583
|
+
Done \u2014 ${starter.name} is live and yours.
|
|
73584
|
+
App: ${result.app_id}
|
|
73585
|
+
Project: ${targetPath}
|
|
73586
|
+
|
|
73587
|
+
Edit anything: the tables, the app source, the templates, the docs. There is no
|
|
73588
|
+
link back to the starter and nothing to upgrade \u2014 this is your app now.
|
|
73589
|
+
Ship a change: cd ${path11.relative(process.cwd(), targetPath) || "."} && lotics app deploy -m "<what changed>"`
|
|
73590
|
+
);
|
|
73591
|
+
if (records > 0) {
|
|
73592
|
+
console.error(
|
|
73593
|
+
`
|
|
73594
|
+
${records} sample record${records === 1 ? "" : "s"} came with it. They are ordinary records \u2014
|
|
73595
|
+
delete them whenever you like, or re-run with --no-sample-data next time.`
|
|
73596
|
+
);
|
|
73597
|
+
}
|
|
73598
|
+
if (signInUrl !== null) {
|
|
73599
|
+
console.error(
|
|
73600
|
+
`
|
|
73601
|
+
Open it \u2014 one-time sign-in link, expires in 15 minutes:
|
|
73602
|
+
${signInUrl}`
|
|
73603
|
+
);
|
|
73604
|
+
}
|
|
73605
|
+
}
|
|
73606
|
+
async function starterFixturesCapture(client, args) {
|
|
73607
|
+
const projectDir = path11.resolve(args.projectDir ?? process.cwd());
|
|
73608
|
+
const meta3 = readAppMeta(projectDir);
|
|
73609
|
+
const result = await client.captureStarterFixtures(meta3.app_id, {
|
|
73610
|
+
entities: args.entities,
|
|
73611
|
+
...args.limit !== void 0 ? { limit: args.limit } : {}
|
|
73612
|
+
});
|
|
73613
|
+
const fixturesDir = path11.join(projectDir, "fixtures");
|
|
73614
|
+
fs9.mkdirSync(fixturesDir, { recursive: true });
|
|
73615
|
+
let totalRows = 0;
|
|
73616
|
+
for (const entry of result.captured) {
|
|
73617
|
+
const file2 = path11.join(projectDir, entry.content_ref);
|
|
73618
|
+
fs9.writeFileSync(file2, `${JSON.stringify(entry.file, null, 2)}
|
|
73619
|
+
`, "utf-8");
|
|
73620
|
+
totalRows += entry.file.rows.length;
|
|
73621
|
+
console.error(
|
|
73622
|
+
` ${entry.content_ref} \u2014 ${entry.file.rows.length} row${entry.file.rows.length === 1 ? "" : "s"}`
|
|
73623
|
+
);
|
|
73624
|
+
for (const note of entry.notes) console.error(` \u26A0 ${note}`);
|
|
73625
|
+
}
|
|
73626
|
+
if (result.captured.length === 0) {
|
|
73627
|
+
console.error(
|
|
73628
|
+
`This app declares no tables, so there is nothing to capture.
|
|
73629
|
+
Entities available: ${result.available_entity_aliases.join(", ") || "(none)"}`
|
|
73630
|
+
);
|
|
73631
|
+
return;
|
|
73632
|
+
}
|
|
73633
|
+
console.error(
|
|
73634
|
+
`
|
|
73635
|
+
Captured ${totalRows} row${totalRows === 1 ? "" : "s"} across ${result.captured.length} entit${result.captured.length === 1 ? "y" : "ies"}.
|
|
73636
|
+
|
|
73637
|
+
READ WHAT IT WROTE before committing. These rows ship inside the starter and are
|
|
73638
|
+
created in every workspace that copies it \u2014 a real customer name, a real price or a
|
|
73639
|
+
real address captured here is published.
|
|
73640
|
+
|
|
73641
|
+
Entities available: ${result.available_entity_aliases.join(", ")}`
|
|
73642
|
+
);
|
|
73643
|
+
}
|
|
73644
|
+
|
|
74795
73645
|
// src/inputs.ts
|
|
74796
73646
|
async function ingestJsonArgs(opts) {
|
|
74797
73647
|
let raw = opts.rawArg;
|
|
@@ -74851,11 +73701,11 @@ async function validateOrgWorkspacePin(client, orgId, profile) {
|
|
|
74851
73701
|
}
|
|
74852
73702
|
|
|
74853
73703
|
// src/xlsx.ts
|
|
74854
|
-
import
|
|
73704
|
+
import fs11 from "node:fs";
|
|
74855
73705
|
|
|
74856
73706
|
// src/file_command_io.ts
|
|
74857
|
-
import
|
|
74858
|
-
import
|
|
73707
|
+
import fs10 from "node:fs";
|
|
73708
|
+
import path12 from "node:path";
|
|
74859
73709
|
var CliError = class extends Error {
|
|
74860
73710
|
constructor(message2) {
|
|
74861
73711
|
super(message2);
|
|
@@ -74876,14 +73726,14 @@ function rejectExtraArgs(rest2, arity, usage) {
|
|
|
74876
73726
|
fail2(`${usage} takes ${arity} argument${arity === 1 ? "" : "s"} after <file>, got ${rest2.length}. Unused: ${rest2.slice(arity).join(" ")}`);
|
|
74877
73727
|
}
|
|
74878
73728
|
function writeFileAtomic(filePath, bytes) {
|
|
74879
|
-
const dir =
|
|
74880
|
-
const tmp =
|
|
74881
|
-
|
|
73729
|
+
const dir = path12.dirname(path12.resolve(filePath));
|
|
73730
|
+
const tmp = path12.join(dir, `.${path12.basename(filePath)}.${process.pid}.${Date.now()}.tmp`);
|
|
73731
|
+
fs10.writeFileSync(tmp, bytes);
|
|
74882
73732
|
try {
|
|
74883
|
-
|
|
73733
|
+
fs10.renameSync(tmp, filePath);
|
|
74884
73734
|
} catch (error52) {
|
|
74885
73735
|
try {
|
|
74886
|
-
|
|
73736
|
+
fs10.unlinkSync(tmp);
|
|
74887
73737
|
} catch {
|
|
74888
73738
|
}
|
|
74889
73739
|
throw error52;
|
|
@@ -77680,16 +76530,16 @@ var MatcherView = class {
|
|
|
77680
76530
|
* @returns {string|undefined}
|
|
77681
76531
|
*/
|
|
77682
76532
|
getCurrentTag() {
|
|
77683
|
-
const
|
|
77684
|
-
return
|
|
76533
|
+
const path14 = this._matcher.path;
|
|
76534
|
+
return path14.length > 0 ? path14[path14.length - 1].tag : void 0;
|
|
77685
76535
|
}
|
|
77686
76536
|
/**
|
|
77687
76537
|
* Get current namespace.
|
|
77688
76538
|
* @returns {string|undefined}
|
|
77689
76539
|
*/
|
|
77690
76540
|
getCurrentNamespace() {
|
|
77691
|
-
const
|
|
77692
|
-
return
|
|
76541
|
+
const path14 = this._matcher.path;
|
|
76542
|
+
return path14.length > 0 ? path14[path14.length - 1].namespace : void 0;
|
|
77693
76543
|
}
|
|
77694
76544
|
/**
|
|
77695
76545
|
* Get current node's attribute value.
|
|
@@ -77697,9 +76547,9 @@ var MatcherView = class {
|
|
|
77697
76547
|
* @returns {*}
|
|
77698
76548
|
*/
|
|
77699
76549
|
getAttrValue(attrName) {
|
|
77700
|
-
const
|
|
77701
|
-
if (
|
|
77702
|
-
return
|
|
76550
|
+
const path14 = this._matcher.path;
|
|
76551
|
+
if (path14.length === 0) return void 0;
|
|
76552
|
+
return path14[path14.length - 1].values?.[attrName];
|
|
77703
76553
|
}
|
|
77704
76554
|
/**
|
|
77705
76555
|
* Check if current node has an attribute.
|
|
@@ -77707,9 +76557,9 @@ var MatcherView = class {
|
|
|
77707
76557
|
* @returns {boolean}
|
|
77708
76558
|
*/
|
|
77709
76559
|
hasAttr(attrName) {
|
|
77710
|
-
const
|
|
77711
|
-
if (
|
|
77712
|
-
const current =
|
|
76560
|
+
const path14 = this._matcher.path;
|
|
76561
|
+
if (path14.length === 0) return false;
|
|
76562
|
+
const current = path14[path14.length - 1];
|
|
77713
76563
|
return current.values !== void 0 && attrName in current.values;
|
|
77714
76564
|
}
|
|
77715
76565
|
/**
|
|
@@ -77735,18 +76585,18 @@ var MatcherView = class {
|
|
|
77735
76585
|
* @returns {number}
|
|
77736
76586
|
*/
|
|
77737
76587
|
getPosition() {
|
|
77738
|
-
const
|
|
77739
|
-
if (
|
|
77740
|
-
return
|
|
76588
|
+
const path14 = this._matcher.path;
|
|
76589
|
+
if (path14.length === 0) return -1;
|
|
76590
|
+
return path14[path14.length - 1].position ?? 0;
|
|
77741
76591
|
}
|
|
77742
76592
|
/**
|
|
77743
76593
|
* Get current node's repeat counter (occurrence count of this tag name).
|
|
77744
76594
|
* @returns {number}
|
|
77745
76595
|
*/
|
|
77746
76596
|
getCounter() {
|
|
77747
|
-
const
|
|
77748
|
-
if (
|
|
77749
|
-
return
|
|
76597
|
+
const path14 = this._matcher.path;
|
|
76598
|
+
if (path14.length === 0) return -1;
|
|
76599
|
+
return path14[path14.length - 1].counter ?? 0;
|
|
77750
76600
|
}
|
|
77751
76601
|
/**
|
|
77752
76602
|
* Get current node's sibling index (alias for getPosition).
|
|
@@ -80627,14 +79477,14 @@ function isOle2(bytes) {
|
|
|
80627
79477
|
}
|
|
80628
79478
|
function readCfbStreams(bytes) {
|
|
80629
79479
|
const dv = new DataView(bytes.buffer, bytes.byteOffset, bytes.byteLength);
|
|
80630
|
-
const
|
|
80631
|
-
const
|
|
80632
|
-
const sectorSize = 1 <<
|
|
80633
|
-
const miniSectorSize = 1 <<
|
|
80634
|
-
const firstDirSector =
|
|
80635
|
-
const miniCutoff =
|
|
80636
|
-
const firstMiniFatSector =
|
|
80637
|
-
const firstDifatSector =
|
|
79480
|
+
const u163 = (o) => dv.getUint16(o, true);
|
|
79481
|
+
const u322 = (o) => dv.getUint32(o, true);
|
|
79482
|
+
const sectorSize = 1 << u163(30);
|
|
79483
|
+
const miniSectorSize = 1 << u163(32);
|
|
79484
|
+
const firstDirSector = u322(48);
|
|
79485
|
+
const miniCutoff = u322(56);
|
|
79486
|
+
const firstMiniFatSector = u322(60);
|
|
79487
|
+
const firstDifatSector = u322(68);
|
|
80638
79488
|
if (sectorSize < 512 || sectorSize > 1 << 20) {
|
|
80639
79489
|
throw new Error("Unsupported OLE2 file: invalid sector size");
|
|
80640
79490
|
}
|
|
@@ -80642,7 +79492,7 @@ function readCfbStreams(bytes) {
|
|
|
80642
79492
|
const maxSectors = Math.ceil(bytes.length / sectorSize) + 1;
|
|
80643
79493
|
const difat = [];
|
|
80644
79494
|
for (let i2 = 0; i2 < 109; i2++) {
|
|
80645
|
-
const v =
|
|
79495
|
+
const v = u322(76 + i2 * 4);
|
|
80646
79496
|
if (v !== FREESECT) difat.push(v);
|
|
80647
79497
|
}
|
|
80648
79498
|
let ds = firstDifatSector;
|
|
@@ -80652,10 +79502,10 @@ function readCfbStreams(bytes) {
|
|
|
80652
79502
|
seenDifat.add(ds);
|
|
80653
79503
|
const base = sectorOffset(ds);
|
|
80654
79504
|
for (let i2 = 0; i2 < entriesPerSector - 1; i2++) {
|
|
80655
|
-
const v =
|
|
79505
|
+
const v = u322(base + i2 * 4);
|
|
80656
79506
|
if (v !== FREESECT) difat.push(v);
|
|
80657
79507
|
}
|
|
80658
|
-
ds =
|
|
79508
|
+
ds = u322(base + (entriesPerSector - 1) * 4);
|
|
80659
79509
|
}
|
|
80660
79510
|
const fat = [];
|
|
80661
79511
|
for (const fatSector of difat) {
|
|
@@ -80663,7 +79513,7 @@ function readCfbStreams(bytes) {
|
|
|
80663
79513
|
if (fatSector >= maxSectors) continue;
|
|
80664
79514
|
const base = sectorOffset(fatSector);
|
|
80665
79515
|
for (let i2 = 0; i2 < entriesPerSector && fat.length < maxSectors; i2++) {
|
|
80666
|
-
fat.push(
|
|
79516
|
+
fat.push(u322(base + i2 * 4));
|
|
80667
79517
|
}
|
|
80668
79518
|
}
|
|
80669
79519
|
const readChain = (src, start, size2, ss, offOf, chain2) => {
|
|
@@ -83404,10 +82254,10 @@ function resolveRelativePath(basePath, relativePath) {
|
|
|
83404
82254
|
}
|
|
83405
82255
|
return resolved.join("/");
|
|
83406
82256
|
}
|
|
83407
|
-
function findZipEntry(zipEntries,
|
|
83408
|
-
if (zipEntries[
|
|
83409
|
-
if (zipEntries[`xl/${
|
|
83410
|
-
const noSlash =
|
|
82257
|
+
function findZipEntry(zipEntries, path14) {
|
|
82258
|
+
if (zipEntries[path14]) return zipEntries[path14];
|
|
82259
|
+
if (zipEntries[`xl/${path14}`]) return zipEntries[`xl/${path14}`];
|
|
82260
|
+
const noSlash = path14.replace(/^\//, "");
|
|
83411
82261
|
if (zipEntries[noSlash]) return zipEntries[noSlash];
|
|
83412
82262
|
return void 0;
|
|
83413
82263
|
}
|
|
@@ -84523,6 +83373,221 @@ function ensureVmlArray(val) {
|
|
|
84523
83373
|
return Array.isArray(val) ? val : [val];
|
|
84524
83374
|
}
|
|
84525
83375
|
|
|
83376
|
+
// ../xlsx/src/biff8_styles.ts
|
|
83377
|
+
var DEFAULT_PALETTE = [
|
|
83378
|
+
"#000000",
|
|
83379
|
+
"#FFFFFF",
|
|
83380
|
+
"#FF0000",
|
|
83381
|
+
"#00FF00",
|
|
83382
|
+
"#0000FF",
|
|
83383
|
+
"#FFFF00",
|
|
83384
|
+
"#FF00FF",
|
|
83385
|
+
"#00FFFF",
|
|
83386
|
+
"#000000",
|
|
83387
|
+
"#FFFFFF",
|
|
83388
|
+
"#FF0000",
|
|
83389
|
+
"#00FF00",
|
|
83390
|
+
"#0000FF",
|
|
83391
|
+
"#FFFF00",
|
|
83392
|
+
"#FF00FF",
|
|
83393
|
+
"#00FFFF",
|
|
83394
|
+
"#800000",
|
|
83395
|
+
"#008000",
|
|
83396
|
+
"#000080",
|
|
83397
|
+
"#808000",
|
|
83398
|
+
"#800080",
|
|
83399
|
+
"#008080",
|
|
83400
|
+
"#C0C0C0",
|
|
83401
|
+
"#808080",
|
|
83402
|
+
"#9999FF",
|
|
83403
|
+
"#993366",
|
|
83404
|
+
"#FFFFCC",
|
|
83405
|
+
"#CCFFFF",
|
|
83406
|
+
"#660066",
|
|
83407
|
+
"#FF8080",
|
|
83408
|
+
"#0066CC",
|
|
83409
|
+
"#CCCCFF",
|
|
83410
|
+
"#000080",
|
|
83411
|
+
"#FF00FF",
|
|
83412
|
+
"#FFFF00",
|
|
83413
|
+
"#00FFFF",
|
|
83414
|
+
"#800080",
|
|
83415
|
+
"#800000",
|
|
83416
|
+
"#008080",
|
|
83417
|
+
"#0000FF",
|
|
83418
|
+
"#00CCFF",
|
|
83419
|
+
"#CCFFFF",
|
|
83420
|
+
"#CCFFCC",
|
|
83421
|
+
"#FFFF99",
|
|
83422
|
+
"#99CCFF",
|
|
83423
|
+
"#FF99CC",
|
|
83424
|
+
"#CC99FF",
|
|
83425
|
+
"#FFCC99",
|
|
83426
|
+
"#3366FF",
|
|
83427
|
+
"#33CCCC",
|
|
83428
|
+
"#99CC00",
|
|
83429
|
+
"#FFCC00",
|
|
83430
|
+
"#FF9900",
|
|
83431
|
+
"#FF6600",
|
|
83432
|
+
"#666699",
|
|
83433
|
+
"#969696",
|
|
83434
|
+
"#003366",
|
|
83435
|
+
"#339966",
|
|
83436
|
+
"#003300",
|
|
83437
|
+
"#333300",
|
|
83438
|
+
"#993300",
|
|
83439
|
+
"#993366",
|
|
83440
|
+
"#333399",
|
|
83441
|
+
"#333333"
|
|
83442
|
+
];
|
|
83443
|
+
var AUTOMATIC = /* @__PURE__ */ new Set([64, 65, 32767]);
|
|
83444
|
+
var u162 = (b, o) => b[o] | b[o + 1] << 8;
|
|
83445
|
+
var u32 = (b, o) => (u162(b, o) | u162(b, o + 2) << 16) >>> 0;
|
|
83446
|
+
function parsePalette(body) {
|
|
83447
|
+
const palette = [...DEFAULT_PALETTE];
|
|
83448
|
+
const count = u162(body, 0);
|
|
83449
|
+
for (let i2 = 0; i2 < count && 2 + i2 * 4 + 3 < body.length; i2++) {
|
|
83450
|
+
const o = 2 + i2 * 4;
|
|
83451
|
+
const hex3 = (n) => n.toString(16).padStart(2, "0").toUpperCase();
|
|
83452
|
+
palette[8 + i2] = `#${hex3(body[o])}${hex3(body[o + 1])}${hex3(body[o + 2])}`;
|
|
83453
|
+
}
|
|
83454
|
+
return palette;
|
|
83455
|
+
}
|
|
83456
|
+
function defaultPalette() {
|
|
83457
|
+
return [...DEFAULT_PALETTE];
|
|
83458
|
+
}
|
|
83459
|
+
function parseFont2(body) {
|
|
83460
|
+
const grbit = u162(body, 2);
|
|
83461
|
+
const uls = body[10];
|
|
83462
|
+
const sss = u162(body, 8);
|
|
83463
|
+
let name2 = "";
|
|
83464
|
+
if (body.length > 15) {
|
|
83465
|
+
const cch = body[14];
|
|
83466
|
+
const high = (body[15] & 1) !== 0;
|
|
83467
|
+
for (let i2 = 0; i2 < cch; i2++) {
|
|
83468
|
+
const o = 16 + (high ? i2 * 2 : i2);
|
|
83469
|
+
if (o >= body.length) break;
|
|
83470
|
+
name2 += String.fromCharCode(high ? body[o] | body[o + 1] << 8 : body[o]);
|
|
83471
|
+
}
|
|
83472
|
+
}
|
|
83473
|
+
return {
|
|
83474
|
+
size: u162(body, 0) / 20,
|
|
83475
|
+
bold: u162(body, 6) >= 600,
|
|
83476
|
+
italic: (grbit & 2) !== 0,
|
|
83477
|
+
strike: (grbit & 8) !== 0,
|
|
83478
|
+
underline: uls === 1 || uls === 33 ? "single" : uls === 2 || uls === 34 ? "double" : void 0,
|
|
83479
|
+
vertAlign: sss === 1 ? "superscript" : sss === 2 ? "subscript" : void 0,
|
|
83480
|
+
colorIndex: u162(body, 4),
|
|
83481
|
+
name: name2
|
|
83482
|
+
};
|
|
83483
|
+
}
|
|
83484
|
+
function parseXf2(body) {
|
|
83485
|
+
const alignByte = body[6] ?? 0;
|
|
83486
|
+
const indentByte = body[8] ?? 0;
|
|
83487
|
+
const b1 = u32(body, 10);
|
|
83488
|
+
const b22 = u32(body, 14);
|
|
83489
|
+
const fill = u162(body, 18);
|
|
83490
|
+
const HORIZ = [
|
|
83491
|
+
void 0,
|
|
83492
|
+
"left",
|
|
83493
|
+
"center",
|
|
83494
|
+
"right",
|
|
83495
|
+
void 0,
|
|
83496
|
+
void 0,
|
|
83497
|
+
"center"
|
|
83498
|
+
];
|
|
83499
|
+
const VERT = ["top", "middle", "bottom", "middle", "middle"];
|
|
83500
|
+
const rot = body[7] ?? 0;
|
|
83501
|
+
return {
|
|
83502
|
+
fontIndex: u162(body, 0),
|
|
83503
|
+
horizontal: HORIZ[alignByte & 7],
|
|
83504
|
+
vertical: VERT[alignByte >> 4 & 7],
|
|
83505
|
+
wrap: (alignByte & 8) !== 0,
|
|
83506
|
+
shrink: (indentByte & 16) !== 0,
|
|
83507
|
+
indent: indentByte & 15,
|
|
83508
|
+
// 0–90 means degrees; 91–180 means −1…−90; 255 is stacked/vertical text.
|
|
83509
|
+
rotation: rot === 255 ? 255 : rot <= 90 ? rot : -(rot - 90),
|
|
83510
|
+
borders: {
|
|
83511
|
+
left: b1 & 15,
|
|
83512
|
+
right: b1 >> 4 & 15,
|
|
83513
|
+
top: b1 >> 8 & 15,
|
|
83514
|
+
bottom: b1 >> 12 & 15,
|
|
83515
|
+
leftColor: b1 >> 16 & 127,
|
|
83516
|
+
rightColor: b1 >> 23 & 127,
|
|
83517
|
+
topColor: b22 & 127,
|
|
83518
|
+
bottomColor: b22 >> 7 & 127
|
|
83519
|
+
},
|
|
83520
|
+
fillPattern: b22 >>> 26 & 63,
|
|
83521
|
+
fillFore: fill & 127,
|
|
83522
|
+
fillBack: fill >> 7 & 127
|
|
83523
|
+
};
|
|
83524
|
+
}
|
|
83525
|
+
var BORDER_STYLES = [
|
|
83526
|
+
"none",
|
|
83527
|
+
"thin",
|
|
83528
|
+
"medium",
|
|
83529
|
+
"dashed",
|
|
83530
|
+
"dotted",
|
|
83531
|
+
"thick",
|
|
83532
|
+
"double",
|
|
83533
|
+
"hair",
|
|
83534
|
+
"mediumDashed",
|
|
83535
|
+
"dashDot",
|
|
83536
|
+
"mediumDashDot",
|
|
83537
|
+
"dashDotDot",
|
|
83538
|
+
"mediumDashDotDot",
|
|
83539
|
+
"slantDashDot"
|
|
83540
|
+
];
|
|
83541
|
+
var BORDER_WIDTH = { thick: 3, medium: 2, mediumDashed: 2, mediumDashDot: 2, mediumDashDotDot: 2, double: 3, hair: 1 };
|
|
83542
|
+
function colorOf(index, palette) {
|
|
83543
|
+
if (AUTOMATIC.has(index)) return void 0;
|
|
83544
|
+
return palette[index];
|
|
83545
|
+
}
|
|
83546
|
+
function borderOf(style, colorIndex, palette) {
|
|
83547
|
+
if (style === 0) return void 0;
|
|
83548
|
+
const name2 = BORDER_STYLES[style] ?? "thin";
|
|
83549
|
+
return { width: BORDER_WIDTH[name2] ?? 1, style: name2, color: colorOf(colorIndex, palette) ?? "#000000" };
|
|
83550
|
+
}
|
|
83551
|
+
function toCellStyle(xf, fonts, palette) {
|
|
83552
|
+
const style = {};
|
|
83553
|
+
const font = fonts[xf.fontIndex];
|
|
83554
|
+
if (font) {
|
|
83555
|
+
if (font.bold) style.fontBold = true;
|
|
83556
|
+
if (font.italic) style.fontItalic = true;
|
|
83557
|
+
if (font.strike) style.fontStrike = true;
|
|
83558
|
+
if (font.underline) style.fontUnderline = font.underline;
|
|
83559
|
+
if (font.vertAlign) style.fontVertAlign = font.vertAlign;
|
|
83560
|
+
if (font.size > 0) style.fontSize = font.size;
|
|
83561
|
+
if (font.name) style.fontName = font.name;
|
|
83562
|
+
const color = colorOf(font.colorIndex, palette);
|
|
83563
|
+
if (color) style.fontColor = color;
|
|
83564
|
+
}
|
|
83565
|
+
if (xf.horizontal) style.horizontalAlign = xf.horizontal;
|
|
83566
|
+
if (xf.vertical) style.verticalAlign = xf.vertical;
|
|
83567
|
+
if (xf.wrap) style.wrapText = true;
|
|
83568
|
+
if (xf.shrink) style.shrinkToFit = true;
|
|
83569
|
+
if (xf.indent > 0) style.indent = xf.indent;
|
|
83570
|
+
if (xf.rotation === 255) style.textRotation = "vertical";
|
|
83571
|
+
else if (xf.rotation !== 0) style.textRotation = xf.rotation;
|
|
83572
|
+
const left = borderOf(xf.borders.left, xf.borders.leftColor, palette);
|
|
83573
|
+
const right = borderOf(xf.borders.right, xf.borders.rightColor, palette);
|
|
83574
|
+
const top = borderOf(xf.borders.top, xf.borders.topColor, palette);
|
|
83575
|
+
const bottom = borderOf(xf.borders.bottom, xf.borders.bottomColor, palette);
|
|
83576
|
+
if (left) style.borderLeft = left;
|
|
83577
|
+
if (right) style.borderRight = right;
|
|
83578
|
+
if (top) style.borderTop = top;
|
|
83579
|
+
if (bottom) style.borderBottom = bottom;
|
|
83580
|
+
if (xf.fillPattern === 1) {
|
|
83581
|
+
const bg = colorOf(xf.fillFore, palette);
|
|
83582
|
+
if (bg) style.backgroundColor = bg;
|
|
83583
|
+
} else if (xf.fillPattern > 1) {
|
|
83584
|
+
const bg = colorOf(xf.fillBack, palette);
|
|
83585
|
+
if (bg) style.backgroundColor = bg;
|
|
83586
|
+
style.patternType = "gray125";
|
|
83587
|
+
}
|
|
83588
|
+
return style;
|
|
83589
|
+
}
|
|
83590
|
+
|
|
84526
83591
|
// ../xlsx/src/biff8_reader.ts
|
|
84527
83592
|
var DEFAULT_MAX_ROWS = 1e4;
|
|
84528
83593
|
var REC = {
|
|
@@ -84544,7 +83609,12 @@ var REC = {
|
|
|
84544
83609
|
MULBLANK: 190,
|
|
84545
83610
|
LABELSST: 253,
|
|
84546
83611
|
SST: 252,
|
|
84547
|
-
BOF: 2057
|
|
83612
|
+
BOF: 2057,
|
|
83613
|
+
DEFCOLWIDTH: 85,
|
|
83614
|
+
COLINFO: 125,
|
|
83615
|
+
FONT: 49,
|
|
83616
|
+
PALETTE: 146,
|
|
83617
|
+
ROW: 520
|
|
84548
83618
|
};
|
|
84549
83619
|
function* iterRecords(stream, from, to) {
|
|
84550
83620
|
const dv = new DataView(stream.buffer, stream.byteOffset, stream.byteLength);
|
|
@@ -84562,6 +83632,9 @@ function parseGlobals(stream) {
|
|
|
84562
83632
|
const sstChunks = [];
|
|
84563
83633
|
const formats = /* @__PURE__ */ new Map();
|
|
84564
83634
|
const xfFormatIds = [];
|
|
83635
|
+
const xfRecords = [];
|
|
83636
|
+
const fonts = [];
|
|
83637
|
+
let palette = null;
|
|
84565
83638
|
const boundsheets = [];
|
|
84566
83639
|
let date1904 = false;
|
|
84567
83640
|
let sawSst = false;
|
|
@@ -84605,8 +83678,17 @@ function parseGlobals(stream) {
|
|
|
84605
83678
|
}
|
|
84606
83679
|
case REC.XF: {
|
|
84607
83680
|
xfFormatIds.push(readU16(r.body, 2));
|
|
83681
|
+
xfRecords.push(r.body.slice());
|
|
83682
|
+
break;
|
|
83683
|
+
}
|
|
83684
|
+
case REC.FONT: {
|
|
83685
|
+
fonts.push(parseFont2(r.body));
|
|
83686
|
+
if (fonts.length === 4) fonts.push(fonts[3]);
|
|
84608
83687
|
break;
|
|
84609
83688
|
}
|
|
83689
|
+
case REC.PALETTE:
|
|
83690
|
+
palette = parsePalette(r.body);
|
|
83691
|
+
break;
|
|
84610
83692
|
case REC.BOUNDSHEET: {
|
|
84611
83693
|
const pos = dv.getUint32(r.offset + 4, true);
|
|
84612
83694
|
boundsheets.push({ name: readUnicodeShort(r.body, 6, 1), pos });
|
|
@@ -84618,7 +83700,9 @@ function parseGlobals(stream) {
|
|
|
84618
83700
|
}
|
|
84619
83701
|
const sst = parseSst(sstChunks, sstUnique);
|
|
84620
83702
|
const xfFormats = xfFormatIds.map((id) => formats.get(id) ?? builtinFormat(id));
|
|
84621
|
-
|
|
83703
|
+
const pal = palette ?? defaultPalette();
|
|
83704
|
+
const xfStyles = xfRecords.map((body) => toCellStyle(parseXf2(body), fonts, pal));
|
|
83705
|
+
return { sst, date1904, xfFormats, xfStyles, boundsheets };
|
|
84622
83706
|
}
|
|
84623
83707
|
function parseSst(chunks, count) {
|
|
84624
83708
|
const out = [];
|
|
@@ -84703,26 +83787,55 @@ function parseSheet2(stream, start, name2, g, maxRows) {
|
|
|
84703
83787
|
break;
|
|
84704
83788
|
}
|
|
84705
83789
|
}
|
|
83790
|
+
const colDefs = /* @__PURE__ */ new Map();
|
|
83791
|
+
const rowHeights = /* @__PURE__ */ new Map();
|
|
83792
|
+
const hiddenRows = /* @__PURE__ */ new Set();
|
|
84706
83793
|
for (const r of iterRecords(stream, start, end)) {
|
|
84707
83794
|
switch (r.type) {
|
|
83795
|
+
case REC.DEFCOLWIDTH: {
|
|
83796
|
+
sheet.defaultColWidth = readU16(r.body, 0);
|
|
83797
|
+
break;
|
|
83798
|
+
}
|
|
83799
|
+
case REC.COLINFO: {
|
|
83800
|
+
const first3 = readU16(r.body, 0), last3 = readU16(r.body, 2);
|
|
83801
|
+
const width = readU16(r.body, 4) / 256;
|
|
83802
|
+
const grbit = readU16(r.body, 8);
|
|
83803
|
+
const hidden = (grbit & 1) !== 0;
|
|
83804
|
+
const outline = grbit >> 8 & 7;
|
|
83805
|
+
for (let c = first3; c <= last3 && c <= 255; c++) {
|
|
83806
|
+
colDefs.set(c, { index: c + 1, width, hidden, customWidth: true });
|
|
83807
|
+
if (outline > 0) sheet.colOutlineLevels.set(c + 1, outline);
|
|
83808
|
+
}
|
|
83809
|
+
break;
|
|
83810
|
+
}
|
|
83811
|
+
case REC.ROW: {
|
|
83812
|
+
const row = readU16(r.body, 0);
|
|
83813
|
+
const grbit = readU16(r.body, 12);
|
|
83814
|
+
const height = (readU16(r.body, 6) & 32767) / 20;
|
|
83815
|
+
if (height > 0) rowHeights.set(row, height);
|
|
83816
|
+
if ((grbit & 32) !== 0) hiddenRows.add(row);
|
|
83817
|
+
const outline = grbit & 7;
|
|
83818
|
+
if (outline > 0) sheet.rowOutlineLevels.set(row + 1, outline);
|
|
83819
|
+
break;
|
|
83820
|
+
}
|
|
84708
83821
|
case REC.LABELSST: {
|
|
84709
|
-
const row = readU16(r.body, 0), col = readU16(r.body, 2), isst = readU32(r.body, 6);
|
|
84710
|
-
put(row, col, textCell(col, g.sst[isst] ?? ""));
|
|
83822
|
+
const row = readU16(r.body, 0), col = readU16(r.body, 2), xf = readU16(r.body, 4), isst = readU32(r.body, 6);
|
|
83823
|
+
put(row, col, textCell(col, g.sst[isst] ?? "", g.xfStyles[xf]));
|
|
84711
83824
|
break;
|
|
84712
83825
|
}
|
|
84713
83826
|
case REC.LABEL: {
|
|
84714
|
-
const row = readU16(r.body, 0), col = readU16(r.body, 2);
|
|
84715
|
-
put(row, col, textCell(col, readUnicodeShort(r.body, 6, 2)));
|
|
83827
|
+
const row = readU16(r.body, 0), col = readU16(r.body, 2), xf = readU16(r.body, 4);
|
|
83828
|
+
put(row, col, textCell(col, readUnicodeShort(r.body, 6, 2), g.xfStyles[xf]));
|
|
84716
83829
|
break;
|
|
84717
83830
|
}
|
|
84718
83831
|
case REC.NUMBER: {
|
|
84719
83832
|
const row = readU16(r.body, 0), col = readU16(r.body, 2), xf = readU16(r.body, 4);
|
|
84720
|
-
put(row, col, numberCell(col, readF64(r.body, 6), g.xfFormats[xf]));
|
|
83833
|
+
put(row, col, numberCell(col, readF64(r.body, 6), g.xfFormats[xf], g.xfStyles[xf]));
|
|
84721
83834
|
break;
|
|
84722
83835
|
}
|
|
84723
83836
|
case REC.RK: {
|
|
84724
83837
|
const row = readU16(r.body, 0), col = readU16(r.body, 2), xf = readU16(r.body, 4);
|
|
84725
|
-
put(row, col, numberCell(col, decodeRk(readU32(r.body, 6)), g.xfFormats[xf]));
|
|
83838
|
+
put(row, col, numberCell(col, decodeRk(readU32(r.body, 6)), g.xfFormats[xf], g.xfStyles[xf]));
|
|
84726
83839
|
break;
|
|
84727
83840
|
}
|
|
84728
83841
|
case REC.MULRK: {
|
|
@@ -84731,13 +83844,13 @@ function parseSheet2(stream, start, name2, g, maxRows) {
|
|
|
84731
83844
|
for (let i2 = 0; i2 < n; i2++) {
|
|
84732
83845
|
const xf = readU16(r.body, 4 + i2 * 6);
|
|
84733
83846
|
const rk = readU32(r.body, 6 + i2 * 6);
|
|
84734
|
-
put(row, first3 + i2, numberCell(first3 + i2, decodeRk(rk), g.xfFormats[xf]));
|
|
83847
|
+
put(row, first3 + i2, numberCell(first3 + i2, decodeRk(rk), g.xfFormats[xf], g.xfStyles[xf]));
|
|
84735
83848
|
}
|
|
84736
83849
|
break;
|
|
84737
83850
|
}
|
|
84738
83851
|
case REC.FORMULA: {
|
|
84739
83852
|
const row = readU16(r.body, 0), col = readU16(r.body, 2), xf = readU16(r.body, 4);
|
|
84740
|
-
const cell = formulaCell(col, r.body, g.xfFormats[xf]);
|
|
83853
|
+
const cell = formulaCell(col, r.body, g.xfFormats[xf], g.xfStyles[xf]);
|
|
84741
83854
|
if (cell) put(row, col, cell);
|
|
84742
83855
|
break;
|
|
84743
83856
|
}
|
|
@@ -84751,17 +83864,23 @@ function parseSheet2(stream, start, name2, g, maxRows) {
|
|
|
84751
83864
|
const r = grid.get(ri);
|
|
84752
83865
|
if (!r) continue;
|
|
84753
83866
|
const cells = [...r.values()].sort((a, b) => a.column - b.column);
|
|
84754
|
-
rows.push({
|
|
83867
|
+
rows.push({
|
|
83868
|
+
index: ri + 1,
|
|
83869
|
+
height: rowHeights.get(ri) ?? sheet.defaultRowHeight,
|
|
83870
|
+
cells,
|
|
83871
|
+
hidden: hiddenRows.has(ri)
|
|
83872
|
+
});
|
|
84755
83873
|
}
|
|
84756
83874
|
sheet.rows = rows;
|
|
83875
|
+
sheet.columns = [...colDefs.values()].sort((a, b) => a.index - b.index);
|
|
84757
83876
|
sheet.totalRowCount = maxRow + 1;
|
|
84758
83877
|
sheet.truncated = truncated;
|
|
84759
83878
|
return sheet;
|
|
84760
83879
|
}
|
|
84761
|
-
function textCell(column, text) {
|
|
84762
|
-
return { column: column + 1, value: text, typedValue: text, content: { type: "plain", text }, style
|
|
83880
|
+
function textCell(column, text, style = {}) {
|
|
83881
|
+
return { column: column + 1, value: text, typedValue: text, content: { type: "plain", text }, style };
|
|
84763
83882
|
}
|
|
84764
|
-
function numberCell(column, num3, numFmt) {
|
|
83883
|
+
function numberCell(column, num3, numFmt, style = {}) {
|
|
84765
83884
|
const value2 = Number.isFinite(num3) ? String(num3) : "";
|
|
84766
83885
|
return {
|
|
84767
83886
|
column: column + 1,
|
|
@@ -84770,19 +83889,19 @@ function numberCell(column, num3, numFmt) {
|
|
|
84770
83889
|
typedValue: num3,
|
|
84771
83890
|
numFmtCode: numFmt && numFmt !== "General" ? numFmt : void 0,
|
|
84772
83891
|
content: { type: "plain", text: value2 },
|
|
84773
|
-
style
|
|
83892
|
+
style
|
|
84774
83893
|
};
|
|
84775
83894
|
}
|
|
84776
|
-
function formulaCell(column, body, numFmt) {
|
|
83895
|
+
function formulaCell(column, body, numFmt, style = {}) {
|
|
84777
83896
|
if (readU16(body, 12) === 65535) {
|
|
84778
83897
|
const kind = body[6];
|
|
84779
83898
|
if (kind === 1) {
|
|
84780
83899
|
const b = body[8] !== 0;
|
|
84781
|
-
return { column: column + 1, value: b ? "TRUE" : "FALSE", typedValue: b, content: { type: "plain", text: b ? "TRUE" : "FALSE" }, style
|
|
83900
|
+
return { column: column + 1, value: b ? "TRUE" : "FALSE", typedValue: b, content: { type: "plain", text: b ? "TRUE" : "FALSE" }, style };
|
|
84782
83901
|
}
|
|
84783
83902
|
return null;
|
|
84784
83903
|
}
|
|
84785
|
-
return numberCell(column, readF64(body, 6), numFmt);
|
|
83904
|
+
return numberCell(column, readF64(body, 6), numFmt, style);
|
|
84786
83905
|
}
|
|
84787
83906
|
function decodeRk(rk) {
|
|
84788
83907
|
const div100 = (rk & 1) !== 0;
|
|
@@ -85039,9 +84158,9 @@ function parseExcelFromZip(zip, options) {
|
|
|
85039
84158
|
}
|
|
85040
84159
|
return result;
|
|
85041
84160
|
}
|
|
85042
|
-
function findEntry(zip,
|
|
85043
|
-
if (zip[
|
|
85044
|
-
const lower2 =
|
|
84161
|
+
function findEntry(zip, path14) {
|
|
84162
|
+
if (zip[path14]) return zip[path14];
|
|
84163
|
+
const lower2 = path14.toLowerCase();
|
|
85045
84164
|
for (const key of Object.keys(zip)) {
|
|
85046
84165
|
if (key.toLowerCase() === lower2) return zip[key];
|
|
85047
84166
|
}
|
|
@@ -85678,12 +84797,12 @@ function extractPivotRoundTripInfo(originalZip) {
|
|
|
85678
84797
|
if (paths.length > 0) pivotTablesBySheetIndex.set(i2, paths);
|
|
85679
84798
|
}
|
|
85680
84799
|
const pivotXmlPaths = [];
|
|
85681
|
-
for (const
|
|
85682
|
-
if (
|
|
85683
|
-
pivotXmlPaths.push(
|
|
84800
|
+
for (const path14 of Object.keys(originalZip)) {
|
|
84801
|
+
if (path14.startsWith("xl/pivotTables/") && path14.endsWith(".xml")) {
|
|
84802
|
+
pivotXmlPaths.push(path14);
|
|
85684
84803
|
}
|
|
85685
|
-
if (
|
|
85686
|
-
pivotXmlPaths.push(
|
|
84804
|
+
if (path14.startsWith("xl/pivotCache/") && path14.endsWith(".xml")) {
|
|
84805
|
+
pivotXmlPaths.push(path14);
|
|
85687
84806
|
}
|
|
85688
84807
|
}
|
|
85689
84808
|
return { cachesByWorkbook, pivotTablesBySheetIndex, pivotXmlPaths };
|
|
@@ -85691,15 +84810,15 @@ function extractPivotRoundTripInfo(originalZip) {
|
|
|
85691
84810
|
function decode3(bytes) {
|
|
85692
84811
|
return new TextDecoder().decode(bytes);
|
|
85693
84812
|
}
|
|
85694
|
-
function pivotContentTypeFor(
|
|
85695
|
-
if (
|
|
85696
|
-
return `<Override PartName="/${
|
|
84813
|
+
function pivotContentTypeFor(path14) {
|
|
84814
|
+
if (path14.startsWith("xl/pivotTables/") && path14.endsWith(".xml")) {
|
|
84815
|
+
return `<Override PartName="/${path14}" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.pivotTable+xml"/>`;
|
|
85697
84816
|
}
|
|
85698
|
-
if (
|
|
85699
|
-
return `<Override PartName="/${
|
|
84817
|
+
if (path14.includes("/pivotCacheDefinition") && path14.endsWith(".xml")) {
|
|
84818
|
+
return `<Override PartName="/${path14}" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.pivotCacheDefinition+xml"/>`;
|
|
85700
84819
|
}
|
|
85701
|
-
if (
|
|
85702
|
-
return `<Override PartName="/${
|
|
84820
|
+
if (path14.includes("/pivotCacheRecords") && path14.endsWith(".xml")) {
|
|
84821
|
+
return `<Override PartName="/${path14}" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.pivotCacheRecords+xml"/>`;
|
|
85703
84822
|
}
|
|
85704
84823
|
return void 0;
|
|
85705
84824
|
}
|
|
@@ -85772,16 +84891,16 @@ function exportWorkbook(workbook, originalZip) {
|
|
|
85772
84891
|
regeneratedPaths.add(`xl/worksheets/sheet${i2 + 1}.xml`);
|
|
85773
84892
|
regeneratedPaths.add(`xl/worksheets/_rels/sheet${i2 + 1}.xml.rels`);
|
|
85774
84893
|
}
|
|
85775
|
-
for (const
|
|
85776
|
-
if (
|
|
85777
|
-
regeneratedPaths.add(
|
|
84894
|
+
for (const path14 of Object.keys(originalZip)) {
|
|
84895
|
+
if (path14.startsWith("xl/drawings/") || path14.startsWith("xl/charts/") || path14.startsWith("xl/tables/") || path14.startsWith("xl/media/")) {
|
|
84896
|
+
regeneratedPaths.add(path14);
|
|
85778
84897
|
}
|
|
85779
84898
|
}
|
|
85780
|
-
for (const [
|
|
85781
|
-
if (regeneratedPaths.has(
|
|
85782
|
-
const ext =
|
|
84899
|
+
for (const [path14, data2] of Object.entries(originalZip)) {
|
|
84900
|
+
if (regeneratedPaths.has(path14)) continue;
|
|
84901
|
+
const ext = path14.slice(path14.lastIndexOf(".") + 1).toLowerCase();
|
|
85783
84902
|
if (!DECLARED_EXTENSIONS.includes(ext)) continue;
|
|
85784
|
-
entries2[
|
|
84903
|
+
entries2[path14] = data2;
|
|
85785
84904
|
}
|
|
85786
84905
|
}
|
|
85787
84906
|
const sharedStrings = buildSharedStrings(workbook);
|
|
@@ -85797,8 +84916,8 @@ function exportWorkbook(workbook, originalZip) {
|
|
|
85797
84916
|
buildWorkbookRels(workbook, pivotInfo)
|
|
85798
84917
|
);
|
|
85799
84918
|
const extraContentTypes = [];
|
|
85800
|
-
for (const
|
|
85801
|
-
const ct = pivotContentTypeFor(
|
|
84919
|
+
for (const path14 of pivotInfo.pivotXmlPaths) {
|
|
84920
|
+
const ct = pivotContentTypeFor(path14);
|
|
85802
84921
|
if (ct) extraContentTypes.push(ct);
|
|
85803
84922
|
}
|
|
85804
84923
|
let globalChartIndex = 1;
|
|
@@ -94984,14 +94103,14 @@ var DependencyGraph = class {
|
|
|
94984
94103
|
stack.push({ cell: p, path: [cell, p] });
|
|
94985
94104
|
}
|
|
94986
94105
|
while (stack.length > 0) {
|
|
94987
|
-
const { cell: current, path:
|
|
94988
|
-
if (current === cell || originCoarse.has(current)) return
|
|
94106
|
+
const { cell: current, path: path14 } = stack.pop();
|
|
94107
|
+
if (current === cell || originCoarse.has(current)) return path14;
|
|
94989
94108
|
if (visited.has(current)) continue;
|
|
94990
94109
|
visited.add(current);
|
|
94991
94110
|
const nextPrec = this.precedents.get(current);
|
|
94992
94111
|
if (!nextPrec) continue;
|
|
94993
94112
|
for (const p of nextPrec) {
|
|
94994
|
-
stack.push({ cell: p, path: [...
|
|
94113
|
+
stack.push({ cell: p, path: [...path14, p] });
|
|
94995
94114
|
}
|
|
94996
94115
|
}
|
|
94997
94116
|
return null;
|
|
@@ -96437,8 +95556,8 @@ var SIMPLE_SHEET_KEYS = /* @__PURE__ */ new Set(["name", "cells", "merges", "fre
|
|
|
96437
95556
|
var MAX_COLUMN = 16384;
|
|
96438
95557
|
var MAX_ROW = 1048576;
|
|
96439
95558
|
function loadFile(filePath) {
|
|
96440
|
-
if (!
|
|
96441
|
-
const buffer =
|
|
95559
|
+
if (!fs11.existsSync(filePath)) fail2(`File not found: ${filePath}`);
|
|
95560
|
+
const buffer = fs11.readFileSync(filePath);
|
|
96442
95561
|
const arrayBuffer = buffer.buffer.slice(buffer.byteOffset, buffer.byteOffset + buffer.byteLength);
|
|
96443
95562
|
const originalZip = unzipXlsx(arrayBuffer);
|
|
96444
95563
|
const parsed = parseExcelBuffer(arrayBuffer);
|
|
@@ -96488,7 +95607,7 @@ function lazyEngine(workbook) {
|
|
|
96488
95607
|
};
|
|
96489
95608
|
}
|
|
96490
95609
|
function readToJson(filePath, filter3, opts) {
|
|
96491
|
-
const buffer =
|
|
95610
|
+
const buffer = fs11.readFileSync(filePath);
|
|
96492
95611
|
const arrayBuffer = buffer.buffer.slice(buffer.byteOffset, buffer.byteOffset + buffer.byteLength);
|
|
96493
95612
|
const parsed = parseExcelBuffer(arrayBuffer);
|
|
96494
95613
|
let sheets = parsed.sheets;
|
|
@@ -97001,7 +96120,7 @@ async function runXlsxCommand(subcommand, toolArgs, restArgs) {
|
|
|
97001
96120
|
}
|
|
97002
96121
|
|
|
97003
96122
|
// src/docx.ts
|
|
97004
|
-
import
|
|
96123
|
+
import fs12 from "node:fs";
|
|
97005
96124
|
|
|
97006
96125
|
// ../ooxml/src/doc/errors.ts
|
|
97007
96126
|
var DocParseError = class extends Error {
|
|
@@ -101830,8 +100949,8 @@ async function docModelToDocx(model) {
|
|
|
101830
100949
|
// ../ooxml/src/opc.ts
|
|
101831
100950
|
var import_jszip = __toESM(require_lib4(), 1);
|
|
101832
100951
|
function dropFolderEntries(zip) {
|
|
101833
|
-
for (const [
|
|
101834
|
-
if (entry.dir) delete zip.files[
|
|
100952
|
+
for (const [path14, entry] of Object.entries(zip.files)) {
|
|
100953
|
+
if (entry.dir) delete zip.files[path14];
|
|
101835
100954
|
}
|
|
101836
100955
|
}
|
|
101837
100956
|
|
|
@@ -102086,11 +101205,11 @@ async function parseDocx(buffer) {
|
|
|
102086
101205
|
const zip = await import_jszip3.default.loadAsync(buffer);
|
|
102087
101206
|
const parts = /* @__PURE__ */ new Map();
|
|
102088
101207
|
const filePromises = [];
|
|
102089
|
-
zip.forEach((
|
|
101208
|
+
zip.forEach((path14, file2) => {
|
|
102090
101209
|
if (file2.dir) return;
|
|
102091
101210
|
filePromises.push(
|
|
102092
101211
|
file2.async("uint8array").then((bytes) => {
|
|
102093
|
-
parts.set(
|
|
101212
|
+
parts.set(path14, bytes);
|
|
102094
101213
|
})
|
|
102095
101214
|
);
|
|
102096
101215
|
});
|
|
@@ -102322,9 +101441,9 @@ var DEFAULT_PARTS = [
|
|
|
102322
101441
|
["word/theme/theme1.xml", () => encoder.encode(THEME_XML)]
|
|
102323
101442
|
];
|
|
102324
101443
|
function fillDefaultParts(parts) {
|
|
102325
|
-
for (const [
|
|
102326
|
-
if (!parts.has(
|
|
102327
|
-
parts.set(
|
|
101444
|
+
for (const [path14, makeBytes] of DEFAULT_PARTS) {
|
|
101445
|
+
if (!parts.has(path14)) {
|
|
101446
|
+
parts.set(path14, makeBytes());
|
|
102328
101447
|
}
|
|
102329
101448
|
}
|
|
102330
101449
|
return parts;
|
|
@@ -102334,9 +101453,9 @@ function fillDefaultParts(parts) {
|
|
|
102334
101453
|
async function serializeDocx(doc) {
|
|
102335
101454
|
const zip = new import_jszip4.default();
|
|
102336
101455
|
const parts = fillDefaultParts(new Map(doc.parts));
|
|
102337
|
-
for (const [
|
|
102338
|
-
if (
|
|
102339
|
-
zip.file(
|
|
101456
|
+
for (const [path14, bytes] of parts) {
|
|
101457
|
+
if (path14 === "word/document.xml") continue;
|
|
101458
|
+
zip.file(path14, bytes);
|
|
102340
101459
|
}
|
|
102341
101460
|
const documentXml = serializeDocumentXml(doc);
|
|
102342
101461
|
zip.file("word/document.xml", documentXml);
|
|
@@ -102423,8 +101542,8 @@ var DEFAULT_DOC_ATTRS = {
|
|
|
102423
101542
|
"@_xmlns:w": "http://schemas.openxmlformats.org/wordprocessingml/2006/main"
|
|
102424
101543
|
};
|
|
102425
101544
|
async function loadFile2(filePath) {
|
|
102426
|
-
if (!
|
|
102427
|
-
const bytes =
|
|
101545
|
+
if (!fs12.existsSync(filePath)) fail2(`File not found: ${filePath}`);
|
|
101546
|
+
const bytes = fs12.readFileSync(filePath);
|
|
102428
101547
|
if (isLegacyDoc(bytes)) {
|
|
102429
101548
|
const upgraded = await saveDocxToBuffer(await loadDocxFromBuffer(bytes));
|
|
102430
101549
|
return parseDocx(new Uint8Array(upgraded));
|
|
@@ -102909,7 +102028,7 @@ async function runDocxCommand(subcommand, toolArgs, restArgs) {
|
|
|
102909
102028
|
}
|
|
102910
102029
|
|
|
102911
102030
|
// src/knowledge.ts
|
|
102912
|
-
import
|
|
102031
|
+
import fs13 from "node:fs";
|
|
102913
102032
|
|
|
102914
102033
|
// ../shared/src/knowledge_tags.ts
|
|
102915
102034
|
function isHiddenDoc(doc) {
|
|
@@ -102918,8 +102037,8 @@ function isHiddenDoc(doc) {
|
|
|
102918
102037
|
|
|
102919
102038
|
// src/knowledge.ts
|
|
102920
102039
|
function readBodyFile(filePath) {
|
|
102921
|
-
if (!
|
|
102922
|
-
return
|
|
102040
|
+
if (!fs13.existsSync(filePath)) fail2(`File not found: ${filePath}`);
|
|
102041
|
+
return fs13.readFileSync(filePath, "utf-8");
|
|
102923
102042
|
}
|
|
102924
102043
|
function resolveBody(flags, required2) {
|
|
102925
102044
|
if (flags.from !== void 0 && flags.content !== void 0) {
|
|
@@ -103128,7 +102247,7 @@ async function runKnowledgeCommand(client, subcommand, toolArgs, flags, restArgs
|
|
|
103128
102247
|
import { spawn as spawn3 } from "node:child_process";
|
|
103129
102248
|
import { createServer } from "node:http";
|
|
103130
102249
|
import { readFileSync as readFileSync2, writeFileSync, existsSync as existsSync2, mkdtempSync, rmSync, readdirSync } from "node:fs";
|
|
103131
|
-
import { tmpdir as
|
|
102250
|
+
import { tmpdir as tmpdir3 } from "node:os";
|
|
103132
102251
|
import { join as join2, dirname, resolve, extname, basename } from "node:path";
|
|
103133
102252
|
import { fileURLToPath as fileURLToPath3 } from "node:url";
|
|
103134
102253
|
import { setTimeout as sleep } from "node:timers/promises";
|
|
@@ -103227,7 +102346,7 @@ async function runPreviewCommand(filePath, flags) {
|
|
|
103227
102346
|
});
|
|
103228
102347
|
await new Promise((r) => server.listen(0, "127.0.0.1", () => r()));
|
|
103229
102348
|
const httpPort = server.address().port;
|
|
103230
|
-
const udd = mkdtempSync(join2(
|
|
102349
|
+
const udd = mkdtempSync(join2(tmpdir3(), "lotics-render-"));
|
|
103231
102350
|
const child = spawn3(chrome, [
|
|
103232
102351
|
"--headless=new",
|
|
103233
102352
|
"--disable-gpu",
|
|
@@ -103467,8 +102586,8 @@ function prompt(question) {
|
|
|
103467
102586
|
});
|
|
103468
102587
|
});
|
|
103469
102588
|
}
|
|
103470
|
-
async function publicPost(
|
|
103471
|
-
const response = await fetch(`${API_BASE_URL}${
|
|
102589
|
+
async function publicPost(path14, body) {
|
|
102590
|
+
const response = await fetch(`${API_BASE_URL}${path14}`, {
|
|
103472
102591
|
method: "POST",
|
|
103473
102592
|
headers: { "Content-Type": "application/json" },
|
|
103474
102593
|
body: JSON.stringify(body)
|
|
@@ -103636,13 +102755,13 @@ async function resolveWorkspace(client, ctx) {
|
|
|
103636
102755
|
function resolveUploadPaths(rawPaths) {
|
|
103637
102756
|
const result = [];
|
|
103638
102757
|
for (const p of rawPaths) {
|
|
103639
|
-
const resolved =
|
|
103640
|
-
const stat =
|
|
102758
|
+
const resolved = path13.resolve(p);
|
|
102759
|
+
const stat = fs14.statSync(resolved);
|
|
103641
102760
|
if (stat.isDirectory()) {
|
|
103642
|
-
const entries2 =
|
|
102761
|
+
const entries2 = fs14.readdirSync(resolved, { withFileTypes: true });
|
|
103643
102762
|
for (const entry of entries2) {
|
|
103644
102763
|
if (entry.isFile()) {
|
|
103645
|
-
result.push(
|
|
102764
|
+
result.push(path13.join(resolved, entry.name));
|
|
103646
102765
|
}
|
|
103647
102766
|
}
|
|
103648
102767
|
} else {
|
|
@@ -103691,23 +102810,69 @@ async function main() {
|
|
|
103691
102810
|
console.log(VERSION);
|
|
103692
102811
|
return;
|
|
103693
102812
|
}
|
|
103694
|
-
if (command === "
|
|
103695
|
-
if (
|
|
103696
|
-
|
|
103697
|
-
|
|
103698
|
-
|
|
102813
|
+
if (command === "starter") {
|
|
102814
|
+
if (subcommand === "list") {
|
|
102815
|
+
const { client: client2, ctx: ctx2 } = requireClient(flags);
|
|
102816
|
+
await resolveWorkspace(client2, ctx2);
|
|
102817
|
+
await starterList(client2);
|
|
102818
|
+
return;
|
|
103699
102819
|
}
|
|
103700
|
-
|
|
103701
|
-
|
|
103702
|
-
|
|
103703
|
-
|
|
103704
|
-
|
|
103705
|
-
|
|
103706
|
-
|
|
103707
|
-
|
|
103708
|
-
|
|
103709
|
-
|
|
103710
|
-
|
|
102820
|
+
if (subcommand === "show") {
|
|
102821
|
+
if (!toolArgs) {
|
|
102822
|
+
console.error("Usage: lotics starter show <starter_id>");
|
|
102823
|
+
process.exit(1);
|
|
102824
|
+
}
|
|
102825
|
+
const { client: client2, ctx: ctx2 } = requireClient(flags);
|
|
102826
|
+
await resolveWorkspace(client2, ctx2);
|
|
102827
|
+
await starterShow(client2, toolArgs);
|
|
102828
|
+
return;
|
|
102829
|
+
}
|
|
102830
|
+
if (subcommand === "init") {
|
|
102831
|
+
if (!toolArgs) {
|
|
102832
|
+
console.error("Usage: lotics starter init <starter_id> [path] [--no-sample-data] [--adopt]");
|
|
102833
|
+
console.error(" Copies a starter into this workspace: schema, templates, knowledge");
|
|
102834
|
+
console.error(" docs, sample records and an editable app project. Builds and deploys");
|
|
102835
|
+
console.error(" locally, so it needs node and a few minutes.");
|
|
102836
|
+
process.exit(1);
|
|
102837
|
+
}
|
|
102838
|
+
const { client: client2, ctx: ctx2 } = requireClient(flags);
|
|
102839
|
+
await resolveWorkspace(client2, ctx2);
|
|
102840
|
+
await starterInit(client2, {
|
|
102841
|
+
starter_id: toolArgs,
|
|
102842
|
+
...restArgs[0] !== void 0 ? { targetPath: restArgs[0] } : {},
|
|
102843
|
+
...flags.noSampleData === true ? { noSampleData: true } : {},
|
|
102844
|
+
...flags.adopt === true ? { adopt: true } : {}
|
|
102845
|
+
});
|
|
102846
|
+
return;
|
|
102847
|
+
}
|
|
102848
|
+
if (subcommand === "fixtures") {
|
|
102849
|
+
if (toolArgs !== "capture") {
|
|
102850
|
+
console.error("Usage: lotics starter fixtures capture [--entity <alias> ...] [--limit <n>]");
|
|
102851
|
+
console.error(" Writes fixtures/<entity>.json into this app project from live records.");
|
|
102852
|
+
console.error(" Repeat --entity to capture a linked set in one call: a link only");
|
|
102853
|
+
console.error(" resolves within ONE capture, so separate calls lose the edge.");
|
|
102854
|
+
process.exit(1);
|
|
102855
|
+
}
|
|
102856
|
+
let limit;
|
|
102857
|
+
if (flags.limit !== void 0) {
|
|
102858
|
+
limit = Number(flags.limit);
|
|
102859
|
+
if (!Number.isInteger(limit) || limit < 1) {
|
|
102860
|
+
console.error(`Invalid --limit "${flags.limit}" \u2014 expected a positive integer.`);
|
|
102861
|
+
process.exit(1);
|
|
102862
|
+
}
|
|
102863
|
+
}
|
|
102864
|
+
const { client: client2, ctx: ctx2 } = requireClient(flags);
|
|
102865
|
+
await resolveWorkspace(client2, ctx2);
|
|
102866
|
+
await starterFixturesCapture(client2, {
|
|
102867
|
+
entities: flags.entity,
|
|
102868
|
+
...limit !== void 0 ? { limit } : {}
|
|
102869
|
+
});
|
|
102870
|
+
return;
|
|
102871
|
+
}
|
|
102872
|
+
console.error(
|
|
102873
|
+
"Usage: lotics starter list | show <starter_id> | init <starter_id> [path] | fixtures capture"
|
|
102874
|
+
);
|
|
102875
|
+
process.exit(1);
|
|
103711
102876
|
}
|
|
103712
102877
|
if (command === "docs") {
|
|
103713
102878
|
docsCommand({ area: subcommand });
|
|
@@ -103717,11 +102882,11 @@ async function main() {
|
|
|
103717
102882
|
let input = subcommand ?? "";
|
|
103718
102883
|
if (input.startsWith("@")) {
|
|
103719
102884
|
const file2 = input.slice(1);
|
|
103720
|
-
if (!
|
|
102885
|
+
if (!fs14.existsSync(file2)) {
|
|
103721
102886
|
console.error(`No such file: ${file2}`);
|
|
103722
102887
|
process.exit(1);
|
|
103723
102888
|
}
|
|
103724
|
-
input =
|
|
102889
|
+
input = fs14.readFileSync(file2, "utf-8");
|
|
103725
102890
|
} else if (input === "-") {
|
|
103726
102891
|
input = await readStdin();
|
|
103727
102892
|
}
|
|
@@ -103848,13 +103013,13 @@ async function main() {
|
|
|
103848
103013
|
if (command === "preview") {
|
|
103849
103014
|
if (subcommand && isStoredFileId(subcommand)) {
|
|
103850
103015
|
const { client: client2 } = requireClient(flags);
|
|
103851
|
-
const tmpDir =
|
|
103016
|
+
const tmpDir = fs14.mkdtempSync(path13.join(os4.tmpdir(), "lotics-preview-"));
|
|
103852
103017
|
try {
|
|
103853
103018
|
const { path: localPath, filename } = await client2.downloadFileById(subcommand, tmpDir);
|
|
103854
103019
|
const output = flags.output ?? defaultPreviewOutputPath(filename, process.cwd());
|
|
103855
103020
|
await runPreviewCommand(localPath, { output });
|
|
103856
103021
|
} finally {
|
|
103857
|
-
|
|
103022
|
+
fs14.rmSync(tmpDir, { recursive: true, force: true });
|
|
103858
103023
|
}
|
|
103859
103024
|
return;
|
|
103860
103025
|
}
|
|
@@ -104402,7 +103567,7 @@ ${JSON.stringify(info.input_schema, null, 2)}`);
|
|
|
104402
103567
|
const ingested = await ingestJsonArgs({
|
|
104403
103568
|
rawArg: toolArgs,
|
|
104404
103569
|
stdinIsTTY: process.stdin.isTTY ?? false,
|
|
104405
|
-
readFile: (p) =>
|
|
103570
|
+
readFile: (p) => fs14.readFileSync(p, "utf-8"),
|
|
104406
103571
|
readStdin
|
|
104407
103572
|
});
|
|
104408
103573
|
if (ingested.kind === "error") {
|