vue-cli: Subtle error when importing typescript definition file into vue file
Version
3.0.0-rc.12
Node and OS info
Node v10.8.0 / Npm 6.3.0 / Linux WS-001 4.17.13-arch1
Steps to reproduce
- vue create test
- Add the following to
srcfolder (a simple typescript declaration file, namedMyEnums.d.ts):
export const enum MyEnums {
C0 = 'ABC',
C1 = 'DEF'
}
- Add the following to
main.tsinsrc:
import { MyEnums } from '@/MyEnums';
interface MyIf {
enums: MyEnums,
name: string,
}
let p0: MyIf = {
enums: MyEnums.C0,
name: 'My name',
}
- Run
npm run serve, and you get the error:
This dependency was not found:
* @/MyEnums in ./src/main.ts
- Rename
MyEnums.d.tstoMyEnums.ts - Run
npm run serve, and everything is fine. - Rename
MyEnums.tstoMyEnums.d.ts - Change the code above to:
import { MyEnums } from '@/MyEnums.d';
interface MyIf {
enums: MyEnums,
name: string,
}
let p0: MyIf = {
enums: MyEnums.C0,
name: 'My name',
}
- Run ‘npm run serve’, and you get the error:
Using 1 worker with 2048MB memory limit
94% after seal
ERROR Failed to compile with 1 errors 5:46:44 PM
error in ./src/MyEnums.d.ts
Module build failed (from ./node_modules/ts-loader/index.js):
Error: Debug Failure. Output generation failed
at Object.transpileModule (/home/user/temp/ts/test/node_modules/typescript/lib/typescript.js:100526:29)
at getTranspilationEmit (/home/user/temp/ts/test/node_modules/ts-loader/dist/index.js:231:74)
at successLoader (/home/user/temp/ts/test/node_modules/ts-loader/dist/index.js:33:11)
at Object.loader (/home/user/temp/ts/test/node_modules/ts-loader/dist/index.js:21:12)
@ ./src/main.ts 10:0-38 12:9-16
@ multi (webpack)-dev-server/client?http://192.168.1.48:8081/sockjs-node (webpack)/hot/dev-server.js ./src/main.ts
Type checking in progress...
No type errors found
Version: typescript 3.0.1
Time: 1984ms
- Even though you get
No type errors found, when you browse to the addresshttp://localhost:8081, you get the report:URIError: Failed to decode param '/%3C%=%20BASE_URL%20%%3Efavicon.ico' ..., and a blank web page.
What is expected?
No error when using typescript definition files with solution
What is actually happening?
The build tools are complaining about missing dependency, or when using more specific path (so that I make sure the path ends in .ts) I get ‘Output generation failed’.
I run into the issue when building my solution, and after pinning it down to my enums, I realized it has something to do with the naming of the definition files ending in .d.ts and not in .ts.
About this issue
- Original URL
- State: closed
- Created 6 years ago
- Reactions: 16
- Comments: 18 (2 by maintainers)
I have run into the same problem. Let me add what I found:
Problem appears only if you have some
enums in your.d.tsfile. It happens becauseenumis not only a type information that can be stripped, but it has some run-time information (I mean enum values).I run several tests for simple TS code with babel@7 transpilation without webpack. And I think I found a reason of the issue.
enums.d.tsintoenums.d.jsimport { SomeEnum } from './enums'; const value: SomeEnum = 2;) then transpiled JS does not have a reference to enum, because babel just strip it. And this case causes no errorsNow it is obvious that JS expects
enums.jsfile, but we have onlyenums.d.js. And here it fails.Well, the core issue is not
vue-cli, but I’m not sure where we should report itThe approach I indicated above only works for development, to fix it in both production and development use:
@OzairP What do you mean that one of your modules doesn’t transpile TS, isn’t webpack doing the transpilation? In any case, a new app created with the CLI will suffer this problem, so this fixes it for the time being.
@ericdfields I’ve ended up with using string unions instead of enums.
For me, code looks cleaner. And TS still gets your back with
Argument of type '"dawn"' is not assignable to parameter of type 'Direction'check. Auto-completion works too. Looks like a great solution.You can’t export any actual JavaScript code from declaration files (
*.d.ts), because TypeScript removes them from the generated output. Here is a playground demo that illustrates what enums are compiled into.More info here: https://lukasbehal.com/2017-05-22-enums-in-declaration-files/
I’ve seen this a few times. I think the right solution (given recent enough typescript, I’m using 4.1.3) is
import type {Prop} from 'vue/types/options'rather thanimport {Prop} from 'vue/types/options', i.e. useimport typewhen you’re only importing types. YMMV but it seems to help for me.I’m encountering this with a codemirror embed in my app. Is there are proper solution at this point?