klaemo opened a new pull request, #382:
URL: https://github.com/apache/couchdb-nano/pull/382

   ## Overview
   
   Fixes to `lib/nano.d.ts` only; there are no runtime changes. As agreed in 
#381, this combines #362, #380 and #381, because they touch the same lines.
   
   1. **`Configuration.parseUrl` was missing (#362).** The runtime still reads 
it (`'parseUrl' in cfg`), and the README documents it. The "Set to false to 
prevent parsing of url" comment had ended up above `headers`, with the "Custom 
request headers" comment after it. This adds `parseUrl?: boolean` back and puts 
both comments on the right properties.
   2. **`Configuration.agentOptions` is now a Dispatcher instance (#380).** It 
used to be a union of `AgentOptions` and constructor types (`typeof 
undici.Agent`, ...). nano passes the value unchanged to `fetch` as 
`dispatcher`, so it has to be an instance. Before this change, `new 
Agent({...})` and `new MockAgent()` failed with TS2322. Passing the `Agent` 
class or a plain options object typechecked, but every request then failed with 
`TypeError: agent.dispatch is not a function`. The `AgentOptions` interface 
stays exported, so existing `nano.AgentOptions` references keep compiling.
   3. **`RequestError.request` now describes the object nano attaches (#380).** 
That object is the scrubbed `fetchOptions` from `relax()`: `url` (including the 
query string), lower-case `method`, `headers`, `body`, `credentials`, 
`redirect`, `signal`, `bodyTimeout`, and `dispatcher` when one is configured. 
This replaces the old `uri`/`qs` shape, which nano 11 never sets. All 
properties stay optional, like the rest of `RequestError`.
   4. **No more `undici` import (#381).** This is option 2 from the issue. 
`nano.d.ts` declares a structural `nano.Dispatcher` interface 
(`dispatch(options: object, handler: object): boolean`) instead of `import 
undici from "undici"`. Consumers no longer need undici's types to compile with 
`skipLibCheck: false`, and with `skipLibCheck: true` `agentOptions` is no 
longer silently `any`. undici remains a devDependency for the test mocks.
   
   Compatibility: the only code that stops compiling is code that was already 
broken at runtime. That covers reading `err.request.uri`/`err.request.qs` 
(always `undefined` in v11) and passing a class, a plain object or a 
non-dispatcher as `agentOptions`. Comparisons like `err.request?.method === 
'GET'` still compile, although at runtime the method is lower case.
   
   ## Testing recommendations
   
   `npm test` passes (`tsc lib/nano.d.ts` plus 243 tests). The repo has no 
type-level tests, so I checked the changes with consumer projects using 
`module`/`moduleResolution: nodenext`, `strict` and `skipLibCheck: false`.
   
   With undici 7 installed, this file compiles cleanly with this PR as both ESM 
and CJS (`import Nano = require('nano')`). Against `main` it gives 7 × TS2322 
(one per instance line), TS2353 on `parseUrl`, TS2339 on `request.url`, and 3 
unused `@ts-expect-error` directives:
   
   ```ts
   import Nano from 'nano'
   import { Agent, MockAgent, Pool, ProxyAgent, RetryAgent, getGlobalDispatcher 
} from 'undici'
   
   const url = 'http://localhost:5984'
   
   // accepted: Dispatcher instances, parseUrl
   Nano({ url, agentOptions: new Agent({ connections: 10 }) })
   Nano({ url, agentOptions: new MockAgent() })
   Nano({ url, agentOptions: new Pool(url) })
   Nano({ url, agentOptions: new ProxyAgent('http://proxy:8080') })
   Nano({ url, agentOptions: new RetryAgent(new Agent()) })
   Nano({ url, agentOptions: getGlobalDispatcher() })
   Nano({ url, agentOptions: new Agent().compose((d) => d) })
   Nano({ url: `${url}/mydb`, parseUrl: false })
   
   // rejected: these all throw "agent.dispatch is not a function" at runtime
   // @ts-expect-error class constructor, not an instance
   Nano({ url, agentOptions: Agent })
   // @ts-expect-error plain options object
   Nano({ url, agentOptions: { bodyTimeout: 1000 } })
   
   // RequestError.request matches what nano attaches
   const err = {} as Nano.RequestError
   const reqUrl: string | undefined = err.request?.url
   const method: string | undefined = err.request?.method
   // @ts-expect-error not present at runtime; the query string is part of `url`
   err.request?.qs
   // @ts-expect-error not present at runtime; see `url` (`err.headers.uri` 
still exists)
   err.request?.uri
   ```
   
   Without undici installed, this compiles cleanly with this PR. Against `main` 
it fails with `TS2307: Cannot find module 'undici'` in `nano.d.ts`:
   
   ```ts
   import Nano from 'nano'
   Nano({ url: 'http://localhost:5984' })
   // @ts-expect-error not a Dispatcher
   Nano({ url: 'http://localhost:5984', agentOptions: 42 })
   ```
   
   For reference, this is the runtime `err.request` for a 404 with an `Agent` 
configured. I got it against a local stub server with nano 11.0.7 on Node 24.21:
   
   ```js
   {
     url: 'http://localhost:39187/db/doc?revs_info=true',
     method: 'get',
     headers: { accept: 'application/json', 'user-agent': 'nano/11.0.7 (Node.js 
v24.21.0)',
                'Accept-Encoding': 'deflate, gzip', Authorization: 'XXXXXXX', 
'content-type': 'application/json' },
     credentials: 'include',
     body: undefined,
     redirect: 'error',
     signal: undefined,
     bodyTimeout: 0,
     dispatcher: Agent { ... }
   }
   ```
   
   ## GitHub issue number
   
   Fixes #362
   Fixes #380
   Fixes #381
   
   ## Related Pull Requests
   
   None. Separately, the README and migration guide examples pass the agent as 
`undiciOptions`, which nano ignores, rather than as `agentOptions`. That's a 
docs fix and not part of this PR.
   
   ## Checklist
   
   - [x] Code is written and works correctly;
   - [x] Changes are covered by tests; (`tsc lib/nano.d.ts` in `npm test`, plus 
the consumer snippets above; the repo has no type-test harness)
   - [x] Documentation reflects the changes; (JSDoc in `nano.d.ts`)
   
   ---
   
   This PR was prepared with Claude Code (AI-assisted, per the ASF generative 
tooling guidance). I reviewed the changes and checked them against 
`lib/nano.js`.
   
   🤖 Generated with [Claude Code](https://claude.com/claude-code)
   


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to