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

Make directives available to all components within a render tree #6732

Closed
trainiac opened this issue Oct 2, 2017 · 3 comments
Closed

Make directives available to all components within a render tree #6732

trainiac opened this issue Oct 2, 2017 · 3 comments

Comments

@trainiac
Copy link

trainiac commented Oct 2, 2017

What problem does this feature solve?

If you have a directive that relies on a piece of user data (e.g. language), in server side rendering you need to be able to create a new directive per request.

const getTranslateDirective = lang => ( {
  bind () {
    // access to lang
  },
  update () {
    // access to lang
  }
})

const translate = getTranslateDirective(() => parsedLangHeader.language)

// PROBLEM - this sets translate a directive globally across reqeusts
Vue.directive('translate', translate)

However this is a problem because when you call Vue.directive('translate', translate) this changes the translate directive across ALL requests.

What does the proposed API look like?

What is needed is a way to make directives available to a component and all of it's children components

const getTranslateDirective = lang => ( {
  bind () {
    // access to lang
  },
  update () {
    // access to lang
  }
})

const translate = getTranslateDirective(() => parsedLangHeader.language)

new Vue({
  directives: {
    translate: {
      module: translate,
      provide: true // Makes the directive available to this component and all of it's children.
    }
  }
})
@yyx990803
Copy link
Member

FYI directives on the server needs to be implemented in a completely different fashion (as VNode transforms) because there's no DOM access: https://ssr.vuejs.org/en/api.html#directives

Also, I don't see the point of creating fresh directive instances for each request. You should somehow inject parsedLangHeader.language into your app as a piece of application state so it can be accessed across the app instance for that request.

@trainiac
Copy link
Author

trainiac commented Oct 2, 2017

@yyx990803 Thanks for taking the time to review this. When you say

You should somehow inject parsedLangHeader.language into your app as a piece of application state so it can be accessed across the app instance for that request.

I think for most cases that is appropriate but consider this example.

The desired translation directive is

<!-- The language is implicit -->
<div v-translate>Hello</div>

I could do this instead

<div v-translate='$store.state.language'>Hello</div>

But this feels very verbose to have to do all over the application.

Given Vue's exsiting API I dont see how you can avoid this.

I understand directives don't have DOM access on the server, but my feature request (most likely naive) is to make it easy to provide the application state to a directive at creating time per request so it doesnt have to be passed into the directive throughout the entire application

@trainiac
Copy link
Author

It looks like this might be solved with vuejs/rfcs#29

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

No branches or pull requests

2 participants