The Wayback Machine - https://web.archive.org/web/20201214202209/https://github.com/vuejs/vue-class-component/issues/406
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

[Vue v3] Changes for @Component decorator and Vue base class #406

Open
ktsn opened this issue Mar 19, 2020 · 17 comments
Open

[Vue v3] Changes for @Component decorator and Vue base class #406

ktsn opened this issue Mar 19, 2020 · 17 comments
Labels

Comments

@ktsn
Copy link
Member

@ktsn ktsn commented Mar 19, 2020

Summary

  • @Component will be renamed to @Options.
  • @Options is optional if you don't declare any options with it.
  • Vue constructor is provided from vue-class-component package.
  • Component.registerHooks will move to Vue.registerHooks

Example:

<template>
  <div>{{ count }}</div>
  <button @click="increment">+1</button>
</template>

<script>
import { Vue, Options } from 'vue-class-component'

// Component definition
@Options({
  // Define component options
  watch: {
    count: value => {
      console.log(value)
    }
  }
})
export default class Counter extends Vue {
  // The behavior in class is the same as the current
  count = 0

  increment() {
    this.count++
  }
}
</script>
// Adding lifecycle hooks
import { Vue } from 'vue-class-component'

Vue.registerHooks([
  'beforeRouteEnter',
  'beforeRouteLeave',
  'beforeRouteUpdate'
])

Details

As Vue v3 no longer provides base Vue constructor, Vue Class Component will provide it instead. Fortunately, we can add class component specific features in the base class as we define it in Vue Class Component package.

One of the benefits with the new Vue constructor is we can make @Component decorator optional. There were non-trivial number of confusions regarding missing @Component decorator in super class / mixins (e.g. #180). Making decorator optional would solve this problem.

Also renaming @Component with @Options would make more sense as it is for adding component options to your class components rather than making a class component.

Since @Options is optional, having registerHooks on the decorator will not work. So we will move the method under static field of Vue constructor.

Alternative approach

Declaring component options as static properties

We could do this to define class component options:

export default class Counter extends Vue {
  // All component options are static properties
  static watch = {
    count: value => {
      console.log(value)
    }
  }

  count = 0

  increment() {
    this.count++
  }
}

But it has a drawback: we cannot define static properties / methods not for component options both on userland and library side. e.g. we cannot define static method like registerHooks on Vue.

@ktsn ktsn pinned this issue Mar 19, 2020
@sodatea
Copy link
Member

@sodatea sodatea commented Mar 19, 2020

Seems some of the breaking changes may not be fully covered with a codemod.
Is it possible to implement a runtime compatibility layer on top of it in vue-property-decorator?

@ktsn
Copy link
Member Author

@ktsn ktsn commented Mar 19, 2020

Yes, we can provide a runtime compatibility layer. Just wrapping Options with Component as Options provides almost the same API interface and feature with the current Component.

Maybe providing Options and Vue from vue-class-component with minor update would help to migrate.

@nicolidin
Copy link

@nicolidin nicolidin commented Mar 24, 2020

Is there a way to already test it with the vuejs/composition-api ??
Thanks!

@ktsn
Copy link
Member Author

@ktsn ktsn commented Mar 25, 2020

I'm going to create a bridge api for composition functions in a separated issue. -> Edit: created #416

@ktsn ktsn added the v8 label Apr 12, 2020
@ktsn ktsn mentioned this issue Apr 26, 2020
@the-emerald
Copy link

@the-emerald the-emerald commented May 30, 2020

Does the abandonment of the Class API proposal have any affect on this package and whether it would be maintained at the same level in the future? Cheers.

@HIMISOCOOL
Copy link

@HIMISOCOOL HIMISOCOOL commented Jun 18, 2020

Does the abandonment of the Class API proposal have any affect on this package and whether it would be maintained at the same level in the future? Cheers.

nope, from what I understand this package will always exist and will always have 1st party package status, its just not practical for the base vue package to use classes in todays world.

@LifeIsStrange
Copy link

@LifeIsStrange LifeIsStrange commented Oct 9, 2020

@ktsn So we did try the latest vue class component beta and while the new props declaration is working just fine, we need to have Watch, Provide and other related Vue features.
Putting watch in @options works but is not expressive enough at all. The static alternative is not yet implemented but would suffer the same issue being static ?

The issue is that we were able to access the class variables through this inside the method that react to the thing it watch.
This expressivity is needed for a lot of behavior and we are unable to migrate to Vue3 until this crucial limitation is fixed.

@calebeaires
Copy link

@calebeaires calebeaires commented Oct 18, 2020

@LifeIsStrange like you, our team share with those concerns. Waiting for an update!

@iklemm
Copy link

@iklemm iklemm commented Nov 1, 2020

Seems that this new API does not match with documentation https://class-component.vuejs.org which is very confusing.

@Chris2011
Copy link

@Chris2011 Chris2011 commented Nov 8, 2020

@LifeIsStrange I think having Watch and Provide and other decorators for class methods and fields are part of vue-property-decorators, isn't it?

Already mentioned in the documentation: You may also want to check out the @Prop and @Watch decorators provided by Vue Property Decorator.

@LifeIsStrange
Copy link

@LifeIsStrange LifeIsStrange commented Nov 8, 2020

@Chris2011
Vue property decorator has not be ported to vue 3 and nobody is working on it for the foreseeable future. This is very worrying for the industry.

@Chris2011
Copy link

@Chris2011 Chris2011 commented Nov 8, 2020

@LifeIsStrange well, vue-property-decorator depends on vue-class-component, so I guess they will farely wait for the new version 8 of this package here. :). Just my opinion, no insides.

@calebeaires
Copy link

@calebeaires calebeaires commented Nov 8, 2020

Hope this situation changes. This two libs belongs to the top of mind of the Vue community!

@LifeIsStrange
Copy link

@LifeIsStrange LifeIsStrange commented Nov 8, 2020

@Chris2011 that's not how it should work, they should begin working on it while it's in beta. If they need to do some breaking changes to vue class component it will be too late after a stable release

@ZhengXingchi
Copy link

@ZhengXingchi ZhengXingchi commented Dec 1, 2020

how can we modify a msg in watch method like that

image

<template>
  <div>{{ count }}</div>
  <button @click="increment">+1</button>
</template>

<script>
import { Vue, Options } from 'vue-class-component'

// Component definition
@Options({
  // Define component options
  watch: {
    count: value => {
      console.log(value)
      if(value==10){
        this.msg='计数超过10了'
      }
    }
  }
})
export default class Counter extends Vue {
  // The behavior in class is the same as the current
  count = 0
  msg=''

  increment() {
    this.count++
  }
}
</script>
@ZhengXingchi
Copy link

@ZhengXingchi ZhengXingchi commented Dec 1, 2020

@ygj6
Copy link

@ygj6 ygj6 commented Dec 8, 2020

@ZhengXingchi this cannot be used in arrow functions, the following code is work
watch: {
count( value) {
console.log(value)
if(value==10){
this.msg='计数超过10了'
}
}
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Linked pull requests

Successfully merging a pull request may close this issue.

None yet
You can’t perform that action at this time.
Morty Proxy This is a proxified and sanitized view of the page, visit original site.