@pipelex/sdk 0.46.1 → 0.48.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/README.md +20 -9
- package/dist/cli/script.d.ts +1 -1
- package/dist/cli/source.d.ts +8 -7
- package/dist/cli/source.js +11 -5
- package/dist/cli/source.js.map +1 -1
- package/dist/client.d.ts +455 -237
- package/dist/client.js +1067 -522
- package/dist/client.js.map +1 -1
- package/dist/errors.d.ts +49 -19
- package/dist/errors.js +50 -21
- package/dist/errors.js.map +1 -1
- package/dist/hooks/bundle-gather.d.ts +28 -40
- package/dist/hooks/bundle-gather.js +55 -230
- package/dist/hooks/bundle-gather.js.map +1 -1
- package/dist/hooks/claude-mthds-check.d.ts +7 -5
- package/dist/hooks/claude-mthds-check.js +8 -53
- package/dist/hooks/claude-mthds-check.js.map +1 -1
- package/dist/hooks/validate-stage.d.ts +27 -0
- package/dist/hooks/validate-stage.js +57 -0
- package/dist/hooks/validate-stage.js.map +1 -0
- package/dist/index.d.ts +7 -7
- package/dist/index.js +6 -3
- package/dist/index.js.map +1 -1
- package/dist/method-trees.d.ts +344 -0
- package/dist/method-trees.js +876 -0
- package/dist/method-trees.js.map +1 -0
- package/dist/models.d.ts +162 -59
- package/dist/prepare-inputs.d.ts +46 -27
- package/dist/prepare-inputs.js +123 -42
- package/dist/prepare-inputs.js.map +1 -1
- package/dist/product-models.d.ts +97 -75
- package/dist/runs.d.ts +5 -3
- package/dist/runs.js.map +1 -1
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/docs/architecture.md +20 -21
- package/docs/cli.md +1 -1
- package/docs/crate-routes.md +42 -20
- package/docs/errors.md +7 -6
- package/docs/hook-bundle.md +1 -1
- package/docs/input-preparation.md +15 -40
- package/docs/method-trees.md +199 -0
- package/docs/run-results.md +5 -2
- package/package.json +2 -2
- package/dist/bundle-resources.d.ts +0 -62
- package/dist/bundle-resources.js +0 -165
- package/dist/bundle-resources.js.map +0 -1
- package/dist/method-source.d.ts +0 -19
- package/dist/method-source.js +0 -50
- package/dist/method-source.js.map +0 -1
- package/docs/bundle-resources.md +0 -107
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The `.mthds` post-edit hook's networked stage: the edited file's method tree validated through
|
|
3
|
+
* the SDK (`POST /v1/validate`, `allow_signatures: true`), held to one deadline over the whole
|
|
4
|
+
* stage, so the hook never outlasts its harness's patience whatever the network does.
|
|
5
|
+
*/
|
|
6
|
+
import { gatherMethodTree } from "./bundle-gather.js";
|
|
7
|
+
import { createHookClient } from "./validate-client.js";
|
|
8
|
+
/**
|
|
9
|
+
* The deadline over the whole validate stage, well under the hook's overall timeout: the version
|
|
10
|
+
* handshake, the blob route, the uploads of the files the API lacks (a tree up to the gatherer's
|
|
11
|
+
* caps, 12 MiB) and the validation itself all run under it.
|
|
12
|
+
*/
|
|
13
|
+
export const VALIDATE_TIMEOUT_MS = 10_000;
|
|
14
|
+
/**
|
|
15
|
+
* Run the networked validate stage on `filePath`. Every no-verdict condition maps to
|
|
16
|
+
* `unavailable` — no API key, a tree the gatherer refuses, the deadline running out, any failure
|
|
17
|
+
* of the client — so a machine consumer branches on the structured verdict, never on transport,
|
|
18
|
+
* and the lint and format verdicts the hook already applied stand.
|
|
19
|
+
*/
|
|
20
|
+
export async function runValidateStage(filePath, options = {}) {
|
|
21
|
+
if (options.client === undefined && !process.env.PIPELEX_API_KEY) {
|
|
22
|
+
return { status: "unavailable" };
|
|
23
|
+
}
|
|
24
|
+
// One deadline over the whole stage: the signal reaches every request and upload the
|
|
25
|
+
// validation makes, each stopped in flight once it fires, so nothing keeps running after the
|
|
26
|
+
// hook has given up on it.
|
|
27
|
+
const deadline = AbortSignal.timeout(options.timeoutMs ?? VALIDATE_TIMEOUT_MS);
|
|
28
|
+
const gathered = await gatherMethodTree(filePath);
|
|
29
|
+
if (!gathered.ok) {
|
|
30
|
+
return { status: "unavailable" };
|
|
31
|
+
}
|
|
32
|
+
try {
|
|
33
|
+
const client = options.client ?? createHookClient();
|
|
34
|
+
const result = await client.validate({ tree: gathered.tree }, true, { signal: deadline });
|
|
35
|
+
if (result.is_valid === true) {
|
|
36
|
+
return {
|
|
37
|
+
status: "valid",
|
|
38
|
+
pendingSignatures: Array.isArray(result.pending_signatures)
|
|
39
|
+
? result.pending_signatures
|
|
40
|
+
: [],
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
if (result.is_valid === false) {
|
|
44
|
+
return {
|
|
45
|
+
status: "invalid",
|
|
46
|
+
message: result.message,
|
|
47
|
+
validationErrors: Array.isArray(result.validation_errors) ? result.validation_errors : [],
|
|
48
|
+
renderedMarkdown: result.rendered_markdown,
|
|
49
|
+
};
|
|
50
|
+
}
|
|
51
|
+
return { status: "unavailable" }; // no discriminant — no verdict
|
|
52
|
+
}
|
|
53
|
+
catch {
|
|
54
|
+
return { status: "unavailable" };
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
//# sourceMappingURL=validate-stage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"validate-stage.js","sourceRoot":"","sources":["../../src/hooks/validate-stage.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAIH,OAAO,EAAE,gBAAgB,EAAE,MAAM,oBAAoB,CAAC;AACtD,OAAO,EAAE,gBAAgB,EAAE,MAAM,sBAAsB,CAAC;AAExD;;;;GAIG;AACH,MAAM,CAAC,MAAM,mBAAmB,GAAG,MAAM,CAAC;AAU1C;;;;;GAKG;AACH,MAAM,CAAC,KAAK,UAAU,gBAAgB,CACpC,QAAgB,EAChB,UAAgC,EAAE;IAElC,IAAI,OAAO,CAAC,MAAM,KAAK,SAAS,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,eAAe,EAAE,CAAC;QACjE,OAAO,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;IACnC,CAAC;IACD,qFAAqF;IACrF,6FAA6F;IAC7F,2BAA2B;IAC3B,MAAM,QAAQ,GAAG,WAAW,CAAC,OAAO,CAAC,OAAO,CAAC,SAAS,IAAI,mBAAmB,CAAC,CAAC;IAC/E,MAAM,QAAQ,GAAG,MAAM,gBAAgB,CAAC,QAAQ,CAAC,CAAC;IAClD,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;QACjB,OAAO,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;IACnC,CAAC;IACD,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,IAAI,gBAAgB,EAAE,CAAC;QACpD,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,QAAQ,CAAC,EAAE,IAAI,EAAE,QAAQ,CAAC,IAAI,EAAE,EAAE,IAAI,EAAE,EAAE,MAAM,EAAE,QAAQ,EAAE,CAAC,CAAC;QAC1F,IAAI,MAAM,CAAC,QAAQ,KAAK,IAAI,EAAE,CAAC;YAC7B,OAAO;gBACL,MAAM,EAAE,OAAO;gBACf,iBAAiB,EAAE,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,kBAAkB,CAAC;oBACzD,CAAC,CAAC,MAAM,CAAC,kBAAkB;oBAC3B,CAAC,CAAC,EAAE;aACP,CAAC;QACJ,CAAC;QACD,IAAI,MAAM,CAAC,QAAQ,KAAK,KAAK,EAAE,CAAC;YAC9B,OAAO;gBACL,MAAM,EAAE,SAAS;gBACjB,OAAO,EAAE,MAAM,CAAC,OAAO;gBACvB,gBAAgB,EAAE,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,iBAAiB,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,iBAAiB,CAAC,CAAC,CAAC,EAAE;gBACzF,gBAAgB,EAAE,MAAM,CAAC,iBAAiB;aAC3C,CAAC;QACJ,CAAC;QACD,OAAO,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC,CAAC,+BAA+B;IACnE,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;IACnC,CAAC;AACH,CAAC"}
|
package/dist/index.d.ts
CHANGED
|
@@ -12,9 +12,9 @@ export * from "mthds/protocol";
|
|
|
12
12
|
export { PipelexApiClient, DEFAULT_API_BASE_URL, isGatewayCutOff } from "./client.js";
|
|
13
13
|
export { buildUserAgent, validateAppInfo, MAX_USER_AGENT_LENGTH } from "./user-agent.js";
|
|
14
14
|
export type { AppInfo, RuntimeInfo } from "./user-agent.js";
|
|
15
|
-
export type {
|
|
16
|
-
export
|
|
17
|
-
export {
|
|
15
|
+
export type { PipelexApiRunExtensions, PipelexHostedRunExtensions, PipelexRunOptions, PipelexStartOptions, PipelexStartRequestOptions, PipelexValidateSource, ValidateMethodSelector, ValidateOptions, PipelexApiClientOptions, } from "./client.js";
|
|
16
|
+
export { INLINE_TREE_MAX_BYTES } from "./method-trees.js";
|
|
17
|
+
export type { MethodTreeForms, MethodTreeLimits } from "./method-trees.js";
|
|
18
18
|
export { parseMethodSelector } from "./method-selector.js";
|
|
19
19
|
export type { ParsedMethodSelector } from "./method-selector.js";
|
|
20
20
|
export { ExactJsonUnsupportedError, parseExactJson, stringifyExactJson } from "./exact-json.js";
|
|
@@ -26,15 +26,15 @@ export type { InputFormFault, PrepareInputsBase, PrepareInputsClosure, PrepareIn
|
|
|
26
26
|
export { inputFormFault } from "./prepare-inputs.js";
|
|
27
27
|
export { locateArtifacts, collectArtifacts, artifactFilename, PIPELEX_STORAGE_SCHEME, BULK_RESOLVE_MAX_URIS, DEFAULT_ARTIFACT_MAX_BYTES, DEFAULT_ARTIFACT_TIMEOUT_MS, DEFAULT_DOWNLOAD_MAX_TOTAL_BYTES, DEFAULT_DOWNLOAD_CONCURRENCY, } from "./artifacts.js";
|
|
28
28
|
export type { ArtifactItemError, ArtifactLocation, ArtifactScope, BulkResolveStorageUrlsInput, BulkResolvedStorageUrls, DownloadArtifactsOptions, DownloadArtifactsRequest, DownloadArtifactsResult, DownloadedArtifact, FetchArtifactOptions, ResolvedArtifact, } from "./artifacts.js";
|
|
29
|
-
export type { DiagnosticKind, DiagnosticRange, Diagnostic, LintResponse, FormatResponse, DictStuff, DictWorkingMemory, DictPipeOutput, DictRunResultExecute, MethodProvenance, PipelexRunResultStart, PipelexHostedToolingExtensions, DryRunStatus, ValidatedPipeEntry, LiftablePipeEntry, PipelexValidationReport, PipelexInvalidReport, PipelexValidationResult, ValidationErrorCategory, ValidationErrorItem, FixSafety, FixOpKind, TomlScalar, TomlValue, FixValue, SetKeyOp, EnsureTableOp, DeleteKeyOp, DeleteTableOp, RenameTableKeyOp, MoveKeyOp, RemapValueOp, FixOp, SuggestedFix,
|
|
29
|
+
export type { DiagnosticKind, DiagnosticRange, Diagnostic, LintResponse, FormatResponse, DictStuff, DictWorkingMemory, DictPipeOutput, DictRunResultExecute, MethodProvenance, PipelexRunResultStart, PipelexHostedToolingExtensions, DryRunStatus, ValidatedPipeEntry, LiftablePipeEntry, TreeFileUse, TreeFileRead, PipelexValidationReport, PipelexInvalidReport, PipelexValidationResult, ValidationErrorCategory, ValidationErrorItem, FixSafety, FixOpKind, TomlScalar, TomlValue, FixValue, SetKeyOp, EnsureTableOp, DeleteKeyOp, DeleteTableOp, RenameTableKeyOp, MoveKeyOp, RemapValueOp, FixOp, SuggestedFix, CrateRequestBase, CrateRouteOptions, CrateInvalidReport, GeneratedArtifact, ResolveRequest, ResolveValidReport, ResolveResponse, CodegenKind, CodegenTarget, CodegenRequest, CodegenValidReport, CodegenResponse, PipeIORequest, PipeIOValidReport, PipeIOResponse, ModelCheckCategory, ModelReferenceKind, ModelReferenceResolution, ModelReferenceMatchBase, PresetMatch, AliasMatch, WaterfallMatch, HandleMatch, ModelReferenceMatch, ModelReferenceVerdictBase, PresetReferenceVerdict, AliasReferenceVerdict, WaterfallReferenceVerdict, HandleReferenceVerdict, ModelReferenceVerdict, } from "./models.js";
|
|
30
30
|
export { runCodegenCheck, isStampableArtifactPath, STAMPABLE_ARTIFACT_SUFFIXES, CodegenLockError, } from "./codegen-check.js";
|
|
31
31
|
export type { CodegenCheckInput, CodegenCheckReport, CodegenDrift, CodegenDriftCategory, CodegenTreeFile, } from "./codegen-check.js";
|
|
32
|
-
export type { UserProfile, ListMethodExamplesQuery, ListMethodsQuery, ListMethodVersionsQuery, MethodData, MethodDeletionAccepted, MethodDeletionState, MethodDraftInput, MethodExample, MethodExampleCreateInput, MethodExampleLatestRunInput, MethodExampleLatestRunOutcome, MethodExampleLatestRunRecorded, MethodExampleLatestRunResult, MethodExampleLatestRunStale, MethodExamplePage, MethodExampleUpdateInput, MethodPage, MethodPublished, MethodPublishInput, MethodPublishOutcome, MethodPublishRefusalReason, MethodPublishRefused, MethodPublishResult, MethodPublishUnchanged, MethodRenameInput, MethodSummary, MethodVersion, MethodVersionPage, MethodVersionSummary, MethodWriteInput, Membership, MembershipsResponse, OrgRole, SubscriptionResponse, PlanView, InvoiceView, CheckoutResponse, ChangePlanResponse, BillingPortalResponse, PipelexApiKey, PipelexApiKeyCreated, PipelexApiKeyList, OnboardingRole, OnboardingCurrentTool, OnboardingInputType, OnboardingHeardFrom, OnboardingSubmission, ResolvedStorageUrl, UploadInput, UploadedFile, UploadGrantInput, UploadGrant, ListRunsQuery, PipelineRun, RunDetail, RunHistoryItem, RunPage, UpdateRunInput, } from "./product-models.js";
|
|
32
|
+
export type { UserProfile, ListMethodExamplesQuery, ListMethodsQuery, ListMethodVersionsQuery, MethodData, MethodDeletionAccepted, MethodDeletionState, MethodDetail, MethodDraftInput, MethodExample, MethodExampleCreateInput, MethodExampleLatestRunInput, MethodExampleLatestRunOutcome, MethodExampleLatestRunRecorded, MethodExampleLatestRunResult, MethodExampleLatestRunStale, MethodExamplePage, MethodExampleUpdateInput, MethodPage, MethodPublished, MethodPublishInput, MethodPublishOutcome, MethodPublishRefusalReason, MethodPublishRefused, MethodPublishResult, MethodPublishUnchanged, MethodRenameInput, MethodSummary, MethodTreeInput, MethodVersion, MethodVersionPage, MethodVersionSummary, MethodWriteInput, SavedMethodFile, Membership, MembershipsResponse, OrgRole, SubscriptionResponse, PlanView, InvoiceView, CheckoutResponse, ChangePlanResponse, BillingPortalResponse, PipelexApiKey, PipelexApiKeyCreated, PipelexApiKeyList, OnboardingRole, OnboardingCurrentTool, OnboardingInputType, OnboardingHeardFrom, OnboardingSubmission, ResolvedStorageUrl, UploadInput, UploadedFile, UploadGrantInput, UploadGrant, ListRunsQuery, PipelineRun, RunDetail, RunHistoryItem, RunPage, UpdateRunInput, } from "./product-models.js";
|
|
33
33
|
export { isFresherRunProgress, isTerminalRunStatus, isSuccessRunStatus, RUN_RESULT_ARTIFACTS, } from "./runs.js";
|
|
34
34
|
export type { DegradationReason, GetRunResultOptions, ProgressAttempt, ProgressBatch, ProgressCondition, ProgressFailure, ProgressInvocation, ProgressInvocationStatus, RunDegradation, RunProgress, RunProgressStatus, RunResultArtifact, RunStatus, RunPublic, RunRead, RunResults, RunResultState, StartAndWaitForResultOptions, TokensUsageRecord, WaitForResultOptions, } from "./runs.js";
|
|
35
35
|
export { summarizeUsage } from "./usage.js";
|
|
36
36
|
export type { PipeUsageSummary, RunUsagePair, UsageSummary, UsageSummaryState, UsageTokenTotals, } from "./usage.js";
|
|
37
37
|
export { problemVerdict } from "./error-verdicts.js";
|
|
38
|
-
export { PipelexRequestError, errorVerdictOf, runMayHaveStartedOf, RequestArgumentError, ApiResponseError, ApiUnreachableError, MissingMainStuffError, PagingNotTerminatingError, PipelineExecuteTimeoutError, RunFailedError, RunTimeoutError, RunStillRunningError, RunLifecycleUnavailableError, InputPreparationError,
|
|
39
|
-
export type { ApiResponseErrorOptions, ErrorDomain, ErrorVerdict, IdempotencyErrorCode, MethodErrorCode, RejectedAssetCode, UploadNotAllowedKind, UploadTransportCode, } from "./errors.js";
|
|
38
|
+
export { PipelexRequestError, errorVerdictOf, runMayHaveStartedOf, RequestArgumentError, ApiResponseError, ApiUnreachableError, MissingMainStuffError, PagingNotTerminatingError, PipelineExecuteTimeoutError, RunFailedError, RunTimeoutError, RunStillRunningError, RunLifecycleUnavailableError, InputPreparationError, InvalidLocalSourceError, InvalidInputValueError, UploadNotAllowedError, MethodLoadError, RejectedAssetError, UnsupportedUploadCapabilityError, UploadAuthenticationError, UploadTransportError, ArtifactOperationError, ArtifactAuthenticationError, ArtifactFetchError, ScopeUnavailableError, MethodFileTransferError, } from "./errors.js";
|
|
39
|
+
export type { ApiResponseErrorOptions, ErrorDomain, ErrorVerdict, IdempotencyErrorCode, MethodErrorCode, MethodFileTransferCode, MethodFileTransferOperation, RejectedAssetCode, UploadNotAllowedKind, UploadTransportCode, } from "./errors.js";
|
|
40
40
|
export type { FieldError, MigrationErrorBlock, ProblemDetails, ProviderErrorMetadata, RunErrorReport, UserAction, } from "./error-models.js";
|
package/dist/index.js
CHANGED
|
@@ -19,8 +19,11 @@ export { PipelexApiClient, DEFAULT_API_BASE_URL, isGatewayCutOff } from "./clien
|
|
|
19
19
|
// makes its own raw requests to the API sends the same value, and can check an `appInfo`
|
|
20
20
|
// against the grammar and the length ceiling before constructing a client.
|
|
21
21
|
export { buildUserAgent, validateAppInfo, MAX_USER_AGENT_LENGTH } from "./user-agent.js";
|
|
22
|
-
//
|
|
23
|
-
|
|
22
|
+
// A method's tree: the four forms every method-taking route takes it in, the limits
|
|
23
|
+
// `methodTreeLimits` reports, and the inline threshold below which a tree travels whole. The
|
|
24
|
+
// standard's own tree types (`MethodTreeSource`, `BlobRef`, `MissingBlobsResult` and the rest)
|
|
25
|
+
// come with the `mthds/protocol` re-export above.
|
|
26
|
+
export { INLINE_TREE_MAX_BYTES } from "./method-trees.js";
|
|
24
27
|
// A method selector (`mt_…`, `mt_…@<n>`, `mt_…@draft`) → its bare id and the version it names.
|
|
25
28
|
export { parseMethodSelector } from "./method-selector.js";
|
|
26
29
|
// JSON whose integers stay exact: the reader of the answers carrying a person's data (a method
|
|
@@ -57,5 +60,5 @@ export { summarizeUsage } from "./usage.js";
|
|
|
57
60
|
// `runMayHaveStarted`, read with `runMayHaveStartedOf`. `problemVerdict` reads the standard's
|
|
58
61
|
// problem in the same vocabulary, as `errorVerdictOf` reads an `mthds` error.
|
|
59
62
|
export { problemVerdict } from "./error-verdicts.js";
|
|
60
|
-
export { PipelexRequestError, errorVerdictOf, runMayHaveStartedOf, RequestArgumentError, ApiResponseError, ApiUnreachableError, MissingMainStuffError, PagingNotTerminatingError, PipelineExecuteTimeoutError, RunFailedError, RunTimeoutError, RunStillRunningError, RunLifecycleUnavailableError, InputPreparationError,
|
|
63
|
+
export { PipelexRequestError, errorVerdictOf, runMayHaveStartedOf, RequestArgumentError, ApiResponseError, ApiUnreachableError, MissingMainStuffError, PagingNotTerminatingError, PipelineExecuteTimeoutError, RunFailedError, RunTimeoutError, RunStillRunningError, RunLifecycleUnavailableError, InputPreparationError, InvalidLocalSourceError, InvalidInputValueError, UploadNotAllowedError, MethodLoadError, RejectedAssetError, UnsupportedUploadCapabilityError, UploadAuthenticationError, UploadTransportError, ArtifactOperationError, ArtifactAuthenticationError, ArtifactFetchError, ScopeUnavailableError, MethodFileTransferError, } from "./errors.js";
|
|
61
64
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,6FAA6F;AAC7F,OAAO,EAAE,WAAW,EAAE,MAAM,cAAc,CAAC;AAE3C,oFAAoF;AACpF,kFAAkF;AAClF,mFAAmF;AACnF,wBAAwB;AACxB,cAAc,gBAAgB,CAAC;AAE/B,wEAAwE;AACxE,OAAO,EAAE,gBAAgB,EAAE,oBAAoB,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AACtF,sFAAsF;AACtF,yFAAyF;AACzF,2EAA2E;AAC3E,OAAO,EAAE,cAAc,EAAE,eAAe,EAAE,qBAAqB,EAAE,MAAM,iBAAiB,CAAC;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,6FAA6F;AAC7F,OAAO,EAAE,WAAW,EAAE,MAAM,cAAc,CAAC;AAE3C,oFAAoF;AACpF,kFAAkF;AAClF,mFAAmF;AACnF,wBAAwB;AACxB,cAAc,gBAAgB,CAAC;AAE/B,wEAAwE;AACxE,OAAO,EAAE,gBAAgB,EAAE,oBAAoB,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AACtF,sFAAsF;AACtF,yFAAyF;AACzF,2EAA2E;AAC3E,OAAO,EAAE,cAAc,EAAE,eAAe,EAAE,qBAAqB,EAAE,MAAM,iBAAiB,CAAC;AAczF,oFAAoF;AACpF,6FAA6F;AAC7F,+FAA+F;AAC/F,kDAAkD;AAClD,OAAO,EAAE,qBAAqB,EAAE,MAAM,mBAAmB,CAAC;AAE1D,+FAA+F;AAC/F,OAAO,EAAE,mBAAmB,EAAE,MAAM,sBAAsB,CAAC;AAE3D,+FAA+F;AAC/F,6FAA6F;AAC7F,iGAAiG;AACjG,8FAA8F;AAC9F,iEAAiE;AACjE,OAAO,EAAE,yBAAyB,EAAE,cAAc,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AAEhG,iGAAiG;AACjG,kFAAkF;AAClF,OAAO,EAAE,oBAAoB,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AAK/E,yFAAyF;AACzF,sEAAsE;AACtE,OAAO,EAAE,eAAe,EAAE,MAAM,mBAAmB,CAAC;AASpD,+FAA+F;AAC/F,0EAA0E;AAC1E,OAAO,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAC;AAErD,uEAAuE;AACvE,wFAAwF;AACxF,0FAA0F;AAC1F,iFAAiF;AACjF,OAAO,EACL,eAAe,EACf,gBAAgB,EAChB,gBAAgB,EAChB,sBAAsB,EACtB,qBAAqB,EACrB,0BAA0B,EAC1B,2BAA2B,EAC3B,gCAAgC,EAChC,4BAA4B,GAC7B,MAAM,gBAAgB,CAAC;AAqFxB,+EAA+E;AAC/E,4EAA4E;AAC5E,iFAAiF;AACjF,0EAA0E;AAC1E,OAAO,EACL,eAAe,EACf,uBAAuB,EACvB,2BAA2B,EAC3B,gBAAgB,GACjB,MAAM,oBAAoB,CAAC;AA2E5B,wEAAwE;AACxE,OAAO,EACL,oBAAoB,EACpB,mBAAmB,EACnB,kBAAkB,EAClB,oBAAoB,GACrB,MAAM,WAAW,CAAC;AAwBnB,oFAAoF;AACpF,OAAO,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAS5C,+EAA+E;AAC/E,gGAAgG;AAChG,8FAA8F;AAC9F,8EAA8E;AAC9E,OAAO,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAC;AACrD,OAAO,EACL,mBAAmB,EACnB,cAAc,EACd,mBAAmB,EACnB,oBAAoB,EACpB,gBAAgB,EAChB,mBAAmB,EACnB,qBAAqB,EACrB,yBAAyB,EACzB,2BAA2B,EAC3B,cAAc,EACd,eAAe,EACf,oBAAoB,EACpB,4BAA4B,EAC5B,qBAAqB,EACrB,uBAAuB,EACvB,sBAAsB,EACtB,qBAAqB,EACrB,eAAe,EACf,kBAAkB,EAClB,gCAAgC,EAChC,yBAAyB,EACzB,oBAAoB,EACpB,sBAAsB,EACtB,2BAA2B,EAC3B,kBAAkB,EAClB,qBAAqB,EACrB,uBAAuB,GACxB,MAAM,aAAa,CAAC"}
|
|
@@ -0,0 +1,344 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A method's tree on the client side (see `docs/method-trees.md`): the forms a caller gives a
|
|
3
|
+
* method's tree in, the listing of a directory through the `mthds` package's own lister, how a
|
|
4
|
+
* tree becomes the `files` map a request sends, inline or by hash, the blob routes that let a
|
|
5
|
+
* large tree travel by hash (mthds/docs/spec/protocol.md, "Sending files by hash"), the upload of
|
|
6
|
+
* a blob the receiver lacks, and the writing of a saved tree to disk.
|
|
7
|
+
*
|
|
8
|
+
* The wire types (`MethodTreeSource`, `BlobRef`, `MissingBlob` and the rest) are the standard's,
|
|
9
|
+
* imported from `mthds/protocol`. A directory is listed by `mthds`'s `listMethodTree`, the
|
|
10
|
+
* standard's lister with its membership rule, which this module loads by a dynamic import when a
|
|
11
|
+
* directory is given, so the SDK's static import graph keeps no Node built-in. The choice between
|
|
12
|
+
* inline and by hash follows `mthds`'s `MthdsApiClient` rule exactly, but its helpers are not
|
|
13
|
+
* exported on a subpath free of Node built-ins, so this module carries its own copy of them: the
|
|
14
|
+
* same threshold, the same weighing of the inline map, the same text-or-Base64 choice per file.
|
|
15
|
+
* SHA-256 is Web Crypto's, and Base64 is written here. Only `writeMethodTreeTo` and
|
|
16
|
+
* `listDirectoryTree` need Node, which each loads when called.
|
|
17
|
+
*/
|
|
18
|
+
import type { BlobRef, FileEntry, MethodFiles, MethodTreeSource, MethodTreeSourceFile, MissingBlob } from "mthds/protocol";
|
|
19
|
+
import { RequestArgumentError, type MethodFileTransferCode } from "./errors.js";
|
|
20
|
+
import type { SavedMethodFile } from "./product-models.js";
|
|
21
|
+
/**
|
|
22
|
+
* A method's tree, given in exactly one of four forms. Every route that takes a method's tree
|
|
23
|
+
* takes these: the runs (`execute`, `start`, `startAndWaitForResult`), `validate`, the crate
|
|
24
|
+
* routes (`resolve`, `codegen`, `pipeIo`), `prepareInputs` and the saves (`createMethod`,
|
|
25
|
+
* `writeDraft`).
|
|
26
|
+
*
|
|
27
|
+
* - `directory`, a path on disk, listed by the `mthds` package's lister under the MTHDS
|
|
28
|
+
* standard's membership rule: rooted at the nearest `METHODS.toml` at or above it, else at the
|
|
29
|
+
* directory itself, every file the rule keeps, a run's inputs file (`inputs.json`,
|
|
30
|
+
* `inputs.toml`) never among them, under the limits the deployment announces. A `.mthds` file
|
|
31
|
+
* named alone is a one-file tree unless a `METHODS.toml` above it roots a larger one. Node only.
|
|
32
|
+
* - `contents`, each file's bytes or its text by tree path, a map held in memory.
|
|
33
|
+
* - `tree`, a listed source such as the `MethodTree` `listMethodTree` returns.
|
|
34
|
+
* - `files`, the protocol's map of file entries, sent as given.
|
|
35
|
+
*
|
|
36
|
+
* A `directory`, `contents` or `tree` travels inline when small and by hash otherwise, after the
|
|
37
|
+
* files the receiver lacks are uploaded (`docs/method-trees.md`).
|
|
38
|
+
*/
|
|
39
|
+
export interface MethodTreeForms {
|
|
40
|
+
/** The method's directory, listed by the standard's lister. Node only. */
|
|
41
|
+
directory?: string | null;
|
|
42
|
+
/** Each file's bytes or text, by tree path. */
|
|
43
|
+
contents?: Readonly<Record<string, Uint8Array | string>> | null;
|
|
44
|
+
/** A listed tree, such as the `MethodTree` `listMethodTree` returns. */
|
|
45
|
+
tree?: MethodTreeSource | null;
|
|
46
|
+
/** The protocol's map of file entries, sent as given. */
|
|
47
|
+
files?: MethodFiles | null;
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* A method's tree in exactly one of the four forms of `MethodTreeForms`, each pinning the other
|
|
51
|
+
* three to `never`, so giving two is a compile error. The calls that take the tree beside a
|
|
52
|
+
* selector it excludes (`validate`, `prepareInputs`) take it in this shape.
|
|
53
|
+
*/
|
|
54
|
+
export type MethodTreeForm = {
|
|
55
|
+
directory: string;
|
|
56
|
+
contents?: never;
|
|
57
|
+
tree?: never;
|
|
58
|
+
files?: never;
|
|
59
|
+
} | {
|
|
60
|
+
contents: Readonly<Record<string, Uint8Array | string>>;
|
|
61
|
+
directory?: never;
|
|
62
|
+
tree?: never;
|
|
63
|
+
files?: never;
|
|
64
|
+
} | {
|
|
65
|
+
tree: MethodTreeSource;
|
|
66
|
+
directory?: never;
|
|
67
|
+
contents?: never;
|
|
68
|
+
files?: never;
|
|
69
|
+
} | {
|
|
70
|
+
files: MethodFiles;
|
|
71
|
+
directory?: never;
|
|
72
|
+
contents?: never;
|
|
73
|
+
tree?: never;
|
|
74
|
+
};
|
|
75
|
+
/** The four forms of the tree, each pinned to `never`, for a shape that takes no tree. */
|
|
76
|
+
export interface NoMethodTree {
|
|
77
|
+
directory?: never;
|
|
78
|
+
contents?: never;
|
|
79
|
+
tree?: never;
|
|
80
|
+
files?: never;
|
|
81
|
+
}
|
|
82
|
+
/**
|
|
83
|
+
* What keeps `value` from being a listed tree as far as the client reads one before any request,
|
|
84
|
+
* an object with a `files` list, a `digest` string and a `readFile` function, in words for a
|
|
85
|
+
* refusal ("a list", "an object without them", or its type); `undefined` when it is one. A tree
|
|
86
|
+
* holding no file passes here, and is refused where it would be sent.
|
|
87
|
+
*/
|
|
88
|
+
export declare function treeShapeFault(value: unknown): string | undefined;
|
|
89
|
+
/**
|
|
90
|
+
* The limits a deployment holds a tree to, in the shape the `mthds` package's `listMethodTree`
|
|
91
|
+
* takes as its `limits` option, so a lister stops at the first breach before hashing anything. A
|
|
92
|
+
* limit the deployment does not announce is absent.
|
|
93
|
+
*/
|
|
94
|
+
export interface MethodTreeLimits {
|
|
95
|
+
/** The most files a tree may hold. */
|
|
96
|
+
readonly maxFileCount?: number;
|
|
97
|
+
/** The largest one file may be, in bytes. */
|
|
98
|
+
readonly maxFileSize?: number;
|
|
99
|
+
/** The largest all the files together may be, in bytes. */
|
|
100
|
+
readonly maxTotalSize?: number;
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* Every limit a deployment's handshake announces for a tree under `limits.method_tree`, in bytes
|
|
104
|
+
* for the sizes, named as `mthds`'s `AnnouncedTreeLimits` names them. A limit not announced is
|
|
105
|
+
* absent.
|
|
106
|
+
*/
|
|
107
|
+
export interface AnnouncedTreeLimits {
|
|
108
|
+
/** The files of one tree. */
|
|
109
|
+
readonly maxFiles?: number;
|
|
110
|
+
/** One file of it. */
|
|
111
|
+
readonly maxFileBytes?: number;
|
|
112
|
+
/** All its files together. */
|
|
113
|
+
readonly maxTotalBytes?: number;
|
|
114
|
+
/** The bytes a request carries inline for its tree: its text and Base64 entries. */
|
|
115
|
+
readonly maxInlineBytes?: number;
|
|
116
|
+
}
|
|
117
|
+
/**
|
|
118
|
+
* The heaviest inline map, in bytes of its JSON serialization in UTF-8, that a request or a save
|
|
119
|
+
* sends inline to a deployment keeping a blob store, when the deployment announces no lower inline
|
|
120
|
+
* limit. Below it a tree is cheaper to send whole than to check and upload; above it every file
|
|
121
|
+
* travels by hash. `mthds`'s clients use the same threshold.
|
|
122
|
+
*/
|
|
123
|
+
export declare const INLINE_TREE_MAX_BYTES: number;
|
|
124
|
+
/**
|
|
125
|
+
* How long a version handshake is trusted before the client asks again, `mthds`'s
|
|
126
|
+
* `HANDSHAKE_TTL_MS`: a deployment's blob store and tree limits change only with a deploy, so a
|
|
127
|
+
* client asks once per this span rather than before every request, and drops the answer sooner
|
|
128
|
+
* when a refusal shows it stale (`POST /v1/blobs/missing` gone, a tree refused as too large).
|
|
129
|
+
*/
|
|
130
|
+
export declare const HANDSHAKE_TTL_MS: number;
|
|
131
|
+
/** How many blobs a request or a save uploads at once, and how many files `writeMethodTree` downloads at once. */
|
|
132
|
+
export declare const MAX_CONCURRENT_TRANSFERS = 8;
|
|
133
|
+
/**
|
|
134
|
+
* What a tree is prepared for, as its refusals and its failed uploads say it: a save of a method, or
|
|
135
|
+
* a request that runs or reads one (a run, `validate`, `resolve`, `codegen`, `pipeIo`).
|
|
136
|
+
*/
|
|
137
|
+
export interface TreeSending {
|
|
138
|
+
/** What did not happen because an upload failed, ending its message. */
|
|
139
|
+
readonly unsent: string;
|
|
140
|
+
/** What to give instead of a tree holding no file, when there is something. */
|
|
141
|
+
readonly emptyRemedy?: string;
|
|
142
|
+
}
|
|
143
|
+
/** A save's: a tree holding no file is given as `files: null`, which empties a draft. */
|
|
144
|
+
export declare const SAVE_SENDING: TreeSending;
|
|
145
|
+
/** A request's: a method has at least one file, so there is nothing to give instead. */
|
|
146
|
+
export declare const REQUEST_SENDING: TreeSending;
|
|
147
|
+
/** How a request prepares its tree, beyond what a save needs. */
|
|
148
|
+
export interface TreeSendOptions {
|
|
149
|
+
/**
|
|
150
|
+
* Read before each step the tree costs: each file read, the version handshake's use, the blob
|
|
151
|
+
* route and each upload. Once it has aborted, none of them starts and the abort is thrown; a
|
|
152
|
+
* request already sent runs to its end.
|
|
153
|
+
*/
|
|
154
|
+
readonly signal?: AbortSignal | undefined;
|
|
155
|
+
/**
|
|
156
|
+
* The request's `read_scope`, under which the blob route is asked which blobs are missing, so
|
|
157
|
+
* the blobs are uploaded into the store the request's hash entries are read from. The upload
|
|
158
|
+
* targets the route names are signed for that scope already.
|
|
159
|
+
*/
|
|
160
|
+
readonly readScope?: string | undefined;
|
|
161
|
+
}
|
|
162
|
+
/**
|
|
163
|
+
* A map a crate request was given, or `undefined` when it selects or sends nothing: absent, `null`,
|
|
164
|
+
* or a plain object holding no key, the empty-as-absent rule of the run options and of the Python
|
|
165
|
+
* SDK. Any other value is kept as given, so the server refuses a `files` that is not a map as the
|
|
166
|
+
* shape it is rather than reading it as absent.
|
|
167
|
+
*/
|
|
168
|
+
export declare function presentMap<T>(value: T | null | undefined): T | undefined;
|
|
169
|
+
/** The refusal of a tree holding no file, `call` naming the caller's method. */
|
|
170
|
+
export declare function emptyTreeRefusal(call: string, what: string, sending: TreeSending): RequestArgumentError;
|
|
171
|
+
/** Whether a version handshake declares a blob store (`blob_store: true`). */
|
|
172
|
+
export declare function declaresBlobStore(version: object): boolean;
|
|
173
|
+
/**
|
|
174
|
+
* The tree limits a version handshake announces under `limits.method_tree`. A value that is not a
|
|
175
|
+
* positive safe integer is left out rather than trusted, and a limit not announced is absent, so a
|
|
176
|
+
* bare runner, which announces none, yields no limit.
|
|
177
|
+
*/
|
|
178
|
+
export declare function announcedTreeLimits(version: object): AnnouncedTreeLimits;
|
|
179
|
+
/** The announced limits as the lister takes them, so it stops at the first breach before hashing. */
|
|
180
|
+
export declare function listerLimitsOf(announced: AnnouncedTreeLimits): MethodTreeLimits;
|
|
181
|
+
/**
|
|
182
|
+
* The inline threshold a tree is held to against a receiver keeping a blob store: the lower of
|
|
183
|
+
* `INLINE_TREE_MAX_BYTES` and the inline limit the receiver announces, as `mthds`'s
|
|
184
|
+
* `MthdsApiClient` reads it.
|
|
185
|
+
*/
|
|
186
|
+
export declare function inlineThreshold(announced: AnnouncedTreeLimits): number;
|
|
187
|
+
/** What an inline map spends in a request: its JSON serialization with no whitespace, in UTF-8. */
|
|
188
|
+
export declare function inlineMapBytes(files: MethodFiles): number;
|
|
189
|
+
/** The total of a tree's file sizes, in bytes. */
|
|
190
|
+
export declare function treeTotalSize(tree: MethodTreeSource): number;
|
|
191
|
+
/**
|
|
192
|
+
* Every file's bytes, by tree path, each read and checked by the tree, one file at a time. `signal`
|
|
193
|
+
* is read before each file: once it has aborted, no further file is read and the abort is thrown.
|
|
194
|
+
*/
|
|
195
|
+
export declare function readTreeBytes(tree: MethodTreeSource, signal?: AbortSignal): Promise<Map<string, Uint8Array>>;
|
|
196
|
+
/**
|
|
197
|
+
* Every file's bytes, by tree path, read into `read`: a file already there is not read again, so
|
|
198
|
+
* a request that weighs a tree and then uploads from it, or prepares it a second time, reads each
|
|
199
|
+
* file once. `signal` is read before each file read, as `readTreeBytes` reads it.
|
|
200
|
+
*/
|
|
201
|
+
export declare function readTreeBytesInto(tree: MethodTreeSource, read: Map<string, Uint8Array>, signal?: AbortSignal): Promise<Map<string, Uint8Array>>;
|
|
202
|
+
/** The whole tree as inline entries, from bytes already read by `readTreeBytes`. */
|
|
203
|
+
export declare function inlineFilesOf(tree: MethodTreeSource, bytesByPath: ReadonlyMap<string, Uint8Array>): MethodFiles;
|
|
204
|
+
/** The whole tree as hash entries, which the platform resolves in the organization's blobs. */
|
|
205
|
+
export declare function hashMethodFiles(tree: MethodTreeSource): MethodFiles;
|
|
206
|
+
/** Each blob of the tree once, in the tree's order: files with the same bytes share one blob. */
|
|
207
|
+
export declare function uniqueBlobs(tree: MethodTreeSource): BlobRef[];
|
|
208
|
+
/** A file of the tree holding each blob, so a missing blob's bytes can be read and uploaded. */
|
|
209
|
+
export declare function fileByBlob(tree: MethodTreeSource): Map<string, MethodTreeSourceFile>;
|
|
210
|
+
/**
|
|
211
|
+
* Run `task` over `items`, at most `limit` at a time. The first task to fail stops the run: no
|
|
212
|
+
* queued item is handed out after it, `signal` is aborted so the tasks still in flight can stop
|
|
213
|
+
* early, and once they have settled the first failure is thrown.
|
|
214
|
+
*/
|
|
215
|
+
export declare function forEachConcurrently<T>(items: readonly T[], limit: number, task: (item: T, signal: AbortSignal) => Promise<void>): Promise<void>;
|
|
216
|
+
/**
|
|
217
|
+
* Whether an answer refuses a tree as past one of the receiver's limits, as `mthds`'s
|
|
218
|
+
* `MthdsApiClient` reads one: a `422` whose problem is the core registry's
|
|
219
|
+
* `method.package_invalid` carrying its numeric `limit` parameter, the hosted platform's
|
|
220
|
+
* `method_tree_too_large` code, or pipelex-api's `MethodTreeTooLarge` error type.
|
|
221
|
+
*/
|
|
222
|
+
export declare function isMethodTreeTooLarge(status: number, body: string): boolean;
|
|
223
|
+
/**
|
|
224
|
+
* The blobs a `422` lists as missing, as `mthds`'s `MthdsApiClient` reads them: the
|
|
225
|
+
* `params.missing_blobs` of a problem coded `request.blobs_missing`, or `undefined` when the
|
|
226
|
+
* answer is no such problem or the list holds anything but strings.
|
|
227
|
+
*/
|
|
228
|
+
export declare function missingBlobsOf(status: number, body: string): string[] | undefined;
|
|
229
|
+
/**
|
|
230
|
+
* A signal that aborts when either does, with the reason of the first to abort, and `dispose`,
|
|
231
|
+
* which detaches it from both once it is no longer needed, so a long-lived signal does not keep
|
|
232
|
+
* a listener per call. `second` absent gives `first` itself. Built by hand rather than with
|
|
233
|
+
* `AbortSignal.any`, which older browsers lack.
|
|
234
|
+
*/
|
|
235
|
+
export declare function eitherSignal(first: AbortSignal, second: AbortSignal | undefined): {
|
|
236
|
+
signal: AbortSignal;
|
|
237
|
+
dispose: () => void;
|
|
238
|
+
};
|
|
239
|
+
/**
|
|
240
|
+
* The tree whose files are `contents`, each file's bytes or its text by tree path, a text encoded
|
|
241
|
+
* in UTF-8. The keys are sent as they are, and the platform refuses one that is not a tree path,
|
|
242
|
+
* with the `422` `invalid_method_files` naming it. `call` names the caller's method in a refusal.
|
|
243
|
+
*
|
|
244
|
+
* Throws `RequestArgumentError` for `contents` holding no file, for a value that is neither a
|
|
245
|
+
* string nor bytes, and for a text holding a lone surrogate, which no file can hold. `sending` says
|
|
246
|
+
* what the tree is for, which the refusal of an empty one names.
|
|
247
|
+
*/
|
|
248
|
+
export declare function contentsTreeSource(contents: Readonly<Record<string, Uint8Array | string>>, call: string, sending: TreeSending): Promise<MethodTreeSource>;
|
|
249
|
+
/** A tree listed from the file system: its files, and the absolute path of its root. */
|
|
250
|
+
export interface ListedMethodTree extends MethodTreeSource {
|
|
251
|
+
/** The absolute path of the root, or `null` for the one-file tree of a `.mthds` file alone. */
|
|
252
|
+
readonly root: string | null;
|
|
253
|
+
}
|
|
254
|
+
/**
|
|
255
|
+
* The tree of the method directory `directory`, listed by the `mthds` package's `listMethodTree`
|
|
256
|
+
* under the MTHDS standard's membership rule and Manifest Discovery, stopping at the first of
|
|
257
|
+
* `limits` it breaches, before any file is hashed. A run's inputs file is never in it. Node only:
|
|
258
|
+
* `mthds`'s root entry, which reads the file system, is loaded by this call alone.
|
|
259
|
+
*
|
|
260
|
+
* Throws `RequestArgumentError` naming `call` when the directory cannot be listed as a tree, the
|
|
261
|
+
* `mthds` package's `MethodTreeError` as its `cause` with its `code` (`not_found`,
|
|
262
|
+
* `symbolic_link`, `limit_exceeded`, `empty_tree` and the rest): a path that names nothing, a
|
|
263
|
+
* symbolic link or a special file in the tree, a tree past one of `limits`, a tree holding no file.
|
|
264
|
+
*/
|
|
265
|
+
export declare function listDirectoryTree(directory: string, limits: MethodTreeLimits, call: string): Promise<ListedMethodTree>;
|
|
266
|
+
/**
|
|
267
|
+
* The tree digest of a tree's files: `sha256:` and the SHA-256 of its listing, one line
|
|
268
|
+
* `<sha256> <path>` per file, in tree path order.
|
|
269
|
+
*/
|
|
270
|
+
export declare function treeDigestOf(files: readonly MethodTreeSourceFile[]): Promise<string>;
|
|
271
|
+
/** The SHA-256 of `bytes`, in lowercase hexadecimal, by Web Crypto. */
|
|
272
|
+
export declare function sha256Hex(bytes: Uint8Array): Promise<string>;
|
|
273
|
+
/**
|
|
274
|
+
* Compare two strings byte for byte on their UTF-8 encoding, the order tree paths are sorted in.
|
|
275
|
+
* JavaScript's own string order compares UTF-16 code units, which puts a character above U+FFFF
|
|
276
|
+
* before one between U+E000 and U+FFFF, where UTF-8 puts it after.
|
|
277
|
+
*/
|
|
278
|
+
export declare function compareUtf8(left: string, right: string): number;
|
|
279
|
+
/** The entry a file travels as inline: its text when its bytes are UTF-8, its Base64 otherwise. */
|
|
280
|
+
export declare function inlineFileEntry(bytes: Uint8Array): FileEntry;
|
|
281
|
+
/**
|
|
282
|
+
* Add a file to a map of file entries as an own property, since assigning to a key such as
|
|
283
|
+
* `__proto__`, a tree path like any other, would set the object's prototype instead of adding the
|
|
284
|
+
* file.
|
|
285
|
+
*/
|
|
286
|
+
export declare function defineFileEntry(files: MethodFiles, treePath: string, entry: FileEntry): void;
|
|
287
|
+
/** Canonical padded standard Base64 (RFC 4648), with no line break and its pad bits zero. */
|
|
288
|
+
export declare function encodeBase64(bytes: Uint8Array): string;
|
|
289
|
+
/**
|
|
290
|
+
* Upload one blob's bytes to the target `POST /v1/blobs/missing` named: the bytes as the whole body
|
|
291
|
+
* of a request with the target's method to its URL, carrying exactly the target's headers and no
|
|
292
|
+
* credential of the client, since the signed URL authorizes the upload itself. A `412` from a
|
|
293
|
+
* target asking for a create-only write (`If-None-Match`) means the bytes are already stored, and
|
|
294
|
+
* counts as uploaded.
|
|
295
|
+
*
|
|
296
|
+
* Throws `MethodFileTransferError` (`operation` `upload`) when storage gives no answer within
|
|
297
|
+
* `timeoutMs` or answers any other non-2xx; neither its message nor any member carries the URL,
|
|
298
|
+
* nor storage's error body, which can echo the signed request. Its message ends with what did not
|
|
299
|
+
* happen because of it, `options.unsent`.
|
|
300
|
+
*/
|
|
301
|
+
export declare function uploadBlob(blob: MissingBlob, bytes: Uint8Array, options: {
|
|
302
|
+
timeoutMs: number;
|
|
303
|
+
signal?: AbortSignal;
|
|
304
|
+
unsent: string;
|
|
305
|
+
}): Promise<void>;
|
|
306
|
+
/**
|
|
307
|
+
* The code of a transfer storage answered with a non-2xx `status`: `storage_error` for one the
|
|
308
|
+
* fallback table calls retryable (`408`, `429`, a `5xx` other than `501`), `refused` otherwise.
|
|
309
|
+
*/
|
|
310
|
+
export declare function methodFileTransferCodeOfStatus(status: number): MethodFileTransferCode;
|
|
311
|
+
/**
|
|
312
|
+
* Write a saved tree to disk, each file of `files` at its tree path under `destination`; see
|
|
313
|
+
* `PipelexApiClient.writeMethodTree`. Node only: the file system modules are loaded when it runs.
|
|
314
|
+
*/
|
|
315
|
+
export declare function writeMethodTreeTo(files: readonly SavedMethodFile[], destination: string, options: {
|
|
316
|
+
timeoutMs: number;
|
|
317
|
+
}): Promise<void>;
|
|
318
|
+
/**
|
|
319
|
+
* Refuse a listing whose paths could not be written as a tree, before anything is downloaded. A
|
|
320
|
+
* platform's listing holds tree paths that never collide; the check guards the disk against any
|
|
321
|
+
* other listing a caller hands over, such as one built by hand, since a path such as `../x` would
|
|
322
|
+
* be written outside the destination. Throws `RequestArgumentError`.
|
|
323
|
+
*/
|
|
324
|
+
export declare function refuseUnwritableListing(files: readonly SavedMethodFile[]): void;
|
|
325
|
+
/**
|
|
326
|
+
* Why `candidate` is not a tree path, or `null` when it is one (mthds/docs/spec/method-tree.md,
|
|
327
|
+
* "Tree Paths"), the rule the `mthds` package's `treePathViolation` holds.
|
|
328
|
+
*/
|
|
329
|
+
export declare function treePathViolation(candidate: string): string | null;
|
|
330
|
+
/**
|
|
331
|
+
* The paths that collide: those equal to another once case-folded, and those naming, once
|
|
332
|
+
* case-folded, a directory of another, with the paths under it, sorted byte for byte. The fold is
|
|
333
|
+
* `toUpperCase().toLowerCase()`, which agrees with Unicode full case folding on the scripts a file
|
|
334
|
+
* name uses; a pair it misses still fails the write, which never writes over a file.
|
|
335
|
+
*/
|
|
336
|
+
export declare function pathCollisions(treePaths: readonly string[]): string[];
|
|
337
|
+
/**
|
|
338
|
+
* `text`, an answer that carries signed links, with every link hidden, for an error to hold: in a
|
|
339
|
+
* JSON body every `url` member, at any depth, is replaced whole, and in any text, JSON or not, a
|
|
340
|
+
* truncated body included, the query of every `http(s)` link is replaced, since a signed link's
|
|
341
|
+
* signature rides its query. A link is a bearer credential, so no error, message or member may
|
|
342
|
+
* carry one.
|
|
343
|
+
*/
|
|
344
|
+
export declare function redactSignedLinks(text: string): string;
|