Functional Component - render function not found - using wepback-simple

Hi all,

So I’m trying to set up a functional component and get more familiar with the render function.

I have a new webpack-simple project setup using the Vue cli.

The only fix I can find for this is using this in the webpack config, which is included in the project by default:

  resolve: {
    alias: {
      'vue$': 'vue/dist/vue.common.js'
    }
  },

But… I’m still getting the ‘Failed to mount component: template or render function not defined.’ error.

Here is what my component look like:

import Vue from 'vue'

Vue.component('header-view', {
    functional: true,
    // To compensate for the lack of an instance,
    // we are now provided a 2nd context argument.
    render: function(createElement, context) {
        // ...
    },
    // Props are optional
    props: {
        // ...
    }
})

which is just the example found here

Any ideas?

that all looks correct (assuming your actual render function returns something…). I would assume the problem is likely higher up the chain. Where do you use that functional component? What does the parent look like? How do you bootstrap your app?

Thank you for the quick reply :slight_smile:

edit: I’m just running ‘npm run dev’ . Aside from the code snippets here, I haven’t modified the webpack-simple project at all.

App.vue:

<template>
  <div id="app">
    <Wrap>
      <img src="./assets/logo.png">
      
    </Wrap>
  </div>
</template>

<script>

import Wrap from './Wrap.vue'

export default {
  name: 'app',
  data () {
    return {
      msg: 'Welcome to Your Vue.js App'
    }
  },
  methods: {
    test() {
    }
  },
  components: {
    Wrap
  }
}
</script>

Wrap.vue:

<template>
  <div id="mainWrap">
      <header>This is some Main Header</header>
      <slot></slot>
      <header-view></header-view>
  </div>
</template>

<script>
import headerView from './Header.js'

export default {
  name: 'app',
  data () {
    return {
      msg: 'Welcome to Your Vue.js App',
      title: 'Functional TItle'
    }
  },
  methods: {

  },
  components: {
    headerView
  }
}

function clickTest() {
  console.log('clicked')
}

</script>

Update: I also tried using header-view directly in App.vue without using the Wrap component. Still no dice.

Here’s the entire code here for convenience: https://github.com/patrickodacre/vue-functional-component-test

oh, so you actually have this code in header,js:

render: function(createElement, context) {
        // ...
    },

Try returning something, at least return null

I’ll see if I find the time tonight to clone and run this on my machine.

Change Header.js to :

import Vue from 'vue'

const headerView =Vue.extend({

    functional: true,
    // To compensate for the lack of an instance,
    // we are now provided a 2nd context argument.
    render: function(createElement, context) {
        return createElement('div','Test')
    },
    // Props are optional
    props: {
        // ...
    }
})

export {headerView}

an import it like this:

Sorry. I was returning something on my first attempt. After slapping a ‘debugger’ in there, I saw the function wasn’t even getting called (because Vue wasn’t seeing it).

And thanks @rmorgen, but that doesn’t work either. It doesn’t look like you can export and import that way.

Yes, you can :slight_smile: .It works perfect in my build. Using your approach in the JS-file throws always the error returning anything from the render-function or not.This is not the point here. Even if I return nothing I get no error-message, because the render-function does exist. The point is that you must export the component as shown when you use it in a plain JS-file, and {import} it.

Ah you are right. I am sorry. I forgot the destructuring assignment on my import statement :stuck_out_tongue:

Yes, I understood the error, thanks, but I’m still not clear on why I couldn’t create a Vue.component.

EDIT:

Figured it out. I wasn’t exporting anything =\ I feel sheepish.

This did the trick:

import Vue from 'vue'

const headerView2 = Vue.component('header-view2', {
    functional: true,
    // To compensate for the lack of an instance,
    // we are now provided a 2nd context argument.
    render: function(createElement, context) {
        // ...
        return createElement('h1', 'testing header 2')
    },
    // Props are optional
    props: {
        // ...
    }
})

export {
    headerView2
}

So let this be the lesson… always EXPORT something you intend to IMPORT :stuck_out_tongue:

It’s magic, isn’t it? :+1:

LOL love it.