Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add Typescript support in a few places #7

Closed
mds1 opened this issue Jun 26, 2020 · 5 comments · Fixed by #21
Closed

Add Typescript support in a few places #7

mds1 opened this issue Jun 26, 2020 · 5 comments · Fixed by #21
Labels
dev deployment, devops, codebase hygiene, or dev hapiness changes

Comments

@mds1
Copy link
Contributor

mds1 commented Jun 26, 2020

Files lacking Typescript support or that need TS updates:

  • components.js should be components.ts
  • BaseInput.vue watcher should be updated to remove eslint-disable
  • Calls to this.$router.push({...}) currently use eslint-disable-line to avoid no-unsafe-member-access
  • Calls to notifyUser use eslint-disable-line to avoid no-unsafe-call
@apbendi apbendi added the dev deployment, devops, codebase hygiene, or dev hapiness changes label Jul 3, 2020
@mds1
Copy link
Contributor Author

mds1 commented Jul 6, 2020

Overview

So it seems the root cause of our various problems is simply that TS support for Vue CLI 2 and Vuex 3 (the state management module) is lacking. When Vue CLI 3 and Vuex 4 are released (supposed to happen this summer), there will be full TS support.

Below are the options I see and the one that seems best to me.

Note that as far I can tell from testing, these tradeoffs only apply to *.vue files. This means that if we keep all the core logic outside of *.vue files, such as in wallet.ts, then we'll still have proper type checking in the most important parts of the code.

Options

No Changes

Keep our current architecture. In this approach, we will turn off the no-unsafe-any family of rules for *.vue files.

Pros:

  • Easy and fast

Cons:

  • We’ll lose a lot of the TS benefits within Vue components (but still will have type checking in the core logic in *.ts files

Change Component API

Right now we use what's called the "Options API" in Vue components. I initially went with this because it's a very popular and familiar API. If we switch to the "Composition API", this will remove most lint errors in the *.vue files. The only remaining lint errors will be when accessing the global state (specifically, it thinks the store is the any type, because of the fact that Vuex 3 doesn't have good TS support). We'll be accessing the global state often, so will either have to (1) use an approach similar to above and disable any checks in *.vue files, or (2) disable individual lines as they arise (and there will be a lot of them)

This happens because Vuex 3 does not properly support typing, as explained in this issue.

Pros:

  • The only lint errors in *.vue files will be when accessing the store
  • Easies upgrade path to full type checking with Vue CLI 3 and Vuex 4 once they are released and ready

Cons:

  • May end up being functionally the same as above approach after disabling lint rules
  • Time cost of switching
  • The Composition API does not exist natively in Vue CLI 2, so we're using the @vue/composition-api package to enable this. This package is close to—but not quite—production ready. There are people using it in production, and it's anticipated to be production ready in about a month.

I tested this out on a small project this weekend, and you can see the code here. Since our current project is fairly simple, I think we can migrate to the new format over in about 4 hours, maybe 6 if things go wrong.

Change Component API, and use our own store

This builds upon the above approach. To work around the lack of type support in Vuex 3, some people opt to write their own state management module. I think this is probably not worth the development effort, but wanted to mention it for completeness.

Pros:

  • Full TS support

Cons:

  • Much bigger development cost to switching

@Hawxy
Copy link

Hawxy commented Jul 6, 2020

Sorry for butting in here, I was just reading the Vuex issue thread you linked and clicked on the referenced comments to see what other repos were saying and doing about it.

I've been doing Vue + TS for a while so I wanted to offer my two cents:

  • It looks like you guys are using Quasar so you'll probably be stuck on Vue 2 until Quasar is updated to support Vue 3
  • The Vue + TS story isn't great and the Options API is by far the most soul-crushing way to do it (seriously it sucks). Have you considered using class-style components? Most of the TS community currently uses the vue-class-component package and its extension vue-property-decorator as they offer the best development experience (not perfect) & least overall friction. This option will continue to be officially supported by Vue 3.
  • If you're comfortable with the Composition API already then by all means give it a go as you'll be in a great position for Vue 3. The only issue you might encounter would be community packages that are incompatible with it for whatever reason.
  • To solve Vuex's typing problems (and, imo, some of its developer experience problems) you might want to look into community packages like vuex-module-decorators or vuex-smart-module.

Hopefully this is useful, and good luck with your project 👍

@mds1
Copy link
Contributor Author

mds1 commented Jul 6, 2020

Thanks @Hawxy, really appreciate your help here—this is super helpful information!

I certainly didn't realize how messy the Options API would be when we started this. I've been using Vue for a while but this is the first time attempting TS integration, and it's definitely been trickier to setup than I expected.

To solve Vuex's typing problems (and, imo, some of its developer experience problems) you might want to look into community packages like vuex-module-decorators or vuex-smart-module.

These packages look great! Definitely will look into them. When trying the composition API it seems the only remaining type issues were the fact that the store was of the any type, so these seem super useful.

Most of the TS community currently uses the vue-class-component package and its extension vue-property-decorator as they offer the best development experience (not perfect) & least overall friction. This option will continue to be officially supported by Vue 3.

This is good to know—I hadn't realized this was the most popular approach for TS integration. Are there any differences to be aware of with the class-style components vs. composition API? I'm mostly curious in terms of TS support, though I haven't used the class style components so am wondering if there's any other tradeoffs to consider.

@Hawxy
Copy link

Hawxy commented Jul 7, 2020

Are there any differences to be aware of with the class-style components vs. composition API?

I'll delegate this to the Composition RPC:
https://composition-api.vuejs.org/#better-type-inference
https://composition-api.vuejs.org/#type-issues-with-class-api

I personally find class-style components a very natural way of building components, since you're just writing functions, properties and getters within a class as you would in other OO languages (my background is C#) without needing to conform with vue-specific object syntax. There are definitely edge-cases with its type safety but it generally works well for myself and my team (and I'd rather not force everyone to learn the Comp API right now).

The Composition API is the future of Vue component building, but the somewhat steeper learning curve compared to Options/Class-Component means the other component styles will be sticking around for a while. It's up to you if you want to use it now or wait for Vue 3 to release and the ecosystem to catch up.

I'd probably just recommend spiking a component using both styles and seeing what yourself and your team are the most comfortable with.

@mds1
Copy link
Contributor Author

mds1 commented Jul 8, 2020

Awesome, this is all really helpful info. Thanks so much for helping us get pointed in the right direction!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
dev deployment, devops, codebase hygiene, or dev hapiness changes
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants