chakra-ui / chakra-ui-vue

⚡️ Build scalable and accessible Vue.js applications with ease.
https://vue.chakra-ui.com
MIT License
1.87k stars 136 forks source link

Vetur support for @chakra-ui/vue #46

Open codebender828 opened 4 years ago

codebender828 commented 4 years ago

Is your feature request related to a problem? Please describe. Since Vue component templates in VSCode do not have typescript support, it's difficult to consume component libraries without constantly going to and from in between the docs for autocompletion.

Describe the solution you'd like An extension that suggests component props and types to consumers

Describe alternatives you've considered Vetur extension might be able to support this feature. Should research and compare

phiter commented 4 years ago

Hey!

This is easy to achieve, and I don't think making another extension is the best option. I believe every Vue developer who use VSCode uses Vetur, and vetur has built in support for tag/prop autocomplete.

We need two files, one is called attributes.json and the other is called tags.json.

tags.json holds all the component names. attributes.json holds all the props for all components, their types, possible options, even which package version they were added in.

All of those can also have a description with markdown support (actually there is an open issue about it right now that is not fixed yet).

Here is ElementUI example:

https://github.com/ElementUI/element-helper-json/blob/master/element-attributes.json

https://github.com/ElementUI/element-helper-json/blob/master/element-tags.json

So to make that there are some options.

It could be composed manually, for every component. This can be a burden to keep updated, but I think once every component is there it would make it easier.

Second option is to do something like Vuetify does.
They have an API generator which generates those files automatically.

I think doing something similar to Vuetify is easier to maintain, even though there will be an initial implementation cost.
The vue-styleguidist docgen-api could be used to generate those automatically. Just gotta see how to configure that.

codebender828 commented 4 years ago

Good day, @phiter ! Thank you so much your response towards this. I didn't know that Vetur support that extensive. So there's no need to have a separate VSCode extension for this.

Considering the approaches you've listed, I would recommend to start with the simplest but sufficiently reliable way to implement this. (Manually perhaps). I've already written most component descriptions that I think could go into the tags.json file here:

https://www.notion.so/stellargroup/b379efc7b0f24060b840be7f6c2d0bbb?v=e32ed8a0bce04621975feef3ff344c07

Perhaps this could be starting point.

If you're interested in handling this, I can assign this to you so to determine the best way forward. Let me know how you feel about this 👍

DominusKelvin commented 4 years ago

This is nice. Autocomplete will drive ease of usage and DX.

phiter commented 4 years ago

@codebender828 I made a generator for my company's library, but since it's a starting project, we're making components using .vue files and the docgen handles those files.

I'll see what's the easier and most organized way we can add that to chakra ui.

codebender828 commented 4 years ago

That's great! I'll also try to come up with a few ideas I can share with you to see what you think.

codebender828 commented 4 years ago

Hey @phiter How are you? Been brooding over this idea on how to generate the different component docs for Vetur intellisense support and I think I've come up with an idea.

We could use JSDoc to write the documentation for each component and use that comment block to declare the component props, types and descriptions. During build-time we can then parse the file to extract the comments and parse them for each component to create the element-tags.json and the element-props.json files.

I think this approach doesn't take away from the simplicity of adding to the components API. What do you think? I'm going to make a tiny proof of concept and then see how that will go.

phiter commented 4 years ago

I was thinking... we could have a different approach.

Instead of adding the documentation to the component itself as a comment and have the hassle of parsing it, what if we just add a MyComponent.api.js file in each folder, and export an object from each, with a structure perhaps similar to what is done by vue-styleguidist apidoc?

That would take away the pain of having to make a custom parser and would work just fine.

Only issue is that the file would need to be always up to date with component changes.

Then just look for every *.api.js inside the components folder and loop through them parsing and generating the attributes and tags files.

codebender828 commented 4 years ago

@phiter I like this approach better actually.

About ensuring parity between MyComponent props and the MyComponent.api.js exported object, perhaps we can write tests to ensure that every prop is described in the MyComponent.api.js?

These would change only when modifying the component API. Which is also something that I think would happen rarely. But would be good to have nonetheless.

I appreciate your input towards this. If you want to, let's continue this discussion on discord 😄 https://discord.gg/zkgRfF

callumflack commented 3 years ago

HI @codebender828 can you please post a valid link to the Vue Chakra Discord?

dombavetta commented 3 years ago

@callumflack Heres a Discord invite link for you 😃

lianulloa commented 3 years ago

@codebender828 I am not sure if my problem is directly related with this issue, but I have just create a brand new nuxt.js project, with chakra-ui and typescript and if I set script tag's lang attribute to "ts", then it marks me an error over any use of this.$chakraColorMode(), this.$chakraTheme(), this.$toggleColorMode, this.$toast()

The error: Property '$chakraColorMode' does not exist on type 'CombinedVueInstance<Vue, unknown, unknown, unknown, Readonly<Record<never, any>>>'.Vetur(2339)

Is there any way to work around this??

codebender828 commented 3 years ago

@codebender828 I am not sure if my problem is directly related with this issue, but I have just create a brand new nuxt.js project, with chakra-ui and typescript and if I set script tag's lang attribute to "ts", then it marks me an error over any use of this.$chakraColorMode(), this.$chakraTheme(), this.$toggleColorMode, this.$toast()

The error: Property '$chakraColorMode' does not exist on type 'CombinedVueInstance<Vue, unknown, unknown, unknown, Readonly<Record<never, any>>>'.Vetur(2339)

Is there any way to work around this??

Hi @lianulloa. This seems to be a Typescript issue, and not a Vetur one. Kindly move this to another issue so we can track it separately. 👍🏽

Could you kindly share a link to your repo? I think I have some ideas around extending the Vue global types that could help.

https://vuejs.org/v2/guide/typescript.html#Augmenting-Types-for-Use-with-Plugins

lianulloa commented 3 years ago

@codebender828 I have created issue #469. There I shared a link to the page index from my repo

Pwuts commented 3 years ago

@codebender828 check out class components for Vue, it solves this problem entirely without the need for extra files. I use it all the time and am very glad it exists.

Before:

export default {
  components: {
    OtherComponent,
  },
  computed: {
    whatever() {
      return 1+1;
    }
  },
  data() {
    value: 3
  },
  methods: {
    doSomething() {
      console.log('something');
    }
  }
}

After:

import Vue from 'vue';
import { Component } from 'vue-property-decorator';

@Component({
  components: {
    OtherComponent,
  },
})
export default class MyComponent extends Vue {
  value: number = 3;

  get whatever(): number {
    return 1+1;
  }

  doSomething () {
    console.log('something');
  }
}

Then Vetur has a setting to enable template interpolation so it can also give type hints etc inside the template.

The vue-property-decorator (or nuxt-property-decorator) package also has other really useful decorators like @Watch, @Provide, @ProvideReactive to make life easier.