Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/wet-turtles-relax.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"mobx-tanstack-query": minor
---

added fetch queries new features (FetchQuery, createFetchQuery)
8 changes: 6 additions & 2 deletions .github/workflows/version-or-publish.yml
Original file line number Diff line number Diff line change
Expand Up @@ -21,12 +21,15 @@ jobs:
steps:
- name: Checkout tree
uses: actions/checkout@v4
with:
fetch-depth: 0

- name: Set-up Node.js
uses: actions/setup-node@v4
with:
check-latest: true
node-version-file: .nvmrc
registry-url: https://registry.npmjs.org

- run: corepack enable
- run: pnpm i
Expand All @@ -43,15 +46,16 @@ jobs:
echo "last_tag=$tag" >> $GITHUB_OUTPUT
fi

- run: npm install -g npm@latest

- name: Create Release Pull Request
uses: changesets/action@v1
continue-on-error: false
id: pub-or-release-pr
with:
version: pnpm changeset version
publish: pnpm pub
createGithubReleases: false

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1: The NPM_TOKEN and NPM_AUTH_TOKEN environment variables were removed from the changesets/action step, but no alternative npm authentication was provided. The setup-node step adds registry-url but does not set NODE_AUTH_TOKEN, so no auth token is written to .npmrc. The changesets/action relies on the NPM_TOKEN env var to automatically configure npm authentication for publishing. Without it, the publish step will fail when attempting to publish to the npm registry. Either restore the NPM_TOKEN secret as an env var on the action step, or set NODE_AUTH_TOKEN with ${{ secrets.NPM_TOKEN }} if relying on setup-node auth.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At .github/workflows/version-or-publish.yml, line 58:

<comment>The `NPM_TOKEN` and `NPM_AUTH_TOKEN` environment variables were removed from the `changesets/action` step, but no alternative npm authentication was provided. The `setup-node` step adds `registry-url` but does not set `NODE_AUTH_TOKEN`, so no auth token is written to `.npmrc`. The `changesets/action` relies on the `NPM_TOKEN` env var to automatically configure npm authentication for publishing. Without it, the publish step will fail when attempting to publish to the npm registry. Either restore the `NPM_TOKEN` secret as an env var on the action step, or set `NODE_AUTH_TOKEN` with `${{ secrets.NPM_TOKEN }}` if relying on `setup-node` auth.</comment>

<file context>
@@ -43,15 +46,16 @@ jobs:
         with:
           version: pnpm changeset version
           publish: pnpm pub
+          createGithubReleases: false
         env:
           CI: true
</file context>

env:
CI: true
GITHUB_TOKEN: ${{ github.token }}
Comment on lines +49 to 61

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🩺 Stability & Availability | 🟠 Major | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

sed -n '1,140p' .github/workflows/version-or-publish.yml && printf '\n---\n' && rg -n "NODE_AUTH_TOKEN|NPM_TOKEN|registry-url|changesets/action|pnpm pub" .github/workflows . -g '!**/node_modules/**'

Repository: js2me/mobx-tanstack-query

Length of output: 2586


🏁 Script executed:

sed -n '1,220p' package.json && printf '\n---\n' && fd -a 'config.json' .changeset .github . && printf '\n---\n' && rg -n "\"pub\"|changesets|publishConfig|npmrc|NODE_AUTH_TOKEN|NPM_TOKEN" package.json .changeset .github -g '!**/node_modules/**'

Repository: js2me/mobx-tanstack-query

Length of output: 3817


🌐 Web query:

actions/setup-node registry-url NODE_AUTH_TOKEN authenticated npm publish documentation

💡 Result:

To authenticate and publish an npm package using GitHub Actions, you use the actions/setup-node action to configure a local.npmrc file with your registry information and authentication token [1][2]. For classic token-based authentication: 1. Create a repository secret (e.g., NPM_TOKEN) in your GitHub repository containing your npm authentication token [1][2]. 2. In your workflow YAML, use actions/setup-node with the registry-url input set to the registry (e.g., https://registry.npmjs.org/) [1][2]. 3. Provide the secret to the action via the NODE_AUTH_TOKEN environment variable in the step that runs npm publish [1][2]. Example workflow configuration: - uses: actions/setup-node@v4 with: node-version: '20.x' registry-url: 'https://registry.npmjs.org' - run: npm publish env: NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} When the registry-url is set, actions/setup-node automatically creates a temporary.npmrc file that references the NODE_AUTH_TOKEN variable, allowing npm to authenticate during the publish process [1][2]. Note on Trusted Publishing (OIDC): Modern workflows can use npm's Trusted Publisher (OIDC) feature to publish without long-lived tokens [3]. If you are using OIDC, be aware that setting registry-url in actions/setup-node historically adds an _authToken placeholder to the.npmrc file [4]. While this is the standard setup for token-based auth, some users have reported issues with this configuration in OIDC-only environments [4]. Always ensure your workflow permissions include id-token: write when using OIDC [1][2].

Citations:


Add NODE_AUTH_TOKEN to the publish step. actions/setup-node expects it for npm auth when registry-url is set, but this job only passes GITHUB_TOKEN. pnpm pub will fail to publish unless the npm token is added back.

🔧 Proposed fix
         env:
           CI: true
           GITHUB_TOKEN: ${{ github.token }}
+          NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
- run: npm install -g npm@latest
- name: Create Release Pull Request
uses: changesets/action@v1
continue-on-error: false
id: pub-or-release-pr
with:
version: pnpm changeset version
publish: pnpm pub
createGithubReleases: false
env:
CI: true
GITHUB_TOKEN: ${{ github.token }}
- run: npm install -g npm@latest
- name: Create Release Pull Request
uses: changesets/action@v1
continue-on-error: false
id: pub-or-release-pr
with:
version: pnpm changeset version
publish: pnpm pub
createGithubReleases: false
env:
CI: true
GITHUB_TOKEN: ${{ github.token }}
NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
🧰 Tools
🪛 zizmor (1.26.1)

[warning] 49-49: ad-hoc installation of packages (adhoc-packages): installs a package outside of a lockfile

(adhoc-packages)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/version-or-publish.yml around lines 49 - 61, Add
NODE_AUTH_TOKEN to the env configuration of the changesets/action step
identified by id pub-or-release-pr, sourcing it from the repository’s npm
authentication secret. Preserve the existing GITHUB_TOKEN and publishing
configuration so pnpm pub can authenticate with the npm registry.

Source: Linters/SAST tools

NPM_TOKEN: ${{ secrets.NPM_TOKEN }}
NPM_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
12 changes: 12 additions & 0 deletions docs/.vitepress/config.mts
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,10 @@ export default defineDocsVitepressConfig(configs, {
link: "/api/Query",
items: [
{ text: "Query", link: "/api/Query" },
{ text: "FetchQuery", link: "/api/FetchQuery" },
{ text: "Mutation", link: "/api/Mutation" },
{ text: "InfiniteQuery", link: "/api/InfiniteQuery" },
{ text: "FetchInfiniteQuery", link: "/api/FetchInfiniteQuery" },
{ text: "QueryClient", link: "/api/QueryClient" },
{ text: "Other", link: "/api/other" },
],
Expand All @@ -45,11 +47,21 @@ export default defineDocsVitepressConfig(configs, {
items: [
{ text: "Overview", link: "/preset" },
{ text: "createQuery", link: "/preset/createQuery" },
{ text: "createFetchQuery", link: "/preset/createFetchQuery" },
{ text: "createMutation", link: "/preset/createMutation" },
{ text: "createInfiniteQuery", link: "/preset/createInfiniteQuery" },
{ text: "createFetchInfiniteQuery", link: "/preset/createFetchInfiniteQuery" },
{ text: "queryClient", link: "/preset/queryClient" },
],
},
{
text: "Errors 🚨",
link: "/errors/1",
items: [
{ text: "#1: Fetch query is not configured", link: "/errors/1" },
{ text: "#2: Fetch infinite query is not configured", link: "/errors/2" },
],
},
{
text: "Other",
items: [
Expand Down
67 changes: 67 additions & 0 deletions docs/api/FetchInfiniteQuery.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
# FetchInfiniteQuery

A [`FetchQuery`](/api/FetchQuery) for paginated data — same declarative `params` API, but with built-in page navigation.

Like [`FetchQuery`](/api/FetchQuery), it auto-generates `queryKey` from `params` and handles the HTTP request for you. The difference is that `params` receives a `pageParam` argument, and you control pagination via `getNextPageParam`.

**All properties and methods** (`data`, `isLoading`, `error`, `fetchNextPage`, `hasNextPage`, etc.) are inherited from [`InfiniteQuery`](/api/InfiniteQuery).

[Reference to source code](/src/fetch-infinite-query.ts)

## Usage

```ts
const starsQuery = new FetchInfiniteQuery({
queryClient,
params: ({ pageParam }) => ({
Comment thread
cubic-dev-ai[bot] marked this conversation as resolved.
path: '/stars',
query: {
count: 20,
page: pageParam,
},
}),
initialPageParam: 1,
getNextPageParam: (lastPage, _, lastPageParam) => {
return lastPage.length ? lastPageParam + 1 : null;
},
});
```

### Manual control with `start()`

Create a `FetchInfiniteQuery` without `params` (disabled by default), then fetch manually:

```ts
const starsQuery = new FetchInfiniteQuery({
queryClient,
initialPageParam: 1,
getNextPageParam: (lastPage, _, lastPageParam) => {
return lastPage.length ? lastPageParam + 1 : null;
},
});

const result = await starsQuery.start({
params: { path: '/stars', query: { count: 20 } },
});
```

### How it works

1. `params` is a function that receives `{ pageParam }` — the current page parameter (starts at `initialPageParam`)
2. Each page request uses the same `params` logic with a different `pageParam`
3. After each page loads, `getNextPageParam` determines the next page parameter — return `null` to indicate no more pages
4. `data` is an array of all fetched pages, and `fetchNextPage()` triggers the next request

### Example: cursor-based pagination

```ts
const commentsQuery = new FetchInfiniteQuery({
queryClient,
params: ({ pageParam }) => ({
path: '/comments',
query: { cursor: pageParam },
}),
initialPageParam: undefined as string | undefined,
getNextPageParam: (lastPage) => lastPage.nextCursor ?? null,
});
```
Comment on lines +30 to +67

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

data is not a plain array — it's an InfiniteData object.

Line 53 states "data is an array of all fetched pages," but FetchInfiniteQuery uses InfiniteData<TQueryFnData, TPageParam> (per src/fetch-infinite-query.ts), which is { pages: TQueryFnData[], pageParams: TPageParam[] }. The aggregated pages live in data.pages, not data directly.

📝 Proposed fix
-4. `data` is an array of all fetched pages, and `fetchNextPage()` triggers the next request
+4. `data` is an `InfiniteData` object whose `.pages` array holds all fetched pages, and `fetchNextPage()` triggers the next request
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
### Manual control with `start()`
Create a `FetchInfiniteQuery` without `params` (disabled by default), then fetch manually:
```ts
const starsQuery = new FetchInfiniteQuery({
queryClient,
initialPageParam: 1,
getNextPageParam: (lastPage, _, lastPageParam) => {
return lastPage.length ? lastPageParam + 1 : null;
},
});
const result = await starsQuery.start({
params: { path: '/stars', query: { count: 20 } },
});
```
### How it works
1. `params` is a function that receives `{ pageParam }` — the current page parameter (starts at `initialPageParam`)
2. Each page request uses the same `params` logic with a different `pageParam`
3. After each page loads, `getNextPageParam` determines the next page parameter — return `null` to indicate no more pages
4. `data` is an array of all fetched pages, and `fetchNextPage()` triggers the next request
### Example: cursor-based pagination
```ts
const commentsQuery = new FetchInfiniteQuery({
queryClient,
params: ({ pageParam }) => ({
path: '/comments',
query: { cursor: pageParam },
}),
initialPageParam: undefined as string | undefined,
getNextPageParam: (lastPage) => lastPage.nextCursor ?? null,
});
```
### Manual control with `start()`
Create a `FetchInfiniteQuery` without `params` (disabled by default), then fetch manually:
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@docs/api/FetchInfiniteQuery.md` around lines 30 - 67, Update the “How it
works” description for `FetchInfiniteQuery` so `data` is documented as an
`InfiniteData` object containing `pages` and `pageParams`, with fetched results
accessed through `data.pages` rather than directly as an array.

142 changes: 142 additions & 0 deletions docs/api/FetchQuery.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,142 @@
# FetchQuery

A [`Query`](/api/Query) that makes HTTP requests for you — no need to write `queryFn` or `queryKey` manually.

Instead of describing **how** to fetch data, you describe **what** to fetch using `params`:

```ts
// Query — you write the fetch logic yourself
new Query({
queryClient,
queryKey: ['/pets'],
queryFn: () => fetch('/pets').then(r => r.json()),
})

// FetchQuery — just describe the request
new FetchQuery({
queryClient,
params: { path: '/pets' },
})
```

`FetchQuery` auto-generates `queryKey` from your `params`, so the cache stays consistent automatically.

**All properties and methods** (`data`, `isLoading`, `error`, `refetch`, etc.) are inherited from [`Query`](/api/Query).

[Reference to source code](/src/fetch-query.ts)

## Usage

### Basic GET request

```ts
const petsQuery = new FetchQuery({
queryClient,
params: {
path: '/pets',
},
});

console.log(petsQuery.data, petsQuery.isLoading);
```

### Dynamic params

`params` can be a function — when MobX observables inside it change, the query automatically refetches with new parameters. Return a falsy value to disable the query.

```ts
const petId = observable.box<string>();

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
set -euo pipefail

printf '--- docs/api/FetchQuery.md (around the cited lines) ---\n'
sed -n '1,140p' docs/api/FetchQuery.md | cat -n

printf '\n--- package references to mobx ---\n'
rg -n '"mobx"|observable\.box|FetchQuery' package.json . -g 'package.json' -g '*.md' -g '*.ts' -g '*.tsx' -g '*.js' -g '*.jsx'

Repository: js2me/mobx-tanstack-query

Length of output: 254


🌐 Web query:

MobX observable.box requires initial value TypeScript API

💡 Result:

In MobX, observable.box(value, options?) requires an initial value to be provided [1][2]. While earlier versions or certain type definitions may have permitted omitting the argument, providing an initial value is standard practice to ensure type safety and prevent runtime errors [3]. If you attempt to use observable.box without an argument, it may lead to TypeScript errors or runtime issues when you subsequently call.get on the empty box [3]. To correctly initialize a box with no specific value, you should explicitly pass undefined or null: const myBox = observable.box(undefined); // Correct initialization [3] myBox.set("new value"); // Safely update later The observable.box API is used to create an observable reference to a value, primarily for primitive values that are not owned by an object [2]. Once created, you interact with the value using the.get and.set(newValue) methods [1][2].

Citations:


Initialize the MobX box with a value. observable.box<string>() needs an initial value, so use observable.box<string | undefined>(undefined) or a concrete pet ID.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@docs/api/FetchQuery.md` at line 34, Update the petId observable declaration
to initialize the MobX box with a value, using undefined with a
string-or-undefined type or an appropriate concrete pet ID. Preserve the
existing petId usage and documentation context.


const petQuery = new FetchQuery({
queryClient,
params: () => petId.get()
? { path: `/pets/${petId.get()}` }
: null, // query is disabled while petId is empty
});
```

### POST request with body

```ts
const createPetQuery = new FetchQuery({
queryClient,
params: () => ({
path: '/pets',
method: 'POST',
body: { name: 'Fluffy', type: 'cat' },
}),
});
```

### Full fetch configuration

```ts
const petQuery = new FetchQuery({
queryClient,
params: {
baseUrl: 'https://api.example.com',
path: '/pets',
query: { limit: 10, sort: 'name' },
method: 'GET',
headers: { 'X-Custom-Header': 'value' },
notFoundAsNull: true,
},
});
```

## `FetchQueryParams`

- `path: string` — **Required.** The URL path for the request
- `baseUrl?: string` — Base URL prepended to `path`. Can also be set globally via [`QueryClient.fetchQueries`](/api/QueryClient#fetchqueries)
- `query?: Record<string, string | number | boolean | null | undefined>` — Query parameters to be serialized and appended to the URL
- `method?: string` — HTTP method. Defaults to `"GET"` (or `"POST"` when `body` is provided)
- `headers?: Record<string>` — Request headers. Merged with global headers from `QueryClient.fetchQueries`

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: Record<string> is not valid TypeScript — the Record utility type requires two type arguments (Record<Keys, Type>). This should be Record<string, string> to match the actual type used in the source code (Dict<string>).

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At docs/api/FetchQuery.md, line 79:

<comment>`Record<string>` is not valid TypeScript — the `Record` utility type requires two type arguments (`Record<Keys, Type>`). This should be `Record<string, string>` to match the actual type used in the source code (`Dict<string>`).</comment>

<file context>
@@ -0,0 +1,118 @@
+- `baseUrl?: string` — Base URL prepended to `path`. Can also be set globally via [`QueryClient.fetchQueries`](/api/QueryClient#fetchqueries)
+- `query?: Record<string, string | number | boolean | null | undefined>` — Query parameters to be serialized and appended to the URL
+- `method?: string` — HTTP method. Defaults to `"GET"` (or `"POST"` when `body` is provided)
+- `headers?: Record<string>` — Request headers. Merged with global headers from `QueryClient.fetchQueries`
+- `body?: BodyInit | Record<string, unknown>` — Request body. Objects are JSON-serialized with `Content-Type: application/json`; native `BodyInit` (Blob, FormData, etc.) is passed through as-is
+- `request?: Partial<RequestInit>` — Additional `RequestInit` options (except `signal`, `method`, `headers`, `body`)
</file context>

- `body?: BodyInit | Record<string, unknown>` — Request body. Objects are JSON-serialized with `Content-Type: application/json`; native `BodyInit` (Blob, FormData, etc.) is passed through as-is
Comment on lines +93 to +94

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
set -euo pipefail

# Show the relevant section with line numbers and a bit of surrounding context.
sed -n '60,95p' docs/api/FetchQuery.md | cat -n

# Also locate any similar Record typings elsewhere in the docs to compare conventions.
rg -n "Record<string" docs -S

Repository: js2me/mobx-tanstack-query

Length of output: 3140


Use complete Record type arguments. Record<string> is invalid TypeScript; document headers as Record<string, string> and keep object bodies as Record<string, unknown>.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@docs/api/FetchQuery.md` around lines 79 - 80, Update the FetchQuery
documentation’s headers option to use the complete Record type arguments,
changing it to Record<string, string>; retain Record<string, unknown> for object
request bodies.

- `request?: Partial<RequestInit>` — Additional `RequestInit` options (except `signal`, `method`, `headers`, `body`)
- `notFoundAsNull?: boolean` — If `true`, a 404 response returns `null` instead of throwing
- `responseType?: ResponseType` — Method to read the response body (e.g. `"json"`, `"text"`, `"blob"`). Defaults to `"json"`
- `transformResponse?: TransformResponseFn` — Custom function to transform the `Response` object before data is returned
- `throwOnError?: boolean` — Whether to throw the raw `Response` on non-ok status. Defaults to `true`
- `meta?: QueryMeta` — Metadata attached to the query

## Manual control with `start()`

Create a `FetchQuery` without `params` (disabled by default), then fetch manually:

```ts
const petQuery = new FetchQuery({
queryClient,
// no params — query is disabled
});

const result = await petQuery.start({
params: { path: '/pets/123' },
});

console.log(result.data);
```

## Request behavior

- Per-request `params` are **merged** with global defaults from [`QueryClient.fetchQueries`](/api/QueryClient#fetchqueries) (per-request values take precedence)
- The full URL is built as `baseUrl + path` with `query` params serialized and appended
- `queryKey` is auto-generated from `params` — you never set it manually

## Recommendations

### Use `QueryClient.fetchQueries` for global configuration

Instead of repeating `baseUrl`, `headers`, and other options in every `FetchQuery`, set them once on the `QueryClient`:

```ts
const queryClient = new QueryClient({
fetchQueries: {
baseUrl: 'https://api.example.com',
headers: {
Authorization: 'Bearer my-token',
},
throwOnError: true,
timeout: 30_000,
},
});
```
33 changes: 33 additions & 0 deletions docs/api/QueryClient.md
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ interface QueryClientConfig {
mutations: MobxMutatonFeatures;
};
hooks?: QueryClientHooks;
fetchQueries?: FetchQueriesOptions;
}
```

Expand Down Expand Up @@ -92,6 +93,38 @@ Entity lifecycle events. Available hooks:
| onInfiniteQueryDestroy | Triggered when a [`InfiniteQuery`](/api/InfiniteQuery) is destroyed |
| onMutationDestroy | Triggered when a [`Mutation`](/api/Mutation) is destroyed |

### `fetchQueries`

Global configuration for [`FetchQuery`](/api/FetchQuery) and [`FetchInfiniteQuery`](/api/FetchInfiniteQuery). These defaults are merged with per-request `params` in every fetch query.

- `baseUrl?: string` — Base URL prepended to every `path`
- `headers?: Record<string>` — Default headers merged with per-request headers

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
set -euo pipefail

# Inspect the documented line and nearby context
sed -n '85,120p' docs/api/QueryClient.md

# Search for the same header type pattern elsewhere in docs and source
rg -n "Record<string>" docs src . --glob '!**/node_modules/**' || true

# Find the runtime/query option contract that this doc refers to
rg -n "headers\\?:|Default headers|per-request headers|headers" docs src --glob '!**/node_modules/**' || true

Repository: js2me/mobx-tanstack-query

Length of output: 7341


Use a complete header type here.

Record<string> is incomplete; use Record<string, string> so the header value type is explicit and matches the contract.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@docs/api/QueryClient.md` at line 101, Update the headers option type in the
QueryClient API documentation from Record<string> to Record<string, string>,
keeping the existing description and behavior unchanged.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: Record<string> is invalid TypeScript — it requires two type arguments. Use Record<string, string> to correctly document the headers type.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At docs/api/QueryClient.md, line 101:

<comment>`Record<string>` is invalid TypeScript — it requires two type arguments. Use `Record<string, string>` to correctly document the headers type.</comment>

<file context>
@@ -92,6 +93,38 @@ Entity lifecycle events. Available hooks:
+Global configuration for [`FetchQuery`](/api/FetchQuery) and [`FetchInfiniteQuery`](/api/FetchInfiniteQuery). These defaults are merged with per-request `params` in every fetch query.
+
+- `baseUrl?: string` — Base URL prepended to every `path`
+- `headers?: Record<string>` — Default headers merged with per-request headers
+- `customFetch?: typeof globalThis.fetch` — Custom fetch implementation (useful for testing or non-browser environments)
+- `transformResponse?: TransformResponseFn` — Global response transformation function
</file context>
Suggested change
- `headers?: Record<string>` — Default headers merged with per-request headers
- `headers?: Record<string, string>` — Default headers merged with per-request headers

- `customFetch?: typeof globalThis.fetch` — Custom fetch implementation (useful for testing or non-browser environments)
- `transformResponse?: TransformResponseFn` — Global response transformation function
- `throwOnError?: boolean` — Whether to throw the raw `Response` on non-ok status. Defaults to `true`
- `timeout?: number` — Request timeout in milliseconds
- `credentials?: RequestCredentials` — Credentials mode for requests (e.g. `"include"`, `"same-origin"`)
- `mode?: RequestMode` — Request mode (e.g. `"cors"`, `"no-cors"`)
- `meta?: QueryMeta` — Default metadata attached to fetch queries

Example:

```ts
import { QueryClient } from "mobx-tanstack-query";

const queryClient = new QueryClient({
fetchQueries: {
baseUrl: "https://api.example.com",
headers: {
Authorization: "Bearer __TOKEN__",
},
throwOnError: true,
timeout: 30_000,
credentials: "include",
},
});
```

## Inheritance

`QueryClient` inherits all methods and properties from [QueryClient](https://tanstack.com/query/v5/docs/reference/QueryClient), including:
Expand Down
8 changes: 5 additions & 3 deletions docs/api/other.md
Original file line number Diff line number Diff line change
@@ -1,16 +1,18 @@
# Other

## `InferQuery`, `InferMutation`, `InferInfiniteQuery` types
## `InferQuery`, `InferMutation`, `InferInfiniteQuery`, `InferFetchQuery`, `InferFetchInfiniteQuery` types

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1: The types InferFetchQuery and InferFetchInfiniteQuery are documented in the heading and code example but don't exist anywhere in the source code. Users importing them will get TS errors. Add the missing type definitions (analogous to InferQuery/InferInfiniteQuery) or remove the docs references.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At docs/api/other.md, line 3:

<comment>The types `InferFetchQuery` and `InferFetchInfiniteQuery` are documented in the heading and code example but don't exist anywhere in the source code. Users importing them will get TS errors. Add the missing type definitions (analogous to `InferQuery`/`InferInfiniteQuery`) or remove the docs references.</comment>

<file context>
@@ -1,16 +1,18 @@
 # Other
 
-## `InferQuery`, `InferMutation`, `InferInfiniteQuery` types
+## `InferQuery`, `InferMutation`, `InferInfiniteQuery`, `InferFetchQuery`, `InferFetchInfiniteQuery` types
 
 This types are needed to infer some other types from mutations\configs.
</file context>


This types are needed to infer some other types from mutations\configs.

```ts
type MyData = InferMutation<typeof myMutation, "data">;
type MyVariables = InferMutation<typeof myMutation, "variables">;
type MyConfig = InferMutation<typeof myMutation, "config">;
type MyFetchData = InferFetchQuery<typeof myFetchQuery, "data">;
type MyFetchConfig = InferFetchQuery<typeof myFetchQuery, "config">;
```

## `QueryConfigFromFn`, `MutationConfigFromFn`, `InfiniteQueryConfigFromFn`
## `QueryConfigFromFn`, `MutationConfigFromFn`, `InfiniteQueryConfigFromFn`, `FetchQueryConfigFromFn`, `FetchInfiniteQueryConfigFromFn`

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1: The types FetchQueryConfigFromFn and FetchInfiniteQueryConfigFromFn are documented in the heading but don't exist in the source code. Users trying to import them will get TS errors. Add the missing type definitions (analogous to QueryConfigFromFn/InfiniteQueryConfigFromFn) or remove the docs references.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At docs/api/other.md, line 15:

<comment>The types `FetchQueryConfigFromFn` and `FetchInfiniteQueryConfigFromFn` are documented in the heading but don't exist in the source code. Users trying to import them will get TS errors. Add the missing type definitions (analogous to `QueryConfigFromFn`/`InfiniteQueryConfigFromFn`) or remove the docs references.</comment>

<file context>
@@ -1,16 +1,18 @@

-## QueryConfigFromFn, MutationConfigFromFn, InfiniteQueryConfigFromFn
+## QueryConfigFromFn, MutationConfigFromFn, InfiniteQueryConfigFromFn, FetchQueryConfigFromFn, FetchInfiniteQueryConfigFromFn

This types are needed to create configuration types from your functions of your http client
</file context>


</details>


This types are needed to create configuration types from your functions of your http client

Expand All @@ -24,7 +26,7 @@ type Config = MutationConfigFromFn<typeof myApi.createApple>

## `using` keyword

`Query`, `InfiniteQuery`, `Mutation` supports out-of-box [`using` keyword](https://github.com/tc39/proposal-explicit-resource-management).
`Query`, `InfiniteQuery`, `Mutation`, `FetchQuery`, `FetchInfiniteQuery` supports out-of-box [`using` keyword](https://github.com/tc39/proposal-explicit-resource-management).

In your project you need to install babel plugin [`@babel/plugin-proposal-explicit-resource-management`](https://www.npmjs.com/package/@babel/plugin-proposal-explicit-resource-management) to add this support.

Expand Down
Loading
Loading