rfcs icon indicating copy to clipboard operation
rfcs copied to clipboard

Question on the general TypeScript support in Vue 3

Open sqal opened this issue 5 years ago • 20 comments

Hi. I have a few questions regarding TypeScript support that will come along with Vue 3.0. I wanted to ask them originally in https://github.com/vuejs/rfcs/pull/42 but I thought my comment would quickly disappear in that thread and maybe other people will have a similar questions so I hope you don't mind me opening a new issue here.

In the section Type Inference you briefly described how type inference will work in the script tag, but all the examples presented there touches only functions composition, type checking props. What I'd like to know is if/how TS will generally work in other parts of Single File Components.

Questions I have at the moment:

  1. Will type inference work in the templates of our .vue components? I guess during development Vetur for VS Code will help us with that, but how will it work during compile time?
  2. Will it be possible to have things like refs, slots strongly typed?

Thank you for reply. I really appreciate it :)

sqal avatar Jun 25 '19 15:06 sqal

I think type inference in template interpolation is related to vuejs/vetur

fuafa avatar Jun 25 '19 15:06 fuafa

@sqal I share the concern with you. :) Previously I tend to choose render functions rather than templates, in order to get full type inference support. However, in vue 3.0 templates will get more performance optimization and generally will be faster then hand-written render functions. That puts typing support in templates vital for me.

beeplin avatar Jun 25 '19 16:06 beeplin

I just confirmed with @octref (author of Vetur) a few days ago - Vetur will be able to leverage the type information of the <script> section to provide autocompletion and type inference in <template>.

yyx990803 avatar Jun 26 '19 01:06 yyx990803

There is already working feature in Vetur for template type checking https://vuejs.github.io/vetur/interpolation.html. And we are planning to make it work on compile time.

As for template type checking, it is still behind an experimental flag. It would be appreciated if you feedback about it. 🙂

ktsn avatar Jun 26 '19 04:06 ktsn

how will it work during compile time?

Vetur will have a CLI version where you can get diagnostics. Normally you would be using one of the editor integration based on VLS so you don't have to run this separately, but you do have the option.

I don't think putting type-checking into the webpack compilation chain (if that's what you mean by "compile time") is an good idea:

  • It doesn't have a good place to surface diagnostics. I hate browser overlays for displaying errors. Editor is the most natural place to surface errors.
  • There's a lot of integrations I have to do directly on TypeScript API for this to work. Doing that all under webpack or a webpack loader is impractical.

But you can put the Vetur CLI as part of your CI.

image

refs, slots strongly typed?

You need to be more specific.

octref avatar Jun 26 '19 18:06 octref

@octref, for example, let's image the following component:

// some-component.vue
<template>
  <section class="some-component">
    <some-input ref="someInput"/>
  </section>
</template>

<script>
import SomeInput from 'components/some-input.vue';

export default {
  components: { SomeInput }
  setup(props, context) {
   context.refs.someInput; // Can `someInput` here have the type of SomeInput imported above?
  }
}
</script>

The thing is that it most likely requires type inference not from pre-set types, but direct type extension of the component from the Vetur's side.

Raiondesu avatar Jul 01 '19 07:07 Raiondesu

I would prefer to see this being integrated into a loader for webpack aswell. Maybe it would be great to integrate it into fork-ts-checker-webpack-plugin as it already does type checking and linting of the script part of SFC's. I know there is the idea to have a CLI version available but I still think it would be better for a few reasons.

  1. Transparency: It will be confusing what loader, plugin or additional step is doing what kind of tests/checks. E.g. I have ts-loader, fork-ts-checker-webpack-plugin and vue-loader running...together with the new additional step it's getting hard to figure out what part of the steps is now taking care of transpilation, what part is taking care of type checking and what part is taking care of linting.

  2. Speed: If fork-ts-checker-webpack-plugin already reads all required files (within an open pull request it even parses SFCs to get the script part) and does typescript magic on them, why not just reuse that file instead of reading and parsing it again.

  3. Bootstrapping: Setting up a vue project with Typescript manually already needs so many different parts. Why introduce even more? Also we don't use any kind of task system like gulp or grunt as all we need is done by webpack in one config. This additional step would require much more additional configuration (for example in package.json in an ugly way for the build script).

  4. Consistency: Using Vetur only in the frontend / IDE is not possible for larger projects. Type checking is an essential part and is required for CI. We need to be able to modify files via a basic editor and after commit the CI Build fails letting us know that we made a mistake instead of deploying unchecked and type broken code. Type checking and linting is already done by fork-ts-checker-webpack-plugin...couldn't this be intergrated there aswell?

...

It doesn't have a good place to surface diagnostics. I hate browser overlays for displaying errors. Editor is the most natural place to surface errors.

That is true for local development. Webpack however is not just a local development tool. It's an essential part to create a CI pipeline.

I have no idea how the template type checking is integrated into vetur but if it's possible I'd suggest to create an additional package that is only responsible for typechecking vue files by feeding it a typescript instance/session and the file/files you want to get diagnostics for (maybe some more infos that are needed). This way webpack loaders/plugins can make use of the same logic and also don't need to reimplement parsing of SFCs themself.

WolfspiritM avatar Sep 02 '19 13:09 WolfspiritM

Does it work in relation between two vue components? Eg. passing the wrong type of prop from one to the other. I haven't been able to get that to work yet...

I was able to make this work via TSX syntax, but not in regular Vue files.

mesqueeb avatar Dec 10 '19 05:12 mesqueeb

Will "type safety in templates during compile time" be a feature of the Vue 3 SFC compiler? I saw on the roadmap that it's being worked on now.

Eg. being notified by the Vue compiler when passing a string as a prop that can only be a number at compile time instead of during run time will be beneficial for all devs I believe. It will be easier to catch bugs without having to manually debug with a browser.

mesqueeb avatar Dec 12 '19 03:12 mesqueeb

I published VTI (Vetur Terminal Interface). Feedback here: https://github.com/vuejs/vetur/issues/1635 You can use it this way:

npm i -g vti
# run this in the root of a Vue project
vti
vti diagnostics

vti

octref avatar Jan 13 '20 09:01 octref

@octref this is pretty cool. Can we make sure this is triggered via an npm script to make sure we cannot eg. commit things with errors.

eg. npm run vti && npm run build and have it abort when there's an error.

mesqueeb avatar Jan 13 '20 10:01 mesqueeb

@mesqueeb https://github.com/vuejs/vetur/issues/1640

It'll print all errors and exit with code 1:

image

The changes are published in 0.0.2. Note that this is not well-tested, and might not be very stable.

octref avatar Jan 13 '20 17:01 octref

@octref this is so smart! It's the same as having type safety in templates as compile time! 😄 I very much appreciate all the hard work!

mesqueeb avatar Jan 13 '20 21:01 mesqueeb

@yyx990803 ignoring Vetur, can you comment on whether TS support in Vue 3 will cover templates, specifically component invocations? Hypothetically if a component knows the types of its props, it should be able to fail at compile time if an invocation's attrs don't match up. I guess maybe that would require the template to also have a lang="ts" equivalent?

maxbogue avatar Jan 13 '20 21:01 maxbogue

@maxbogue unfortunately this can only be done via Vetur/VTI, since Vue's own compiler works on the template only and has no knowledge of type information.

yyx990803 avatar Jan 13 '20 22:01 yyx990803

Presumably it could be done as a plugin, like ForkTsCheckerWebpackPlugin

KaelWD avatar Jan 14 '20 11:01 KaelWD

@yyx990803 Have you considered the possibility to emit TS code from the compiler as Angular does?

cexbrayat avatar Jan 14 '20 15:01 cexbrayat

@cexbrayat technically the code emitted is already valid TS code, since the render function doesn't need any manual type hints.

yyx990803 avatar Jan 20 '20 14:01 yyx990803

I see a couple of old comments suggesting Vetur can take care of the type inference in the template. For VSCode users, there's also Volar that does this.

But, what about those of us who don't use VSCode? PHPStorm / Webstorm doesn't seem to cover this...

Cry0nicS avatar Aug 23 '21 14:08 Cry0nicS

@Cry0nicS WebStorm will support it soon https://twitter.com/PiotrekTomiak/status/1429501676357132288

yyx990803 avatar Aug 24 '21 21:08 yyx990803