@goodandready/dsh-key-rotation 0.8.74 → 0.8.75
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/CHANGELOG.md +10 -0
- package/lib/atomic-io.js +47 -4
- package/lib/client.js +178 -0
- package/lib/concurrency.js +25 -5
- package/lib/index.js +2 -0
- package/lib/lifecycle.js +2 -0
- package/lib/ops-telemetry.js +3 -2
- package/lib/pool-builder.js +14 -0
- package/lib/request-budget.js +8 -1
- package/lib/rotate.js +628 -597
- package/lib/safe-fetch.js +30 -28
- package/package.json +9 -12
package/lib/safe-fetch.js
CHANGED
|
@@ -2,7 +2,6 @@
|
|
|
2
2
|
import net from 'node:net';
|
|
3
3
|
import dns from 'node:dns/promises';
|
|
4
4
|
import nodeDns from 'node:dns';
|
|
5
|
-
import { Agent } from 'undici';
|
|
6
5
|
|
|
7
6
|
export const MAX_IMPORT_BYTES = 1024 * 1024; // 1 MB limit
|
|
8
7
|
export const MAX_REDIRECTS = 5;
|
|
@@ -105,33 +104,36 @@ export function isPrivateOrReservedIp(ip) {
|
|
|
105
104
|
* @returns {Agent}
|
|
106
105
|
*/
|
|
107
106
|
export function createSafeDispatcher({ lookupImpl = nodeDns.lookup } = {}) {
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
107
|
+
const lookup = (hostname, options, callback) => {
|
|
108
|
+
const cb = typeof options === 'function' ? options : callback;
|
|
109
|
+
const opts = typeof options === 'function' ? {} : (typeof options === 'number' ? { family: options } : (options || {}));
|
|
110
|
+
lookupImpl(hostname, { ...opts, all: true }, (err, addresses) => {
|
|
111
|
+
if (err) return cb(err);
|
|
112
|
+
const list = Array.isArray(addresses) ? addresses : [addresses];
|
|
113
|
+
for (const item of list) {
|
|
114
|
+
const addr = typeof item === 'string' ? item : item.address;
|
|
115
|
+
if (isPrivateOrReservedIp(addr)) {
|
|
116
|
+
const ssrfErr = new Error(`dsh-key-rotation: connect blocked: host ${hostname} resolves to private or reserved IP ${addr}`);
|
|
117
|
+
ssrfErr.code = 'SSRF_BLOCKED';
|
|
118
|
+
return cb(ssrfErr);
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
if (!opts.all) {
|
|
122
|
+
const first = list[0];
|
|
123
|
+
const addr = typeof first === 'string' ? first : first?.address;
|
|
124
|
+
const fam = typeof first === 'object' && first?.family ? first.family : (net.isIP(addr) || 4);
|
|
125
|
+
return cb(null, addr, fam);
|
|
126
|
+
}
|
|
127
|
+
return cb(null, addresses);
|
|
128
|
+
});
|
|
129
|
+
};
|
|
130
|
+
|
|
131
|
+
return {
|
|
132
|
+
options: {
|
|
133
|
+
connect: { lookup },
|
|
133
134
|
},
|
|
134
|
-
|
|
135
|
+
connect: { lookup },
|
|
136
|
+
};
|
|
135
137
|
}
|
|
136
138
|
|
|
137
139
|
/**
|
|
@@ -270,7 +272,7 @@ export async function safeFetchJson(url, {
|
|
|
270
272
|
redirectsLeft = MAX_REDIRECTS,
|
|
271
273
|
dispatcher,
|
|
272
274
|
} = {}) {
|
|
273
|
-
const safeDispatcher = dispatcher
|
|
275
|
+
const safeDispatcher = dispatcher;
|
|
274
276
|
let currentUrl = url;
|
|
275
277
|
while (true) {
|
|
276
278
|
await assertSafeUrl(currentUrl, { lookupImpl });
|
package/package.json
CHANGED
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@goodandready/dsh-key-rotation",
|
|
3
|
-
"version": "0.8.
|
|
4
|
-
"packageManager": "pnpm@10.33.2",
|
|
3
|
+
"version": "0.8.75",
|
|
5
4
|
"description": "Per-provider API key rotation for DeepSeek Harness: a key pool per provider, auto-created clone routes, and switching to the next key on quota/rate-limit errors. Includes a Settings section (Key Rotation) to edit the key pools, cooldown and switch codes.",
|
|
6
5
|
"keywords": [
|
|
7
6
|
"deepseek-harness",
|
|
@@ -60,13 +59,6 @@
|
|
|
60
59
|
"@deepseek-ai/dsh-llm": "^0.1.7-rc.2 || >=0.2.0-rc.1 <0.2.1-0 || >=0.2.1-alpha.1 <0.2.2-0",
|
|
61
60
|
"@deepseek-ai/schemastery": "^3.18.4"
|
|
62
61
|
},
|
|
63
|
-
"scripts": {
|
|
64
|
-
"test": "node tools/test.mjs",
|
|
65
|
-
"test:core": "node tools/test.mjs --core",
|
|
66
|
-
"check": "node tools/check.mjs",
|
|
67
|
-
"build:client": "node scripts/build-client.mjs",
|
|
68
|
-
"pretest": "node scripts/build-client.mjs"
|
|
69
|
-
},
|
|
70
62
|
"devDependencies": {
|
|
71
63
|
"react": "18.3.1",
|
|
72
64
|
"react-test-renderer": "18.3.1",
|
|
@@ -75,7 +67,12 @@
|
|
|
75
67
|
"@deepseek-ai/schemastery": "^3.18.4",
|
|
76
68
|
"semver": "^7.6.3"
|
|
77
69
|
},
|
|
78
|
-
"dependencies": {
|
|
79
|
-
|
|
70
|
+
"dependencies": {},
|
|
71
|
+
"scripts": {
|
|
72
|
+
"test": "node tools/test.mjs",
|
|
73
|
+
"test:core": "node tools/test.mjs --core",
|
|
74
|
+
"check": "node tools/check.mjs",
|
|
75
|
+
"build:client": "node scripts/build-client.mjs",
|
|
76
|
+
"pretest": "node scripts/build-client.mjs"
|
|
80
77
|
}
|
|
81
|
-
}
|
|
78
|
+
}
|