I am struggling to understand the example of meteor-vue project found here: https://github.com/Akryum/meteor-vue2-example-routing
In particular the line
render: h => h(AppLayout),
in the client/main.js file:
// App layout
import AppLayout from '/imports/ui/AppLayout.vue';
// App start
Meteor.startup(() => {
// Start the router
const router = routerFactory.create();
new Vue({
router,
render: h => h(AppLayout),
}).$mount('app');
});
What is h here?
Is it a function?
Where is it defined and what does it do?
I am guessing that injects the AppLayout vue component inside the root App component being created though this new Vue call but I do not understand the syntax, even after reading the vue docs on render functions. Could anyone clarifies this?
Another question is whether this way to integrate vue with meteor by creating the root app vue component by JavaScript code inside the Meteor.startup object is the only way that works.
Wouldnāt it be possible to simply add an App.vue component in the template/imports/ui/ folder that would look something like:
<template name=āappā>
<app-layout></app-layout>
</template>
<script>
app = new Vue({
el: 'app';
router
})
</script>
?
Or must the code creating the app root instance with the router injected in it must necessarily appear in a Meteor.startup call to link the Vue code to the Meteor code?
I found answer to the first question here: https://github.com/vuejs-templates/webpack-simple/issues/29
In short, this mysterious h
is an alias for the createElement
Vue function that creates a new node in the DOM. It apparently is an compulsory argument to the render lambda that the render option of a Vue instance is expected as value (why it needs to be passed as argument instead of just called inside the render lambda I still donāt get it)
So
h => h(AppLayout)
is just an abbrevation for
createElement => createElement(AppLayout)
Now if you want to stay at the highest possible level of abstraction and hence would like to avoid using render functions, you can substitute
new Vue({
router,
render: h => h(AppLayout),
}).$mount('app');
});
by:
new Vue({
router,
el: 'app',
template: ''<app/>",
components: { AppLayout }
});
BUT, this will only work if you import the development versions of Vue and VueRouter that include the template compiler instead of the production versions that exclude it and thus require the use of a render function.
Hence your imports:
import Vue from 'vueā
import VueRouter from āvue-routerā
must be replaced by:
import Vue from '/node_modules/vue/dist/vue.common.jsā
import VueRouter from ā/node_modules/vue-router/dist/vue-router.common.jsā
1 Like
Great you found the answer @Jacques and thank you for sharing it!
For the sake of completeness Iāll link an article from Sarah Drasner about this: https://css-tricks.com/what-does-the-h-stand-for-in-vues-render-method/
She mentions the Vue Guide and particularly this section: https://vuejs.org/v2/guide/render-function.html#createElement-Arguments where it explains the createElement
's arguments.
Also, maybe best to stick to using the versions that donāt ship the compiler along the rest of the code?