Skip to content

Commit 13a29af

Browse files
authored
fix: compatible with pool stats reading (#578)
<!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit * **Documentation** * Corrected a typographical error in the README. * **Chores** * Updated Node.js versions tested in CI to version 24. * Updated test coverage script for Node.js 16 compatibility. * Enhanced clean script to clear TypeScript build cache. * Upgraded Vitest development dependency to version 3.2.4. * Added polyfills to improve compatibility with Node.js environments lacking certain web APIs. * **Bug Fixes** * Improved compatibility with updated HTTP client pool structure. * Enhanced test assertions with detailed failure messages for easier debugging. <!-- end of auto-generated comment: release notes by coderabbit.ai -->
1 parent ef36c8a commit 13a29af

File tree

11 files changed

+37
-19
lines changed

11 files changed

+37
-19
lines changed

.github/workflows/nodejs.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,6 @@ jobs:
1313
uses: node-modules/github-actions/.github/workflows/node-test.yml@master
1414
with:
1515
os: 'ubuntu-latest, macos-latest, windows-latest'
16-
version: '16, 18, 20, 22, 23'
16+
version: '16, 18, 20, 22, 24'
1717
secrets:
1818
CODECOV_TOKEN: ${{ secrets.CODECOV_TOKEN }}

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -136,7 +136,7 @@ content-type: application/json
136136
}
137137
```
138138

139-
This exmaple can use `options.data` with `application/json` content type:
139+
This example can use `options.data` with `application/json` content type:
140140

141141
```js
142142
await request('https://example.com', {

package.json

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -39,9 +39,9 @@
3939
"test": "npm run lint -- --fix && vitest run",
4040
"test-keepalive": "cross-env TEST_KEEPALIVE_COUNT=50 vitest run --test-timeout 180000 keep-alive-header.test.ts",
4141
"test-node16": "node examples/httpclient.cjs && node examples/search_github.cjs && node examples/timing.cjs",
42-
"cov": "cross-env NODE_OPTIONS='--require ./test/patch-structuredClone.cjs' vitest run --coverage",
42+
"cov": "cross-env NODE_OPTIONS=\"--require ./test/patch-for-node16-18.cjs\" vitest run --coverage",
4343
"ci": "npm run lint && npm run cov && npm run prepublishOnly && npm pack && attw --pack",
44-
"clean": "rm -rf dist",
44+
"clean": "rm -rf dist && tsc -b --clean",
4545
"prepublishOnly": "npm run build"
4646
},
4747
"dependencies": {
@@ -74,11 +74,12 @@
7474
"iconv-lite": "^0.6.3",
7575
"proxy": "^1.0.2",
7676
"selfsigned": "^2.4.1",
77+
"string.prototype.towellformed": "^1.0.2",
7778
"tar-stream": "^2.2.0",
7879
"tshy": "^3.0.0",
7980
"tshy-after": "^1.0.0",
8081
"typescript": "^5.0.4",
81-
"vitest": "^3.0.2"
82+
"vitest": "^3.2.4"
8283
},
8384
"engines": {
8485
"node": ">= 18.19.0"

src/HttpClient.ts

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -227,9 +227,11 @@ export class HttpClient extends EventEmitter {
227227
return poolStatsMap;
228228
}
229229
for (const [ key, ref ] of clients) {
230-
const pool = typeof ref.deref === 'function' ? ref.deref() : ref as unknown as Pool;
231-
const stats = pool?.stats;
230+
const pool = (typeof ref.deref === 'function' ? ref.deref() : ref) as unknown as (Pool & { dispatcher: Pool });
231+
// NOTE: pool become to { dispatcher: Pool } in undici@v7
232+
const stats = pool?.stats ?? pool?.dispatcher?.stats;
232233
if (!stats) continue;
234+
233235
poolStatsMap[key] = {
234236
connected: stats.connected,
235237
free: stats.free,

src/fetch.ts

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -114,9 +114,11 @@ export class FetchFactory {
114114
return poolStatsMap;
115115
}
116116
for (const [ key, ref ] of clients) {
117-
const pool = typeof ref.deref === 'function' ? ref.deref() : ref as unknown as Pool;
118-
const stats = pool?.stats;
117+
const pool = (typeof ref.deref === 'function' ? ref.deref() : ref) as unknown as (Pool & { dispatcher: Pool });
118+
// NOTE: pool become to { dispatcher: Pool } in undici@v7
119+
const stats = pool?.stats ?? pool?.dispatcher?.stats;
119120
if (!stats) continue;
121+
120122
poolStatsMap[key] = {
121123
connected: stats.connected,
122124
free: stats.free,

test/HttpClient.test.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -326,7 +326,8 @@ describe('HttpClient.test.ts', () => {
326326

327327
const response = await httpclient.request(_url);
328328
assert.equal(response.status, 200);
329-
assert.equal(Object.keys(httpclient.getDispatcherPoolStats()).length, 1);
329+
assert.equal(Object.keys(httpclient.getDispatcherPoolStats()).length, 1,
330+
`dispatcher pool stats: ${JSON.stringify(httpclient.getDispatcherPoolStats())}`);
330331
});
331332

332333
it('should check non-ip hostname with custom lookup', async () => {

test/fetch.test.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -108,7 +108,7 @@ describe('fetch.test.ts', () => {
108108

109109
const stats = FetchFactory.getDispatcherPoolStats();
110110
assert(stats);
111-
assert(Object.keys(stats).length > 0);
111+
assert(Object.keys(stats).length > 0, `dispatcher pool stats: ${JSON.stringify(stats)}`);
112112
});
113113

114114
it('fetch request with post should work', async () => {

test/fixtures/socket_server.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import { createServer, Server } from 'node:http';
22

33
const socketPathPrefix = '/tmp/urllib.unix.sock';
44
let index = 0;
5+
56
export async function startServer(): Promise<{
67
server: Server,
78
url: string,

test/options.socketPath.test.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ describe.skipIf(isWindows())('options.socketPath.test.ts', () => {
1919

2020
afterAll(async () => {
2121
await close();
22-
await server2.closeServer();
22+
await server2?.closeServer();
2323
});
2424

2525
it('should request socket successfully', async () => {

test/patch-for-node16-18.cjs

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
// vitest require structuredClone
2+
if (!('structuredClone' in globalThis)) {
3+
const structuredClone = require('@ungap/structured-clone').default;
4+
5+
globalThis.structuredClone = structuredClone;
6+
// console.debug('patched structuredClone for Node.js %s', process.version);
7+
}
8+
9+
// vitest require crypto.getRandomValues
10+
const crypto = require('node:crypto');
11+
if (typeof crypto.getRandomValues !== 'function') {
12+
crypto.getRandomValues = crypto.webcrypto.getRandomValues.bind(crypto.webcrypto);
13+
}
14+
15+
// undici@v7 require String.prototype.toWellFormed, patch on Node.js 16 and 18
16+
if (typeof String.prototype.toWellFormed !== 'function') {
17+
require('string.prototype.towellformed/auto');
18+
}

0 commit comments

Comments
 (0)