I'm aiming to build a Typescript library with AJAX calls (by using the fetch API ), that can be used by both client-side (Webpack/Browserify) and back-end developers ( Node ).
However, I can't seem to get the fetch
to compile without errors.
My first attempt has been with isomorphic-fetch
and @types/isomorphic-fetch
. I'm unsure whether the types are complete, but they didn't bring any global variable (they should be bringing fetch, shouldn't they?) .
npm i isomorphic-fetch @types/isomorphic-fetch
index.ts
import 'isomorphic-fetch';
export function execute() {
return fetch('...') ...
}
tsconfig.json
"compilerOptions": {
...
"lib": ["es2015", "es2016", "es2017"]
}
Output:
node_modules/@types/isomorphic-fetch/index.d.ts(8,30): error TS2304: Cannot find name 'fetch'.
src/index.ts(4,25): error TS2304: Cannot find name 'fetch'.
Do I need " dom
"? Apparently, with the dom
lib it does compile and work on both ✓, but I got no control on whether it will actually work on Node. I mean, it will compile whether or not I import 'isomorphic-fetch'
, but if I miss it in will fail on Node without notice.
Also, Node is not " dom
", regardless of me wanting to support browsers as well.
My second attempt has been with whatwg-fetch
.
npm i whatwg-fetch @types/whatwg-fetch
tsconfig.json
"lib": ["es2015", "es2016", "es2017"] // The same.
This one doesn't even pass the compilation phase (regardless of the " dom
" library):
> tsc --watch
node_modules/@types/whatwg-fetch/index.d.ts(11,27): error TS2304: Cannot find name 'window'.
node_modules/@types/whatwg-fetch/index.d.ts(31,25): error TS2304: Cannot find name 'Blob'.
node_modules/@types/whatwg-fetch/index.d.ts(31,64): error TS2304: Cannot find name 'FormData'.
node_modules/@types/whatwg-fetch/index.d.ts(36,21): error TS2304: Cannot find name 'Blob'.
node_modules/@types/whatwg-fetch/index.d.ts(37,25): error TS2304: Cannot find name 'FormData'.
17:31:50 - Compilation complete. Watching for file changes.
With " dom
":
node_modules/typescript/lib/lib.dom.d.ts(9353,11): error TS2300: Duplicate identifier 'Request'.
node_modules/typescript/lib/lib.dom.d.ts(9370,13): error TS2300: Duplicate identifier 'Request'.
node_modules/typescript/lib/lib.dom.d.ts(9375,11): error TS2300: Duplicate identifier 'Response'.
node_modules/typescript/lib/lib.dom.d.ts(9386,13): error TS2300: Duplicate identifier 'Response'.
node_modules/typescript/lib/lib.dom.d.ts(14940,18): error TS2451: Cannot redeclare block-scoped variable 'fetch'.
node_modules/typescript/lib/lib.dom.d.ts(14945,6): error TS2300: Duplicate identifier 'BodyInit'.
node_modules/typescript/lib/lib.dom.d.ts(14966,6): error TS2300: Duplicate identifier 'HeadersInit'.
node_modules/typescript/lib/lib.dom.d.ts(14976,6): error TS2300: Duplicate identifier 'RequestInfo'.
node_modules/typescript/lib/lib.dom.d.ts(15043,6): error TS2300: Duplicate identifier 'ReferrerPolicy'.
node_modules/typescript/lib/lib.dom.d.ts(15044,6): error TS2300: Duplicate identifier 'RequestCache'.
node_modules/typescript/lib/lib.dom.d.ts(15045,6): error TS2300: Duplicate identifier 'RequestCredentials'.
node_modules/typescript/lib/lib.dom.d.ts(15046,6): error TS2300: Duplicate identifier 'RequestDestination'.
node_modules/typescript/lib/lib.dom.d.ts(15047,6): error TS2300: Duplicate identifier 'RequestMode'.
node_modules/typescript/lib/lib.dom.d.ts(15048,6): error TS2300: Duplicate identifier 'RequestRedirect'.
node_modules/typescript/lib/lib.dom.d.ts(15049,6): error TS2300: Duplicate identifier 'RequestType'.
node_modules/typescript/lib/lib.dom.d.ts(15050,6): error TS2300: Duplicate identifier 'ResponseType'.
...
I've also attempted with other similar libraries such as fetch-ponyfill
, but this one doesn't even have types available for TypeScript.
How are we supposed to call fetch
on a universal application (browser + Node)?
Thanks!
我在一个angular(typescript)项目中使用fetch时遇到了同样的错误,我可以通过声明这样的fetch来解决它:
declare var fetch;
To get proper type definitions you have a couple options.
If your TypeScript will be running in the browser :
Add the built-in "DOM" to your compiler libs (either with the --lib
command line compiler option or to lib in tsconfig.json
). Adding "DOM" to libs is probably the right option if you're TypeScript will be running in a modern browser. However, if you're TypeScript is running in a non-browser environment with a fetch module check Option 2.
If your TypeScript will be running on the server (node.js) :
If you're using a library like node-fetch on node, then add the @types/node-fetch type definitions, and import fetch like import fetch from "node-fetch"
If your TypeScript is running in both browser and server (eg for a server-side rendering project) import the DOM lib and you probably want to add the isomorphic-fetch package .
If you are transpiling with the below command:
"ts-watch": "tsc file1.ts file2.ts --watch"
Then remove the individual file declarations and it should work if you have a valid tsconfig.json:
"ts-watch": "tsc --watch"
Here is an example of a working tsconfig:
{
"compilerOptions": {
"outDir": "lib",
"sourceMap": true,
"noImplicitAny": true,
"lib": [
"ES2015",
"DOM"
],
"module": "esnext",
"target": "ES2015",
"strict": true,
"jsx": "react",
"allowJs": true,
"declaration": true,
"moduleResolution": "node",
"typeRoots": [
"node_modules/@types/",
"index.d.ts"
],
"esModuleInterop": true
},
"include": [
"./typescript/**/*",
]
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.