You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
@@ -105,10 +105,10 @@ type Spec = DefineApiEndpoints<{
105
105
}>;
106
106
const fetchT =fetchasFetchT<"", Spec>;
107
107
108
-
awaitfetchT("/users", {}); // OK
109
-
awaitfetchT("/users/1", {}); // OK
110
-
awaitfetchT("/posts", {}); // Error: Argument of type '"/posts"' is not assignable to parameter of type '"/users" | "/users/:id"'.
111
-
awaitfetchT("/users/1/2", {}); // Error: Argument of type '"/users/1/2"' is not assignable to parameter of type '"/users" | "/users/:id"'.
108
+
awaitfetchT("/users"); // OK
109
+
awaitfetchT("/users/1"); // OK
110
+
awaitfetchT("/posts"); // Error: Argument of type '"/posts"' is not assignable to parameter of type '"/users" | "/users/:id"'.
111
+
awaitfetchT("/users/1/2"); // Error: Argument of type '"/users/1/2"' is not assignable to parameter of type '"/users" | "/users/:id"'.
112
112
```
113
113
114
114
### Query
@@ -126,9 +126,9 @@ type Spec = DefineApiEndpoints<{
126
126
}>;
127
127
128
128
const fetchT =fetchasFetchT<"", Spec>;
129
-
awaitfetchT("/users?page=1", {}); // OK
130
-
awaitfetchT("/users", {}); // Error: Argument of type string is not assignable to parameter of type MissingQueryError<"page">
131
-
awaitfetchT("/users?page=1&noexist=1", {}); // Error: Argument of type string is not assignable to parameter of type ExcessiveQueryError<"noexist">
129
+
awaitfetchT("/users?page=1"); // OK
130
+
awaitfetchT("/users"); // Error: Argument of type string is not assignable to parameter of type MissingQueryError<"page">
131
+
awaitfetchT("/users?page=1&noexist=1"); // Error: Argument of type string is not assignable to parameter of type ExcessiveQueryError<"noexist">
132
132
```
133
133
134
134
### headers
@@ -175,6 +175,63 @@ await fetchT("/users", {
175
175
awaitfetchT("/users", { method: "POST", body: JSONT.stringify({ name: 1 }) }); // Error: Type TypedString<{ userName: number; }> is not assignable to type TypedString<{ userName: string; }>
176
176
```
177
177
178
+
### Init
179
+
180
+
zero-fetch enforces type safety for the `init` parameter of the fetch function. The `init` parameter can be omitted only if all of the following conditions are met:
181
+
182
+
- The endpoint defines an HTTP GET method.
183
+
- All request headers defined for the endpoint are optional.
184
+
185
+
If any of these conditions are not satisfied, omitting the `init` parameter will result in a type error.
186
+
187
+
This behavior ensures that the fetch call adheres strictly to the API specification, preventing runtime errors due to missing or incorrect parameters.
188
+
189
+
```typescript
190
+
typeSpec=DefineApiEndpoints<{
191
+
"/users": {
192
+
get: {
193
+
headers: { "x-api-key"?:string };
194
+
responses: { 200: { body: { names:string[] } } };
195
+
};
196
+
};
197
+
"/posts": {
198
+
get: {
199
+
headers: { "x-api-key":string };
200
+
responses: { 200: { body: { posts:string[] } } };
201
+
};
202
+
};
203
+
}>;
204
+
205
+
const fetchT =fetchasFetchT<"", Spec>;
206
+
207
+
awaitfetchT("/users"); // OK, because GET method is defined and headers are optional
208
+
awaitfetchT("/users", { headers: { "x-api-key": "key" } }); // OK
209
+
awaitfetchT("/users", { headers: {} }); // OK, because headers are optional
210
+
awaitfetchT("/users", { method: "POST" }); // Error: POST method is not defined for this endpoint
211
+
212
+
awaitfetchT("/posts"); // Error: "x-api-key" header is required for this endpoint
213
+
awaitfetchT("/posts", { headers: { "x-api-key": "key" } }); // OK
214
+
```
215
+
216
+
```typescript
217
+
typeSpec=DefineApiEndpoints<{
218
+
"/posts": {
219
+
post: {
220
+
body: { title:string };
221
+
responses: { 201: { body: { id:string } } };
222
+
};
223
+
};
224
+
}>;
225
+
226
+
const fetchT =fetchasFetchT<"", Spec>;
227
+
228
+
awaitfetchT("/posts"); // Error: GET method is not defined for this endpoint
@@ -119,8 +120,12 @@ type FetchT<UrlPrefix extends UrlPrefixPattern, E extends ApiEndpoints> = <
119
120
*
120
121
* @template Headers - Request headers object of the endpoint
121
122
*
123
+
* @template CanOmitHeaders - Whether the headers property in the "init" parameter can be omitted
124
+
*
122
125
* @template Body - Request body object of the endpoint
123
126
*
127
+
* @template CanOmitBody - Whether the body property in the "init" parameter can be omitted
128
+
*
124
129
* @template Response - Response object of the endpoint that matches `CandidatePaths`
125
130
*
126
131
* @template ValidatedUrl - Result of URL validation
@@ -134,7 +139,7 @@ type FetchT<UrlPrefix extends UrlPrefixPattern, E extends ApiEndpoints> = <
134
139
* If the endpoint defines a "get" method, then the method can be omitted
135
140
*
136
141
* @template CanOmitInit - Whether the "init" parameter can be omitted for the request
137
-
* If the method can be omitted (`CanOmitMethod` is true)and the endpoint does not require headers, then the "init" parameter can be omitted
142
+
* If the method can be omitted (`CanOmitMethod` is true), headers can be omitted (`CanOmitHeaders` is true), and body can be omitted (`CanOmitBody` is true), then the "init" parameter can be omitted
0 commit comments