@verdaccio/store 9.0.0-next-9.21 → 9.0.0-next-9.23
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/build/filter-pipeline.d.ts +2 -2
- package/build/filter-pipeline.js.map +1 -1
- package/build/lib/publish-utils.d.ts +1 -1
- package/build/lib/publish-utils.js.map +1 -1
- package/build/lib/publish-utils.mjs.map +1 -1
- package/build/lib/storage-utils.d.ts +18 -18
- package/build/lib/storage-utils.js.map +1 -1
- package/build/lib/storage-utils.mjs.map +1 -1
- package/build/lib/versions-utils.d.ts +2 -2
- package/build/lib/versions-utils.js.map +1 -1
- package/build/lib/versions-utils.mjs.map +1 -1
- package/build/local-storage.d.ts +2 -2
- package/build/local-storage.js.map +1 -1
- package/build/storage.d.ts +7 -6
- package/build/storage.js +94 -68
- package/build/storage.js.map +1 -1
- package/build/storage.mjs +92 -69
- package/build/storage.mjs.map +1 -1
- package/build/type.d.ts +3 -3
- package/package.json +14 -14
package/build/storage.mjs
CHANGED
|
@@ -18,6 +18,9 @@ import Search from "@verdaccio/search";
|
|
|
18
18
|
import { convertDistRemoteToLocalTarballUrls, convertDistVersionToLocalTarballsUrl, getTarballDetails } from "@verdaccio/tarball";
|
|
19
19
|
//#region src/storage.ts
|
|
20
20
|
var debug = buildDebug("verdaccio:storage");
|
|
21
|
+
var noSuchFile = "ENOENT";
|
|
22
|
+
var resourceNotAvailable = "EAGAIN";
|
|
23
|
+
var PROTO_NAME = "__proto__";
|
|
21
24
|
var Storage = class {
|
|
22
25
|
localStorage;
|
|
23
26
|
filters;
|
|
@@ -164,85 +167,105 @@ var Storage = class {
|
|
|
164
167
|
if (cachedManifest?._distfiles && typeof cachedManifest?._distfiles[filename]?.url === "string") {
|
|
165
168
|
debug("dist file found, using it %o", cachedManifest?._distfiles[filename].url);
|
|
166
169
|
const distFile = cachedManifest._distfiles[filename];
|
|
167
|
-
|
|
168
|
-
let expected_length;
|
|
169
|
-
const passThroughRemoteStream = new PassThrough();
|
|
170
|
-
const proxy = this.getUpLinkForDistFile(name, distFile);
|
|
171
|
-
const remoteStream = proxy.fetchTarball(distFile.url, {});
|
|
172
|
-
remoteStream.on("request", async () => {
|
|
173
|
-
try {
|
|
174
|
-
debug("remote stream request");
|
|
175
|
-
const storage = this.getPrivatePackageStorage(name);
|
|
176
|
-
if (proxy.config.cache === true && storage) await pipeline(remoteStream, passThroughRemoteStream, await storage.writeTarball(filename, { signal }), { signal });
|
|
177
|
-
else await pipeline(remoteStream, passThroughRemoteStream, { signal });
|
|
178
|
-
} catch (err) {
|
|
179
|
-
debug("error on pipeline downloading tarball for package %o", name);
|
|
180
|
-
passThroughRemoteStream.emit("error", err);
|
|
181
|
-
}
|
|
182
|
-
});
|
|
183
|
-
remoteStream.on("response", async (res) => {
|
|
184
|
-
if (res.statusCode === HTTP_STATUS.NOT_FOUND) {
|
|
185
|
-
debug("remote stream response 404");
|
|
186
|
-
passThroughRemoteStream.emit("error", errorUtils.getNotFound(errorUtils.API_ERROR.NOT_FILE_UPLINK));
|
|
187
|
-
return;
|
|
188
|
-
}
|
|
189
|
-
if (res.statusCode === HTTP_STATUS.UNAUTHORIZED) {
|
|
190
|
-
debug("remote stream response 401");
|
|
191
|
-
passThroughRemoteStream.emit("error", errorUtils.getUnauthorized(errorUtils.API_ERROR.UNAUTHORIZED_ACCESS));
|
|
192
|
-
return;
|
|
193
|
-
}
|
|
194
|
-
if (!(res.statusCode >= HTTP_STATUS.OK && res.statusCode < HTTP_STATUS.MULTIPLE_CHOICES)) {
|
|
195
|
-
debug("remote stream response %o", res.statusCode);
|
|
196
|
-
passThroughRemoteStream.emit("error", errorUtils.getInternalError(`bad uplink status code: ${res.statusCode}`));
|
|
197
|
-
return;
|
|
198
|
-
}
|
|
199
|
-
if (res.headers[HEADER_TYPE.CONTENT_LENGTH]) {
|
|
200
|
-
expected_length = res.headers[HEADER_TYPE.CONTENT_LENGTH];
|
|
201
|
-
debug("remote stream response content length %o", expected_length);
|
|
202
|
-
passThroughRemoteStream.emit(HEADER_TYPE.CONTENT_LENGTH, res.headers[HEADER_TYPE.CONTENT_LENGTH]);
|
|
203
|
-
}
|
|
204
|
-
}).on("downloadProgress", (progress) => {
|
|
205
|
-
current_length = progress.transferred;
|
|
206
|
-
if (typeof expected_length === "undefined" && progress.total) expected_length = progress.total;
|
|
207
|
-
}).on("end", () => {
|
|
208
|
-
if (expected_length && current_length != expected_length) {
|
|
209
|
-
debug("stream end, but length mismatch %o %o", current_length, expected_length);
|
|
210
|
-
passThroughRemoteStream.emit("error", errorUtils.getInternalError(API_ERROR.CONTENT_MISMATCH));
|
|
211
|
-
}
|
|
212
|
-
debug("remote stream end");
|
|
213
|
-
}).on("error", (err) => {
|
|
214
|
-
debug("remote stream error %o", err);
|
|
215
|
-
passThroughRemoteStream.emit("error", err);
|
|
216
|
-
});
|
|
217
|
-
return passThroughRemoteStream;
|
|
170
|
+
return this.fetchTarballFromDistFile(name, filename, distFile, { signal });
|
|
218
171
|
} else {
|
|
219
172
|
debug("dist file not found, proceed update upstream");
|
|
220
|
-
const passThroughRemoteStream = new PassThrough();
|
|
221
173
|
const [updatedManifest] = await this.syncUplinksMetadata(name, cachedManifest, { uplinksLook: true });
|
|
222
174
|
const distFile = updatedManifest?._distfiles?.[filename];
|
|
223
175
|
if (updatedManifest === null || !distFile) {
|
|
224
176
|
debug("remote tarball not found");
|
|
225
177
|
throw errorUtils.getNotFound(API_ERROR.NO_SUCH_FILE);
|
|
226
178
|
}
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
179
|
+
return this.fetchTarballFromDistFile(name, filename, distFile, { signal });
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
fetchTarballFromDistFile(name, filename, distFile, { signal }) {
|
|
183
|
+
let current_length = 0;
|
|
184
|
+
let expected_length;
|
|
185
|
+
let uplinkStatusError = null;
|
|
186
|
+
const passThroughRemoteStream = new PassThrough();
|
|
187
|
+
const proxy = this.getUpLinkForDistFile(name, distFile);
|
|
188
|
+
const remoteStream = proxy.fetchTarball(distFile.url, { throwHttpErrors: false });
|
|
189
|
+
const readRemoteBody = () => new Promise((resolve) => {
|
|
190
|
+
const chunks = [];
|
|
191
|
+
remoteStream.on("data", (chunk) => chunks.push(chunk));
|
|
192
|
+
remoteStream.once("end", () => {
|
|
193
|
+
const raw = Buffer.concat(chunks);
|
|
194
|
+
if (raw.length === 0) {
|
|
195
|
+
resolve(void 0);
|
|
196
|
+
return;
|
|
197
|
+
}
|
|
230
198
|
try {
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
await pipeline(remoteStream, passThroughRemoteStream, await storage.writeTarball(filename, { signal }), { signal });
|
|
235
|
-
} else {
|
|
236
|
-
debug("cache remote tarball disabled");
|
|
237
|
-
await pipeline(remoteStream, passThroughRemoteStream, { signal });
|
|
238
|
-
}
|
|
239
|
-
} catch (err) {
|
|
240
|
-
debug("error on pipeline downloading tarball for package %o", name);
|
|
241
|
-
passThroughRemoteStream.emit("error", err);
|
|
199
|
+
resolve(JSON.parse(raw.toString("utf8")));
|
|
200
|
+
} catch {
|
|
201
|
+
resolve(void 0);
|
|
242
202
|
}
|
|
243
203
|
});
|
|
244
|
-
|
|
245
|
-
}
|
|
204
|
+
remoteStream.once("error", () => resolve(void 0));
|
|
205
|
+
});
|
|
206
|
+
remoteStream.on("response", async (res) => {
|
|
207
|
+
if (res.statusCode === HTTP_STATUS.NOT_FOUND) {
|
|
208
|
+
debug("remote stream response 404");
|
|
209
|
+
remoteStream.resume();
|
|
210
|
+
uplinkStatusError = errorUtils.getNotFound(errorUtils.API_ERROR.NOT_FILE_UPLINK);
|
|
211
|
+
passThroughRemoteStream.emit("error", uplinkStatusError);
|
|
212
|
+
return;
|
|
213
|
+
}
|
|
214
|
+
if (res.statusCode === HTTP_STATUS.UNAUTHORIZED) {
|
|
215
|
+
debug("remote stream response 401");
|
|
216
|
+
remoteStream.resume();
|
|
217
|
+
uplinkStatusError = errorUtils.getUnauthorized(errorUtils.API_ERROR.UNAUTHORIZED_ACCESS);
|
|
218
|
+
passThroughRemoteStream.emit("error", uplinkStatusError);
|
|
219
|
+
return;
|
|
220
|
+
}
|
|
221
|
+
if (res.statusCode === HTTP_STATUS.FORBIDDEN) {
|
|
222
|
+
debug("remote stream response 403");
|
|
223
|
+
const body = await readRemoteBody();
|
|
224
|
+
const message = body?.detail || body?.title || body?.message || "tarball not available: forbidden by uplink";
|
|
225
|
+
uplinkStatusError = errorUtils.getForbidden(message);
|
|
226
|
+
passThroughRemoteStream.emit("error", uplinkStatusError);
|
|
227
|
+
return;
|
|
228
|
+
}
|
|
229
|
+
if (!(res.statusCode >= HTTP_STATUS.OK && res.statusCode < HTTP_STATUS.MULTIPLE_CHOICES)) {
|
|
230
|
+
debug("remote stream response %o", res.statusCode);
|
|
231
|
+
remoteStream.resume();
|
|
232
|
+
uplinkStatusError = errorUtils.getInternalError(`bad uplink status code: ${res.statusCode}`);
|
|
233
|
+
passThroughRemoteStream.emit("error", uplinkStatusError);
|
|
234
|
+
return;
|
|
235
|
+
}
|
|
236
|
+
if (res.headers[HEADER_TYPE.CONTENT_LENGTH]) {
|
|
237
|
+
expected_length = res.headers[HEADER_TYPE.CONTENT_LENGTH];
|
|
238
|
+
debug("remote stream response content length %o", expected_length);
|
|
239
|
+
passThroughRemoteStream.emit(HEADER_TYPE.CONTENT_LENGTH, res.headers[HEADER_TYPE.CONTENT_LENGTH]);
|
|
240
|
+
}
|
|
241
|
+
try {
|
|
242
|
+
debug("remote stream response ok, starting pipeline");
|
|
243
|
+
const storage = this.getPrivatePackageStorage(name);
|
|
244
|
+
if (proxy.config.cache === true && storage) {
|
|
245
|
+
const localStorageWriteStream = await storage.writeTarball(filename, { signal });
|
|
246
|
+
await pipeline(remoteStream, passThroughRemoteStream, localStorageWriteStream, { signal });
|
|
247
|
+
} else await pipeline(remoteStream, passThroughRemoteStream, { signal });
|
|
248
|
+
} catch (err) {
|
|
249
|
+
if (uplinkStatusError) return;
|
|
250
|
+
debug("error on pipeline downloading tarball for package %o", name);
|
|
251
|
+
passThroughRemoteStream.emit("error", err);
|
|
252
|
+
}
|
|
253
|
+
}).on("downloadProgress", (progress) => {
|
|
254
|
+
current_length = progress.transferred;
|
|
255
|
+
if (typeof expected_length === "undefined" && progress.total) expected_length = progress.total;
|
|
256
|
+
}).on("end", () => {
|
|
257
|
+
if (uplinkStatusError) return;
|
|
258
|
+
if (expected_length && current_length != expected_length) {
|
|
259
|
+
debug("stream end, but length mismatch %o %o", current_length, expected_length);
|
|
260
|
+
passThroughRemoteStream.emit("error", errorUtils.getInternalError(API_ERROR.CONTENT_MISMATCH));
|
|
261
|
+
}
|
|
262
|
+
debug("remote stream end");
|
|
263
|
+
}).on("error", (err) => {
|
|
264
|
+
if (uplinkStatusError) return;
|
|
265
|
+
debug("remote stream error %o", err);
|
|
266
|
+
passThroughRemoteStream.emit("error", err);
|
|
267
|
+
});
|
|
268
|
+
return passThroughRemoteStream;
|
|
246
269
|
}
|
|
247
270
|
/**
|
|
248
271
|
*
|
|
@@ -1314,6 +1337,6 @@ var Storage = class {
|
|
|
1314
1337
|
}
|
|
1315
1338
|
};
|
|
1316
1339
|
//#endregion
|
|
1317
|
-
export { Storage };
|
|
1340
|
+
export { PROTO_NAME, Storage, noSuchFile, resourceNotAvailable };
|
|
1318
1341
|
|
|
1319
1342
|
//# sourceMappingURL=storage.mjs.map
|