@alwaysmeticulous/client 2.276.2 → 2.280.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.
@@ -9,3 +9,59 @@ export interface RepoUrlResponse {
9
9
  }
10
10
  export declare const getProject: (client: MeticulousClient) => Promise<Project | null>;
11
11
  export declare const getRepoUrl: ({ client, }: GetRepoUrlOptions) => Promise<RepoUrlResponse>;
12
+ /**
13
+ * Response of `GET /api/projects/source-archive-url`. Only returned for
14
+ * projects on the source-code-upload workflow.
15
+ *
16
+ * Callers that also need a diff between the resolved head commit and a base
17
+ * commit should make a separate call to `compare-commits` (already handles
18
+ * GitHub and GitLab).
19
+ */
20
+ export interface SourceArchiveUrlResponse {
21
+ /** Short-lived signed URL the caller can `GET` to download the archive. */
22
+ downloadUrl: string;
23
+ /**
24
+ * The actual commit SHA the archive corresponds to. May differ from the
25
+ * requested `commitSha` for session-selection / experiment runs (where the
26
+ * backend walks the default branch to find the latest archive).
27
+ */
28
+ resolvedCommitSha: string;
29
+ }
30
+ export interface GetSourceArchiveUrlOptions {
31
+ client: MeticulousClient;
32
+ /**
33
+ * The commit to fetch source code for. For session-selection / experiment
34
+ * runs pass `"unknown"`/`"experiment"`; the backend will resolve to the
35
+ * latest default-branch commit that has an uploaded archive.
36
+ */
37
+ commitSha: string;
38
+ }
39
+ /**
40
+ * Returns a signed download URL for the uploaded source-code archive at
41
+ * `commitSha`. Backed by `GET /api/projects/source-archive-url`.
42
+ *
43
+ * Only callable for projects with `usesSourceCodeUploads === true` (the
44
+ * backend returns 403 otherwise). Returns 404 (surfaced as a thrown error)
45
+ * if no archive has been uploaded for the requested commit and none of the
46
+ * recent default-branch commits have an archive either; the backend never
47
+ * falls back to a `git clone` URL.
48
+ */
49
+ export declare const getSourceArchiveUrl: ({ client, commitSha, }: GetSourceArchiveUrlOptions) => Promise<SourceArchiveUrlResponse>;
50
+ export interface RequestSourceCodeUploadUrlParams {
51
+ client: MeticulousClient;
52
+ commitSha: string;
53
+ /** Optional content-length so the backend can lock the URL to a fixed size. */
54
+ size?: number;
55
+ }
56
+ export interface RequestSourceCodeUploadUrlResponse {
57
+ uploadUrl: string;
58
+ }
59
+ /**
60
+ * Requests a short-lived signed URL the caller can `PUT` a `source.tar.gz`
61
+ * archive of the customer's repo to, for the given commit. Backed by
62
+ * `POST /api/projects/source-code-upload-url`.
63
+ *
64
+ * The backend rejects the call with a 403 when the project is not enabled
65
+ * for source-code uploads.
66
+ */
67
+ export declare const requestSourceCodeUploadUrl: ({ client, commitSha, size, }: RequestSourceCodeUploadUrlParams) => Promise<RequestSourceCodeUploadUrlResponse>;
@@ -1,8 +1,8 @@
1
1
  "use strict";
2
- !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="16f9e865-fcd8-539f-9e03-1799f62cac66")}catch(e){}}();
2
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="d74c9d4d-3a68-5d26-997c-9ee9a106160e")}catch(e){}}();
3
3
 
4
4
  Object.defineProperty(exports, "__esModule", { value: true });
5
- exports.getRepoUrl = exports.getProject = void 0;
5
+ exports.requestSourceCodeUploadUrl = exports.getSourceArchiveUrl = exports.getRepoUrl = exports.getProject = void 0;
6
6
  const errors_1 = require("../errors");
7
7
  const getProject = async (client) => {
8
8
  const { data } = await client
@@ -31,5 +31,44 @@ const getRepoUrl = async ({ client, }) => {
31
31
  return data;
32
32
  };
33
33
  exports.getRepoUrl = getRepoUrl;
34
+ /**
35
+ * Returns a signed download URL for the uploaded source-code archive at
36
+ * `commitSha`. Backed by `GET /api/projects/source-archive-url`.
37
+ *
38
+ * Only callable for projects with `usesSourceCodeUploads === true` (the
39
+ * backend returns 403 otherwise). Returns 404 (surfaced as a thrown error)
40
+ * if no archive has been uploaded for the requested commit and none of the
41
+ * recent default-branch commits have an archive either; the backend never
42
+ * falls back to a `git clone` URL.
43
+ */
44
+ const getSourceArchiveUrl = async ({ client, commitSha, }) => {
45
+ const params = new URLSearchParams();
46
+ params.set("commitSha", commitSha);
47
+ const path = `projects/source-archive-url?${params.toString()}`;
48
+ const { data } = await client
49
+ .get(path)
50
+ .catch((error) => {
51
+ throw (0, errors_1.maybeEnrichFetchError)(error);
52
+ });
53
+ return data;
54
+ };
55
+ exports.getSourceArchiveUrl = getSourceArchiveUrl;
56
+ /**
57
+ * Requests a short-lived signed URL the caller can `PUT` a `source.tar.gz`
58
+ * archive of the customer's repo to, for the given commit. Backed by
59
+ * `POST /api/projects/source-code-upload-url`.
60
+ *
61
+ * The backend rejects the call with a 403 when the project is not enabled
62
+ * for source-code uploads.
63
+ */
64
+ const requestSourceCodeUploadUrl = async ({ client, commitSha, size, }) => {
65
+ const { data } = await client
66
+ .post("projects/source-code-upload-url", { commitSha, ...(size != null ? { size } : {}) })
67
+ .catch((error) => {
68
+ throw (0, errors_1.maybeEnrichFetchError)(error);
69
+ });
70
+ return data;
71
+ };
72
+ exports.requestSourceCodeUploadUrl = requestSourceCodeUploadUrl;
34
73
  //# sourceMappingURL=project.api.js.map
35
- //# debugId=16f9e865-fcd8-539f-9e03-1799f62cac66
74
+ //# debugId=d74c9d4d-3a68-5d26-997c-9ee9a106160e
@@ -1 +1 @@
1
- {"version":3,"file":"project.api.js","sources":["../../src/api/project.api.ts"],"sourceRoot":"","names":[],"mappings":";;;;;AACA,sCAAgE;AAYzD,MAAM,UAAU,GAEQ,KAAK,EAAE,MAAM,EAAE,EAAE;IAC9C,MAAM,EAAE,IAAI,EAAE,GAAG,MAAM,MAAM;SAC1B,GAAG,CAAU,qBAAqB,CAAC;SACnC,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;QACf,IAAI,IAAA,qBAAY,EAAC,KAAK,CAAC,IAAI,KAAK,CAAC,QAAQ,EAAE,MAAM,KAAK,GAAG,EAAE,CAAC;YAC1D,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;QACxB,CAAC;QAED,MAAM,IAAA,8BAAqB,EAAC,KAAK,CAAC,CAAC;IACrC,CAAC,CAAC,CAAC;IACL,OAAO,IAAI,CAAC;AACd,CAAC,CAAC;AAbW,QAAA,UAAU,cAarB;AAEK,MAAM,UAAU,GAAG,KAAK,EAAE,EAC/B,MAAM,GACY,EAA4B,EAAE;IAChD,MAAM,EAAE,IAAI,EAAE,GAAG,MAAM,MAAM;SAC1B,GAAG,CAAqC,mBAAmB,CAAC;SAC5D,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;QACf,IAAI,IAAA,qBAAY,EAAC,KAAK,CAAC,EAAE,CAAC;YACxB,MAAM,YAAY,GAAG,KAAK,CAAC,QAAQ,EAAE,IAAI,EAAE,OAAO,CAAC;YAEnD,IAAI,YAAY,EAAE,CAAC;gBACjB,MAAM,IAAI,KAAK,CAAC,YAAY,CAAC,CAAC;YAChC,CAAC;QACH,CAAC;QAED,MAAM,KAAK,CAAC;IACd,CAAC,CAAC,CAAC;IAEL,OAAO,IAAI,CAAC;AACd,CAAC,CAAC;AAlBW,QAAA,UAAU,cAkBrB","debugId":"16f9e865-fcd8-539f-9e03-1799f62cac66"}
1
+ {"version":3,"file":"project.api.js","sources":["../../src/api/project.api.ts"],"sourceRoot":"","names":[],"mappings":";;;;;AACA,sCAAgE;AAYzD,MAAM,UAAU,GAEQ,KAAK,EAAE,MAAM,EAAE,EAAE;IAC9C,MAAM,EAAE,IAAI,EAAE,GAAG,MAAM,MAAM;SAC1B,GAAG,CAAU,qBAAqB,CAAC;SACnC,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;QACf,IAAI,IAAA,qBAAY,EAAC,KAAK,CAAC,IAAI,KAAK,CAAC,QAAQ,EAAE,MAAM,KAAK,GAAG,EAAE,CAAC;YAC1D,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;QACxB,CAAC;QAED,MAAM,IAAA,8BAAqB,EAAC,KAAK,CAAC,CAAC;IACrC,CAAC,CAAC,CAAC;IACL,OAAO,IAAI,CAAC;AACd,CAAC,CAAC;AAbW,QAAA,UAAU,cAarB;AAEK,MAAM,UAAU,GAAG,KAAK,EAAE,EAC/B,MAAM,GACY,EAA4B,EAAE;IAChD,MAAM,EAAE,IAAI,EAAE,GAAG,MAAM,MAAM;SAC1B,GAAG,CAAqC,mBAAmB,CAAC;SAC5D,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;QACf,IAAI,IAAA,qBAAY,EAAC,KAAK,CAAC,EAAE,CAAC;YACxB,MAAM,YAAY,GAAG,KAAK,CAAC,QAAQ,EAAE,IAAI,EAAE,OAAO,CAAC;YAEnD,IAAI,YAAY,EAAE,CAAC;gBACjB,MAAM,IAAI,KAAK,CAAC,YAAY,CAAC,CAAC;YAChC,CAAC;QACH,CAAC;QAED,MAAM,KAAK,CAAC;IACd,CAAC,CAAC,CAAC;IAEL,OAAO,IAAI,CAAC;AACd,CAAC,CAAC;AAlBW,QAAA,UAAU,cAkBrB;AAgCF;;;;;;;;;GASG;AACI,MAAM,mBAAmB,GAAG,KAAK,EAAE,EACxC,MAAM,EACN,SAAS,GACkB,EAAqC,EAAE;IAClE,MAAM,MAAM,GAAG,IAAI,eAAe,EAAE,CAAC;IACrC,MAAM,CAAC,GAAG,CAAC,WAAW,EAAE,SAAS,CAAC,CAAC;IACnC,MAAM,IAAI,GAAG,+BAA+B,MAAM,CAAC,QAAQ,EAAE,EAAE,CAAC;IAEhE,MAAM,EAAE,IAAI,EAAE,GAAG,MAAM,MAAM;SAC1B,GAAG,CAA8C,IAAI,CAAC;SACtD,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;QACf,MAAM,IAAA,8BAAqB,EAAC,KAAK,CAAC,CAAC;IACrC,CAAC,CAAC,CAAC;IAEL,OAAO,IAAI,CAAC;AACd,CAAC,CAAC;AAfW,QAAA,mBAAmB,uBAe9B;AAaF;;;;;;;GAOG;AACI,MAAM,0BAA0B,GAAG,KAAK,EAAE,EAC/C,MAAM,EACN,SAAS,EACT,IAAI,GAC6B,EAA+C,EAAE;IAClF,MAAM,EAAE,IAAI,EAAE,GAAG,MAAM,MAAM;SAC1B,IAAI,CACH,iCAAiC,EACjC,EAAE,SAAS,EAAE,GAAG,CAAC,IAAI,IAAI,IAAI,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CACjD;SACA,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;QACf,MAAM,IAAA,8BAAqB,EAAC,KAAK,CAAC,CAAC;IACrC,CAAC,CAAC,CAAC;IAEL,OAAO,IAAI,CAAC;AACd,CAAC,CAAC;AAfW,QAAA,0BAA0B,8BAerC","debugId":"d74c9d4d-3a68-5d26-997c-9ee9a106160e"}
package/dist/index.d.ts CHANGED
@@ -1,7 +1,7 @@
1
1
  export { AgentFeature, StructuredSessionDataResponse, StructuredSessionSummary, DiffsSummaryOptions, DiffsSummaryScreenshot, DiffsSummaryReplayDiff, DiffsSummaryResponse, ScreenshotDomDiffResponse, ScreenshotUrlsResponse, TimelineDiffEntry, TimelineDiffResponse, getStructuredSessionData, getTestRunDiffsSummary, getScreenshotDomDiff, getScreenshotUrls, getTimelineDiff, trackAgentFeatureUsage, } from "./api/agent.api";
2
2
  export * from "./api/github-cloud-replay.api";
3
3
  export { WhoamiResponse, getWhoami } from "./api/oauth.api";
4
- export { getProject, getRepoUrl } from "./api/project.api";
4
+ export { GetRepoUrlOptions, RepoUrlResponse, getProject, getRepoUrl, GetSourceArchiveUrlOptions, SourceArchiveUrlResponse, getSourceArchiveUrl, RequestSourceCodeUploadUrlParams, RequestSourceCodeUploadUrlResponse, requestSourceCodeUploadUrl, } from "./api/project.api";
5
5
  export { ReplayV3UploadLocations, getReplay, getReplayDownloadUrl, getReplayV3DownloadUrls, } from "./api/replay.api";
6
6
  export { getRecordedSession, getRecordedSessionData, getRecordingCommandId, postSessionIdNotification, } from "./api/session.api";
7
7
  export { ReplayDiffResponse, getReplayDiff } from "./api/replay-diff.api";
@@ -16,6 +16,8 @@ export { getValidAccessToken } from "./oauth/oauth-refresh";
16
16
  export { clearOAuthTokens } from "./oauth/oauth-token-store";
17
17
  export type { MeticulousClient } from "./types/client.types";
18
18
  export { getProxyAgent } from "./utils/get-proxy-agent";
19
+ export { PutFileToSignedUrlOptions, putFileToSignedUrl, } from "./utils/put-file-to-signed-url";
20
+ export { UploadError, isTransientUploadError, retryTransientUploadErrors, RetryTransientUploadErrorsOptions, } from "./utils/retry-transient-upload-errors";
19
21
  export { RequestAssetUploadParams, RequestAssetUploadResponse, requestAssetUpload, requestMultipartAssetUpload, RequestMultipartAssetUploadResponse, RequestUploadPartParams, RequestUploadPartResponse, requestUploadPart, RequestGitDiffUploadParams, RequestGitDiffUploadResponse, requestGitDiffUpload, CompleteAssetUploadParams, CompleteAssetUploadResponse, completeAssetUpload, CompleteContainerUploadParams, CompleteContainerUploadResponse, completeContainerUpload, MultiPartUploadInfo, DownloadDeploymentResponse, downloadProjectDeployment, GetContainerDeploymentResponse, getContainerDeployment, ContainerEnvVariable, } from "./api/project-deployments.api";
20
22
  export { GetRegistryAuthResponse, getRegistryAuth } from "./api/registry.api";
21
23
  export { isFetchError } from "./errors";
package/dist/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  "use strict";
2
- !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="787e56fc-127a-5a89-b852-a67e125e370c")}catch(e){}}();
2
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="c4f4b9c9-8243-5016-b0bf-99f3499377d5")}catch(e){}}();
3
3
 
4
4
  var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
5
5
  if (k2 === undefined) k2 = k;
@@ -16,7 +16,8 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
16
16
  for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
17
17
  };
18
18
  Object.defineProperty(exports, "__esModule", { value: true });
19
- exports.getRelevantSessions = exports.isFetchError = exports.getRegistryAuth = exports.getContainerDeployment = exports.downloadProjectDeployment = exports.completeContainerUpload = exports.completeAssetUpload = exports.requestGitDiffUpload = exports.requestUploadPart = exports.requestMultipartAssetUpload = exports.requestAssetUpload = exports.getProxyAgent = exports.clearOAuthTokens = exports.getValidAccessToken = exports.performOAuthLogin = exports.makeRequest = exports.isInteractiveContext = exports.createClientWithOAuth = exports.createClient = exports.getAuthToken = exports.getApiToken = exports.IN_PROGRESS_TEST_RUN_STATUS = exports.getIsLocked = exports.emitTelemetry = exports.getLatestTestRunResults = exports.getTestRunReplayDiffs = exports.getTestRunData = exports.getTestRun = exports.executeSecureTunnelTestRun = exports.getPrDiff = exports.getReplayDiff = exports.postSessionIdNotification = exports.getRecordingCommandId = exports.getRecordedSessionData = exports.getRecordedSession = exports.getReplayV3DownloadUrls = exports.getReplayDownloadUrl = exports.getReplay = exports.getRepoUrl = exports.getProject = exports.getWhoami = exports.trackAgentFeatureUsage = exports.getTimelineDiff = exports.getScreenshotUrls = exports.getScreenshotDomDiff = exports.getTestRunDiffsSummary = exports.getStructuredSessionData = void 0;
19
+ exports.getContainerDeployment = exports.downloadProjectDeployment = exports.completeContainerUpload = exports.completeAssetUpload = exports.requestGitDiffUpload = exports.requestUploadPart = exports.requestMultipartAssetUpload = exports.requestAssetUpload = exports.retryTransientUploadErrors = exports.isTransientUploadError = exports.UploadError = exports.putFileToSignedUrl = exports.getProxyAgent = exports.clearOAuthTokens = exports.getValidAccessToken = exports.performOAuthLogin = exports.makeRequest = exports.isInteractiveContext = exports.createClientWithOAuth = exports.createClient = exports.getAuthToken = exports.getApiToken = exports.IN_PROGRESS_TEST_RUN_STATUS = exports.getIsLocked = exports.emitTelemetry = exports.getLatestTestRunResults = exports.getTestRunReplayDiffs = exports.getTestRunData = exports.getTestRun = exports.executeSecureTunnelTestRun = exports.getPrDiff = exports.getReplayDiff = exports.postSessionIdNotification = exports.getRecordingCommandId = exports.getRecordedSessionData = exports.getRecordedSession = exports.getReplayV3DownloadUrls = exports.getReplayDownloadUrl = exports.getReplay = exports.requestSourceCodeUploadUrl = exports.getSourceArchiveUrl = exports.getRepoUrl = exports.getProject = exports.getWhoami = exports.trackAgentFeatureUsage = exports.getTimelineDiff = exports.getScreenshotUrls = exports.getScreenshotDomDiff = exports.getTestRunDiffsSummary = exports.getStructuredSessionData = void 0;
20
+ exports.getRelevantSessions = exports.isFetchError = exports.getRegistryAuth = void 0;
20
21
  var agent_api_1 = require("./api/agent.api");
21
22
  Object.defineProperty(exports, "getStructuredSessionData", { enumerable: true, get: function () { return agent_api_1.getStructuredSessionData; } });
22
23
  Object.defineProperty(exports, "getTestRunDiffsSummary", { enumerable: true, get: function () { return agent_api_1.getTestRunDiffsSummary; } });
@@ -30,6 +31,8 @@ Object.defineProperty(exports, "getWhoami", { enumerable: true, get: function ()
30
31
  var project_api_1 = require("./api/project.api");
31
32
  Object.defineProperty(exports, "getProject", { enumerable: true, get: function () { return project_api_1.getProject; } });
32
33
  Object.defineProperty(exports, "getRepoUrl", { enumerable: true, get: function () { return project_api_1.getRepoUrl; } });
34
+ Object.defineProperty(exports, "getSourceArchiveUrl", { enumerable: true, get: function () { return project_api_1.getSourceArchiveUrl; } });
35
+ Object.defineProperty(exports, "requestSourceCodeUploadUrl", { enumerable: true, get: function () { return project_api_1.requestSourceCodeUploadUrl; } });
33
36
  var replay_api_1 = require("./api/replay.api");
34
37
  Object.defineProperty(exports, "getReplay", { enumerable: true, get: function () { return replay_api_1.getReplay; } });
35
38
  Object.defineProperty(exports, "getReplayDownloadUrl", { enumerable: true, get: function () { return replay_api_1.getReplayDownloadUrl; } });
@@ -70,6 +73,12 @@ var oauth_token_store_1 = require("./oauth/oauth-token-store");
70
73
  Object.defineProperty(exports, "clearOAuthTokens", { enumerable: true, get: function () { return oauth_token_store_1.clearOAuthTokens; } });
71
74
  var get_proxy_agent_1 = require("./utils/get-proxy-agent");
72
75
  Object.defineProperty(exports, "getProxyAgent", { enumerable: true, get: function () { return get_proxy_agent_1.getProxyAgent; } });
76
+ var put_file_to_signed_url_1 = require("./utils/put-file-to-signed-url");
77
+ Object.defineProperty(exports, "putFileToSignedUrl", { enumerable: true, get: function () { return put_file_to_signed_url_1.putFileToSignedUrl; } });
78
+ var retry_transient_upload_errors_1 = require("./utils/retry-transient-upload-errors");
79
+ Object.defineProperty(exports, "UploadError", { enumerable: true, get: function () { return retry_transient_upload_errors_1.UploadError; } });
80
+ Object.defineProperty(exports, "isTransientUploadError", { enumerable: true, get: function () { return retry_transient_upload_errors_1.isTransientUploadError; } });
81
+ Object.defineProperty(exports, "retryTransientUploadErrors", { enumerable: true, get: function () { return retry_transient_upload_errors_1.retryTransientUploadErrors; } });
73
82
  var project_deployments_api_1 = require("./api/project-deployments.api");
74
83
  Object.defineProperty(exports, "requestAssetUpload", { enumerable: true, get: function () { return project_deployments_api_1.requestAssetUpload; } });
75
84
  Object.defineProperty(exports, "requestMultipartAssetUpload", { enumerable: true, get: function () { return project_deployments_api_1.requestMultipartAssetUpload; } });
@@ -86,4 +95,4 @@ Object.defineProperty(exports, "isFetchError", { enumerable: true, get: function
86
95
  var local_changes_api_1 = require("./api/local-changes.api");
87
96
  Object.defineProperty(exports, "getRelevantSessions", { enumerable: true, get: function () { return local_changes_api_1.getRelevantSessions; } });
88
97
  //# sourceMappingURL=index.js.map
89
- //# debugId=787e56fc-127a-5a89-b852-a67e125e370c
98
+ //# debugId=c4f4b9c9-8243-5016-b0bf-99f3499377d5
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["../src/index.ts"],"sourceRoot":"","names":[],"mappings":";;;;;;;;;;;;;;;;;;;AAAA,6CAkByB;AANvB,qHAAA,wBAAwB,OAAA;AACxB,mHAAA,sBAAsB,OAAA;AACtB,iHAAA,oBAAoB,OAAA;AACpB,8GAAA,iBAAiB,OAAA;AACjB,4GAAA,eAAe,OAAA;AACf,mHAAA,sBAAsB,OAAA;AAExB,gEAA8C;AAC9C,6CAA4D;AAAnC,sGAAA,SAAS,OAAA;AAClC,iDAA2D;AAAlD,yGAAA,UAAU,OAAA;AAAE,yGAAA,UAAU,OAAA;AAC/B,+CAK0B;AAHxB,uGAAA,SAAS,OAAA;AACT,kHAAA,oBAAoB,OAAA;AACpB,qHAAA,uBAAuB,OAAA;AAEzB,iDAK2B;AAJzB,iHAAA,kBAAkB,OAAA;AAClB,qHAAA,sBAAsB,OAAA;AACtB,oHAAA,qBAAqB,OAAA;AACrB,wHAAA,yBAAyB,OAAA;AAE3B,yDAA0E;AAA7C,gHAAA,aAAa,OAAA;AAC1C,yDAAkD;AAAzC,4GAAA,SAAS,OAAA;AAClB,mDAU4B;AAR1B,0HAAA,0BAA0B,OAAA;AAC1B,0GAAA,UAAU,OAAA;AACV,8GAAA,cAAc,OAAA;AACd,qHAAA,qBAAqB,OAAA;AAErB,uHAAA,uBAAuB,OAAA;AAEvB,6GAAA,aAAa,OAAA;AAEf,iEAA4E;AAA/C,kHAAA,WAAW,OAAA;AACxC,+DAAuE;AAA9D,iIAAA,2BAA2B,OAAA;AACpC,qDAA8D;AAArD,8GAAA,WAAW,OAAA;AAAE,+GAAA,YAAY,OAAA;AAClC,mCAMkB;AAJhB,sGAAA,YAAY,OAAA;AACZ,+GAAA,qBAAqB,OAAA;AACrB,8GAAA,oBAAoB,OAAA;AACpB,qGAAA,WAAW,OAAA;AAEb,mDAAwD;AAA/C,gHAAA,iBAAiB,OAAA;AAC1B,uDAA4D;AAAnD,oHAAA,mBAAmB,OAAA;AAC5B,+DAA6D;AAApD,qHAAA,gBAAgB,OAAA;AAEzB,2DAAwD;AAA/C,gHAAA,aAAa,OAAA;AACtB,yEAwBuC;AArBrC,6HAAA,kBAAkB,OAAA;AAClB,sIAAA,2BAA2B,OAAA;AAI3B,4HAAA,iBAAiB,OAAA;AAGjB,+HAAA,oBAAoB,OAAA;AAGpB,8HAAA,mBAAmB,OAAA;AAGnB,kIAAA,uBAAuB,OAAA;AAGvB,oIAAA,yBAAyB,OAAA;AAEzB,iIAAA,sBAAsB,OAAA;AAGxB,mDAA8E;AAA5C,+GAAA,eAAe,OAAA;AACjD,mCAAwC;AAA/B,sGAAA,YAAY,OAAA;AACrB,6DAMiC;AAD/B,wHAAA,mBAAmB,OAAA","debugId":"787e56fc-127a-5a89-b852-a67e125e370c"}
1
+ {"version":3,"file":"index.js","sources":["../src/index.ts"],"sourceRoot":"","names":[],"mappings":";;;;;;;;;;;;;;;;;;;;AAAA,6CAkByB;AANvB,qHAAA,wBAAwB,OAAA;AACxB,mHAAA,sBAAsB,OAAA;AACtB,iHAAA,oBAAoB,OAAA;AACpB,8GAAA,iBAAiB,OAAA;AACjB,4GAAA,eAAe,OAAA;AACf,mHAAA,sBAAsB,OAAA;AAExB,gEAA8C;AAC9C,6CAA4D;AAAnC,sGAAA,SAAS,OAAA;AAClC,iDAW2B;AARzB,yGAAA,UAAU,OAAA;AACV,yGAAA,UAAU,OAAA;AAGV,kHAAA,mBAAmB,OAAA;AAGnB,yHAAA,0BAA0B,OAAA;AAE5B,+CAK0B;AAHxB,uGAAA,SAAS,OAAA;AACT,kHAAA,oBAAoB,OAAA;AACpB,qHAAA,uBAAuB,OAAA;AAEzB,iDAK2B;AAJzB,iHAAA,kBAAkB,OAAA;AAClB,qHAAA,sBAAsB,OAAA;AACtB,oHAAA,qBAAqB,OAAA;AACrB,wHAAA,yBAAyB,OAAA;AAE3B,yDAA0E;AAA7C,gHAAA,aAAa,OAAA;AAC1C,yDAAkD;AAAzC,4GAAA,SAAS,OAAA;AAClB,mDAU4B;AAR1B,0HAAA,0BAA0B,OAAA;AAC1B,0GAAA,UAAU,OAAA;AACV,8GAAA,cAAc,OAAA;AACd,qHAAA,qBAAqB,OAAA;AAErB,uHAAA,uBAAuB,OAAA;AAEvB,6GAAA,aAAa,OAAA;AAEf,iEAA4E;AAA/C,kHAAA,WAAW,OAAA;AACxC,+DAAuE;AAA9D,iIAAA,2BAA2B,OAAA;AACpC,qDAA8D;AAArD,8GAAA,WAAW,OAAA;AAAE,+GAAA,YAAY,OAAA;AAClC,mCAMkB;AAJhB,sGAAA,YAAY,OAAA;AACZ,+GAAA,qBAAqB,OAAA;AACrB,8GAAA,oBAAoB,OAAA;AACpB,qGAAA,WAAW,OAAA;AAEb,mDAAwD;AAA/C,gHAAA,iBAAiB,OAAA;AAC1B,uDAA4D;AAAnD,oHAAA,mBAAmB,OAAA;AAC5B,+DAA6D;AAApD,qHAAA,gBAAgB,OAAA;AAEzB,2DAAwD;AAA/C,gHAAA,aAAa,OAAA;AACtB,yEAGwC;AADtC,4HAAA,kBAAkB,OAAA;AAEpB,uFAK+C;AAJ7C,4HAAA,WAAW,OAAA;AACX,uIAAA,sBAAsB,OAAA;AACtB,2IAAA,0BAA0B,OAAA;AAG5B,yEAwBuC;AArBrC,6HAAA,kBAAkB,OAAA;AAClB,sIAAA,2BAA2B,OAAA;AAI3B,4HAAA,iBAAiB,OAAA;AAGjB,+HAAA,oBAAoB,OAAA;AAGpB,8HAAA,mBAAmB,OAAA;AAGnB,kIAAA,uBAAuB,OAAA;AAGvB,oIAAA,yBAAyB,OAAA;AAEzB,iIAAA,sBAAsB,OAAA;AAGxB,mDAA8E;AAA5C,+GAAA,eAAe,OAAA;AACjD,mCAAwC;AAA/B,sGAAA,YAAY,OAAA;AACrB,6DAMiC;AAD/B,wHAAA,mBAAmB,OAAA","debugId":"c4f4b9c9-8243-5016-b0bf-99f3499377d5"}
@@ -0,0 +1,168 @@
1
+ "use strict";
2
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="3aeafafa-540d-5ca2-a28d-ccf0a9bd2a21")}catch(e){}}();
3
+
4
+ Object.defineProperty(exports, "__esModule", { value: true });
5
+ const vitest_1 = require("vitest");
6
+ const retry_transient_upload_errors_1 = require("../retry-transient-upload-errors");
7
+ (0, vitest_1.describe)("retryTransientUploadErrors", () => {
8
+ const noSleep = async () => { };
9
+ (0, vitest_1.it)("returns the value when the operation succeeds on the first attempt", async () => {
10
+ const operation = vitest_1.vi.fn(async () => "ok");
11
+ const result = await (0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, {
12
+ sleep: noSleep,
13
+ });
14
+ (0, vitest_1.expect)(result).toBe("ok");
15
+ (0, vitest_1.expect)(operation).toHaveBeenCalledTimes(1);
16
+ });
17
+ (0, vitest_1.it)("retries on 503 SlowDown and eventually succeeds", async () => {
18
+ let attempts = 0;
19
+ const operation = async () => {
20
+ attempts++;
21
+ if (attempts < 3) {
22
+ throw new retry_transient_upload_errors_1.UploadError(503, "<Code>SlowDown</Code>");
23
+ }
24
+ return "ok";
25
+ };
26
+ const result = await (0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, {
27
+ sleep: noSleep,
28
+ });
29
+ (0, vitest_1.expect)(result).toBe("ok");
30
+ (0, vitest_1.expect)(attempts).toBe(3);
31
+ });
32
+ (0, vitest_1.it)("retries on 500 InternalError", async () => {
33
+ let attempts = 0;
34
+ const operation = async () => {
35
+ attempts++;
36
+ if (attempts < 2) {
37
+ throw new retry_transient_upload_errors_1.UploadError(500, "<Code>InternalError</Code>");
38
+ }
39
+ return "ok";
40
+ };
41
+ const result = await (0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, {
42
+ sleep: noSleep,
43
+ });
44
+ (0, vitest_1.expect)(result).toBe("ok");
45
+ (0, vitest_1.expect)(attempts).toBe(2);
46
+ });
47
+ (0, vitest_1.it)("retries on 429 Too Many Requests", async () => {
48
+ let attempts = 0;
49
+ const operation = async () => {
50
+ attempts++;
51
+ if (attempts < 2) {
52
+ throw new retry_transient_upload_errors_1.UploadError(429, "");
53
+ }
54
+ return "ok";
55
+ };
56
+ const result = await (0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, {
57
+ sleep: noSleep,
58
+ });
59
+ (0, vitest_1.expect)(attempts).toBe(2);
60
+ (0, vitest_1.expect)(result).toBe("ok");
61
+ });
62
+ (0, vitest_1.it)("retries on transient network errors like ECONNRESET", async () => {
63
+ let attempts = 0;
64
+ const operation = async () => {
65
+ attempts++;
66
+ if (attempts < 2) {
67
+ const err = new Error("socket hang up");
68
+ err.code = "ECONNRESET";
69
+ throw err;
70
+ }
71
+ return "ok";
72
+ };
73
+ const result = await (0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, {
74
+ sleep: noSleep,
75
+ });
76
+ (0, vitest_1.expect)(attempts).toBe(2);
77
+ (0, vitest_1.expect)(result).toBe("ok");
78
+ });
79
+ (0, vitest_1.it)("does not retry on 4xx client errors (e.g. 403 Forbidden)", async () => {
80
+ const operation = vitest_1.vi.fn(async () => {
81
+ throw new retry_transient_upload_errors_1.UploadError(403, "<Code>AccessDenied</Code>");
82
+ });
83
+ await (0, vitest_1.expect)((0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, { sleep: noSleep })).rejects.toBeInstanceOf(retry_transient_upload_errors_1.UploadError);
84
+ (0, vitest_1.expect)(operation).toHaveBeenCalledTimes(1);
85
+ });
86
+ (0, vitest_1.it)("does not retry on arbitrary non-transient errors", async () => {
87
+ const operation = vitest_1.vi.fn(async () => {
88
+ throw new Error("something unrelated");
89
+ });
90
+ await (0, vitest_1.expect)((0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, { sleep: noSleep })).rejects.toThrow("something unrelated");
91
+ (0, vitest_1.expect)(operation).toHaveBeenCalledTimes(1);
92
+ });
93
+ (0, vitest_1.it)("throws the last error after exhausting retries", async () => {
94
+ const operation = vitest_1.vi.fn(async () => {
95
+ throw new retry_transient_upload_errors_1.UploadError(503, "<Code>SlowDown</Code>");
96
+ });
97
+ await (0, vitest_1.expect)((0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, {
98
+ sleep: noSleep,
99
+ maxAttempts: 3,
100
+ })).rejects.toBeInstanceOf(retry_transient_upload_errors_1.UploadError);
101
+ (0, vitest_1.expect)(operation).toHaveBeenCalledTimes(3);
102
+ });
103
+ (0, vitest_1.it)("applies exponential backoff with jitter between retries", async () => {
104
+ const delays = [];
105
+ const sleep = async (ms) => {
106
+ delays.push(ms);
107
+ };
108
+ let attempts = 0;
109
+ const operation = async () => {
110
+ attempts++;
111
+ if (attempts < 4) {
112
+ throw new retry_transient_upload_errors_1.UploadError(503, "");
113
+ }
114
+ return "ok";
115
+ };
116
+ // Make jitter deterministic
117
+ const randomSpy = vitest_1.vi.spyOn(Math, "random").mockReturnValue(0.5);
118
+ try {
119
+ await (0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, {
120
+ sleep,
121
+ baseDelayMs: 100,
122
+ });
123
+ }
124
+ finally {
125
+ randomSpy.mockRestore();
126
+ }
127
+ // With Math.random() = 0.5, jitter multiplier = 0.5 + 0.5 = 1.0
128
+ // So delays should be: 100, 200, 400
129
+ (0, vitest_1.expect)(delays).toEqual([100, 200, 400]);
130
+ });
131
+ (0, vitest_1.it)("invokes onRetry with attempt number and error before sleeping", async () => {
132
+ const onRetry = vitest_1.vi.fn();
133
+ let attempts = 0;
134
+ const operation = async () => {
135
+ attempts++;
136
+ if (attempts < 3) {
137
+ throw new retry_transient_upload_errors_1.UploadError(503, "");
138
+ }
139
+ return "ok";
140
+ };
141
+ await (0, retry_transient_upload_errors_1.retryTransientUploadErrors)(operation, {
142
+ sleep: noSleep,
143
+ onRetry,
144
+ });
145
+ (0, vitest_1.expect)(onRetry).toHaveBeenCalledTimes(2);
146
+ (0, vitest_1.expect)(onRetry).toHaveBeenNthCalledWith(1, 1, vitest_1.expect.any(retry_transient_upload_errors_1.UploadError));
147
+ (0, vitest_1.expect)(onRetry).toHaveBeenNthCalledWith(2, 2, vitest_1.expect.any(retry_transient_upload_errors_1.UploadError));
148
+ });
149
+ });
150
+ (0, vitest_1.describe)("UploadError", () => {
151
+ (0, vitest_1.it)("exposes the status code and response body", () => {
152
+ const error = new retry_transient_upload_errors_1.UploadError(503, "<Code>SlowDown</Code>");
153
+ (0, vitest_1.expect)(error.statusCode).toBe(503);
154
+ (0, vitest_1.expect)(error.responseBody).toBe("<Code>SlowDown</Code>");
155
+ });
156
+ (0, vitest_1.it)("formats the message so existing logs remain readable", () => {
157
+ const error = new retry_transient_upload_errors_1.UploadError(503, "<Code>SlowDown</Code>");
158
+ (0, vitest_1.expect)(error.message).toContain("Failed to upload!");
159
+ (0, vitest_1.expect)(error.message).toContain("Status 503");
160
+ (0, vitest_1.expect)(error.message).toContain("<Code>SlowDown</Code>");
161
+ });
162
+ (0, vitest_1.it)("is an instance of Error", () => {
163
+ const error = new retry_transient_upload_errors_1.UploadError(500, "");
164
+ (0, vitest_1.expect)(error).toBeInstanceOf(Error);
165
+ });
166
+ });
167
+ //# sourceMappingURL=retry-transient-upload-errors.spec.js.map
168
+ //# debugId=3aeafafa-540d-5ca2-a28d-ccf0a9bd2a21
@@ -0,0 +1 @@
1
+ {"version":3,"file":"retry-transient-upload-errors.spec.js","sources":["../../../src/utils/__tests__/retry-transient-upload-errors.spec.ts"],"sourceRoot":"","names":[],"mappings":"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","debugId":"3aeafafa-540d-5ca2-a28d-ccf0a9bd2a21"}
@@ -0,0 +1,18 @@
1
+ export interface PutFileToSignedUrlOptions {
2
+ filePath: string;
3
+ signedUrl: string;
4
+ size: number;
5
+ contentType: string;
6
+ }
7
+ /**
8
+ * Streams `filePath` to `signedUrl` via an HTTPS PUT.
9
+ *
10
+ * Uses Node's built-in `https.request` rather than `fetch` so that we
11
+ * (a) honour `HTTPS_PROXY` via `getProxyAgent()` for customers behind
12
+ * corporate proxies and (b) avoid relying on `fetch`'s `duplex: "half"`
13
+ * streaming support, which is fragile across Node 18.x patch versions.
14
+ *
15
+ * Rejects with `UploadError` for non-200 responses so callers can pair
16
+ * this with `retryTransientUploadErrors`.
17
+ */
18
+ export declare const putFileToSignedUrl: ({ filePath, signedUrl, size, contentType, }: PutFileToSignedUrlOptions) => Promise<void>;
@@ -0,0 +1,58 @@
1
+ "use strict";
2
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="2ace32ed-bc6c-58a2-8d61-e7cc107dc6a8")}catch(e){}}();
3
+
4
+ Object.defineProperty(exports, "__esModule", { value: true });
5
+ exports.putFileToSignedUrl = void 0;
6
+ const fs_1 = require("fs");
7
+ const https_1 = require("https");
8
+ const get_proxy_agent_1 = require("./get-proxy-agent");
9
+ const retry_transient_upload_errors_1 = require("./retry-transient-upload-errors");
10
+ /**
11
+ * Streams `filePath` to `signedUrl` via an HTTPS PUT.
12
+ *
13
+ * Uses Node's built-in `https.request` rather than `fetch` so that we
14
+ * (a) honour `HTTPS_PROXY` via `getProxyAgent()` for customers behind
15
+ * corporate proxies and (b) avoid relying on `fetch`'s `duplex: "half"`
16
+ * streaming support, which is fragile across Node 18.x patch versions.
17
+ *
18
+ * Rejects with `UploadError` for non-200 responses so callers can pair
19
+ * this with `retryTransientUploadErrors`.
20
+ */
21
+ const putFileToSignedUrl = async ({ filePath, signedUrl, size, contentType, }) => {
22
+ return new Promise((resolve, reject) => {
23
+ // A new read stream is required on every attempt — streams cannot be replayed.
24
+ const fileStream = (0, fs_1.createReadStream)(filePath);
25
+ const req = (0, https_1.request)(signedUrl, {
26
+ agent: (0, get_proxy_agent_1.getProxyAgent)(),
27
+ method: "PUT",
28
+ headers: {
29
+ "Content-Length": size,
30
+ "Content-Type": contentType,
31
+ },
32
+ }, (response) => {
33
+ let responseData = "";
34
+ response.on("data", (chunk) => {
35
+ responseData += chunk;
36
+ });
37
+ response.on("end", () => {
38
+ if (response.statusCode === 200) {
39
+ resolve();
40
+ }
41
+ else {
42
+ reject(new retry_transient_upload_errors_1.UploadError(response.statusCode ?? 0, responseData));
43
+ }
44
+ });
45
+ });
46
+ req.on("error", (error) => {
47
+ reject(error);
48
+ });
49
+ fileStream.on("error", (error) => {
50
+ req.destroy(error);
51
+ reject(error);
52
+ });
53
+ fileStream.pipe(req);
54
+ });
55
+ };
56
+ exports.putFileToSignedUrl = putFileToSignedUrl;
57
+ //# sourceMappingURL=put-file-to-signed-url.js.map
58
+ //# debugId=2ace32ed-bc6c-58a2-8d61-e7cc107dc6a8
@@ -0,0 +1 @@
1
+ {"version":3,"file":"put-file-to-signed-url.js","sources":["../../src/utils/put-file-to-signed-url.ts"],"sourceRoot":"","names":[],"mappings":";;;;;AAAA,2BAAsC;AAEtC,iCAAgD;AAChD,uDAAkD;AAClD,mFAA8D;AAS9D;;;;;;;;;;GAUG;AACI,MAAM,kBAAkB,GAAG,KAAK,EAAE,EACvC,QAAQ,EACR,SAAS,EACT,IAAI,EACJ,WAAW,GACe,EAAiB,EAAE;IAC7C,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,MAAM,EAAE,EAAE;QACrC,+EAA+E;QAC/E,MAAM,UAAU,GAAG,IAAA,qBAAgB,EAAC,QAAQ,CAAC,CAAC;QAC9C,MAAM,GAAG,GAAG,IAAA,eAAY,EACtB,SAAS,EACT;YACE,KAAK,EAAE,IAAA,+BAAa,GAAE;YACtB,MAAM,EAAE,KAAK;YACb,OAAO,EAAE;gBACP,gBAAgB,EAAE,IAAI;gBACtB,cAAc,EAAE,WAAW;aAC5B;SACF,EACD,CAAC,QAAyB,EAAE,EAAE;YAC5B,IAAI,YAAY,GAAG,EAAE,CAAC;YAEtB,QAAQ,CAAC,EAAE,CAAC,MAAM,EAAE,CAAC,KAAK,EAAE,EAAE;gBAC5B,YAAY,IAAI,KAAK,CAAC;YACxB,CAAC,CAAC,CAAC;YAEH,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,GAAG,EAAE;gBACtB,IAAI,QAAQ,CAAC,UAAU,KAAK,GAAG,EAAE,CAAC;oBAChC,OAAO,EAAE,CAAC;gBACZ,CAAC;qBAAM,CAAC;oBACN,MAAM,CAAC,IAAI,2CAAW,CAAC,QAAQ,CAAC,UAAU,IAAI,CAAC,EAAE,YAAY,CAAC,CAAC,CAAC;gBAClE,CAAC;YACH,CAAC,CAAC,CAAC;QACL,CAAC,CACF,CAAC;QAEF,GAAG,CAAC,EAAE,CAAC,OAAO,EAAE,CAAC,KAAK,EAAE,EAAE;YACxB,MAAM,CAAC,KAAK,CAAC,CAAC;QAChB,CAAC,CAAC,CAAC;QAEH,UAAU,CAAC,EAAE,CAAC,OAAO,EAAE,CAAC,KAAK,EAAE,EAAE;YAC/B,GAAG,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;YACnB,MAAM,CAAC,KAAK,CAAC,CAAC;QAChB,CAAC,CAAC,CAAC;QAEH,UAAU,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IACvB,CAAC,CAAC,CAAC;AACL,CAAC,CAAC;AA/CW,QAAA,kBAAkB,sBA+C7B","debugId":"2ace32ed-bc6c-58a2-8d61-e7cc107dc6a8"}
@@ -0,0 +1,13 @@
1
+ export declare class UploadError extends Error {
2
+ readonly statusCode: number;
3
+ readonly responseBody: string;
4
+ constructor(statusCode: number, responseBody: string);
5
+ }
6
+ export declare const isTransientUploadError: (error: unknown) => boolean;
7
+ export interface RetryTransientUploadErrorsOptions {
8
+ maxAttempts?: number;
9
+ baseDelayMs?: number;
10
+ onRetry?: (attempt: number, error: unknown) => void;
11
+ sleep?: (ms: number) => Promise<void>;
12
+ }
13
+ export declare const retryTransientUploadErrors: <T>(operation: () => Promise<T>, options?: RetryTransientUploadErrorsOptions) => Promise<T>;
@@ -0,0 +1,73 @@
1
+ "use strict";
2
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="a5523637-fe92-513e-a53e-f2a08a935232")}catch(e){}}();
3
+
4
+ Object.defineProperty(exports, "__esModule", { value: true });
5
+ exports.retryTransientUploadErrors = exports.isTransientUploadError = exports.UploadError = void 0;
6
+ class UploadError extends Error {
7
+ statusCode;
8
+ responseBody;
9
+ constructor(statusCode, responseBody) {
10
+ super(`Failed to upload!\nStatus ${statusCode}.\nResponse:\n${responseBody}`);
11
+ this.name = "UploadError";
12
+ this.statusCode = statusCode;
13
+ this.responseBody = responseBody;
14
+ }
15
+ }
16
+ exports.UploadError = UploadError;
17
+ const TRANSIENT_STATUS_CODES = new Set([429, 500, 502, 503, 504]);
18
+ // Node networking errors that are safe to retry. Upload endpoints (e.g. S3)
19
+ // occasionally reset connections under load; these show up here rather than
20
+ // as HTTP errors. Excludes ECONNREFUSED and ENOTFOUND because those typically
21
+ // indicate misconfiguration rather than transient failures (EAI_AGAIN covers
22
+ // the transient-DNS case).
23
+ const TRANSIENT_NETWORK_ERROR_CODES = new Set([
24
+ "ECONNRESET",
25
+ "ETIMEDOUT",
26
+ "ECONNABORTED",
27
+ "EAI_AGAIN",
28
+ "EPIPE",
29
+ ]);
30
+ const isTransientUploadError = (error) => {
31
+ if (error instanceof UploadError) {
32
+ return TRANSIENT_STATUS_CODES.has(error.statusCode);
33
+ }
34
+ if (error && typeof error === "object" && "code" in error) {
35
+ const code = error.code;
36
+ if (typeof code === "string" && TRANSIENT_NETWORK_ERROR_CODES.has(code)) {
37
+ return true;
38
+ }
39
+ }
40
+ return false;
41
+ };
42
+ exports.isTransientUploadError = isTransientUploadError;
43
+ const DEFAULT_MAX_ATTEMPTS = 5;
44
+ const DEFAULT_BASE_DELAY_MS = 200;
45
+ const MAX_DELAY_MS = 30_000;
46
+ const defaultSleep = (ms) => new Promise((resolve) => setTimeout(resolve, ms));
47
+ const retryTransientUploadErrors = async (operation, options = {}) => {
48
+ const maxAttempts = options.maxAttempts ?? DEFAULT_MAX_ATTEMPTS;
49
+ const baseDelayMs = options.baseDelayMs ?? DEFAULT_BASE_DELAY_MS;
50
+ const sleep = options.sleep ?? defaultSleep;
51
+ let lastError;
52
+ for (let attempt = 1; attempt <= maxAttempts; attempt++) {
53
+ try {
54
+ return await operation();
55
+ }
56
+ catch (error) {
57
+ lastError = error;
58
+ if (!(0, exports.isTransientUploadError)(error) || attempt === maxAttempts) {
59
+ throw error;
60
+ }
61
+ // Exponential backoff with a jitter multiplier in [0.5, 1.5), capped
62
+ // to bound worst-case sleep when callers pass a large baseDelayMs.
63
+ const jitter = 0.5 + Math.random();
64
+ const delayMs = Math.min(Math.floor(baseDelayMs * Math.pow(2, attempt - 1) * jitter), MAX_DELAY_MS);
65
+ options.onRetry?.(attempt, error);
66
+ await sleep(delayMs);
67
+ }
68
+ }
69
+ throw lastError;
70
+ };
71
+ exports.retryTransientUploadErrors = retryTransientUploadErrors;
72
+ //# sourceMappingURL=retry-transient-upload-errors.js.map
73
+ //# debugId=a5523637-fe92-513e-a53e-f2a08a935232
@@ -0,0 +1 @@
1
+ {"version":3,"file":"retry-transient-upload-errors.js","sources":["../../src/utils/retry-transient-upload-errors.ts"],"sourceRoot":"","names":[],"mappings":"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","debugId":"a5523637-fe92-513e-a53e-f2a08a935232"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@alwaysmeticulous/client",
3
- "version": "2.276.2",
3
+ "version": "2.280.0",
4
4
  "description": "Helper methods for using the Meticulous backend API",
5
5
  "license": "ISC",
6
6
  "main": "dist/index.js",
@@ -20,8 +20,8 @@
20
20
  "test": "vitest run --passWithNoTests"
21
21
  },
22
22
  "dependencies": {
23
- "@alwaysmeticulous/api": "2.276.2",
24
- "@alwaysmeticulous/common": "2.276.2",
23
+ "@alwaysmeticulous/api": "2.280.0",
24
+ "@alwaysmeticulous/common": "2.280.0",
25
25
  "loglevel": "^1.8.0",
26
26
  "proxy-agent": "^6.4.0",
27
27
  "undici": "^6.24.1"
@@ -46,5 +46,5 @@
46
46
  "devDependencies": {
47
47
  "vitest": "catalog:"
48
48
  },
49
- "gitHead": "01bc1fa14391f4a39322c7a70e5f51b5ebb45032"
49
+ "gitHead": "87ca975a232d16ea878caa5649a8b21221ebca02"
50
50
  }