vuejs / vitepress

Vite & Vue powered static site generator.

Home Page:https://vitepress.dev

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Conflict between native web componentes (eg. Lit or defineCustomElement) and Vite plugin

kaesar opened this issue · comments

Describe the bug

How can I get a good use of Native Web Components (like Vaading/Lit or defineCustomElement) without wanings, errors or conflict ?...

I think found a conflict, or kind of, because I involve between two diferent errors when I try to use native web componentes (eg. Lit or defineCustomElement) and Vite plugin.

First, I get the Warning: Failed to resolve component: as-link. If this is a native custom element, make sure to exclude it from component resolution via compilerOptions.isCustomElement.

Then I set the Vite plugin in the config.mjs file (with app.config.compilerOptions.isCustomElement = tag => tag.includes('-')) and I get the Error: Failed to resolve component: as-link. If this is a native custom element, make sure to exclude it from component resolution via compilerOptions.isCustomElement.

Reproduction

For example, first I try to use Vaadin UI Components that are made with Lit, or simply use a defineCustomElement in Vue like this, my-link.ce.vue:

<script setup>
import '@vaadin/button/vaadin-button.js'

const props = defineProps(['label', 'link'])

function handleButton () {
    location.assign(props.link)
}
</script>

<template>
    <vaadin-button theme="primary" @click="handleButton">{{ label }}</vaadin-button>
</template>

In the index.md file we can have something like this:

---
layout: home
hero:
  name: Lorem Ipsum
  text: Welcome!
---
<my-link label="Next" link="/next"></my-link>

In the .vitepress/theme/index.js I include for example the next code:

import MyLink from '../my-link.ce.vue'
const MyLinkCE = defineCustomElement(MyLink)
customElements.define('my-link', MyLinkCE)

Then I get the Warning in console...
Failed to resolve component: as-link. If this is a native custom element, make sure to exclude it from component resolution via compilerOptions.isCustomElement

Even if use another component in .vitepress/theme/index.js with export default { extends: DefaultTheme, enhanceApp({ app }) { app.component('MyVueTag', MyVueTag) } that include inside vaadin- or my-link I get that Warning

So, I change the .vitepress/config.mjs file including the next code;

import { defineConfig } from 'vitepress'
import vue from '@vitejs/plugin-vue'

export default defineConfig({
  ...
  vite: {
    plugins: [
      vue({
        template: {
          compilerOptions: {
            isCustomElement: tag => tag.includes('-')
          }
        }
      })
    ],
  }
})

But now I get the next Error on loading (and is bloking)...

At least one <template> or <script> is required in a single file component. /home/user/test/node_modules/vitepress/dist/client/theme-default/components/VPTeamMembers.vue

Expected behavior

Native Web Components (like Vaadin/Lit or defineCustomElement) and Vite Plugin works very well with VitePress.

System Info

System:
    OS: Windows 10 10.0.19045
    CPU: (4) x64 Intel(R) Core(TM) i7-6600U CPU @ 2.60GHz
    Memory: 8.76 GB / 15.67 GB
  Binaries:
    Node: 18.18.2 - C:\Apps\laragon\bin\nodejs\node-v18\node.EXE
    npm: 10.5.0 - C:\Apps\laragon\bin\nodejs\node-v18\npm.CMD
    bun: 1.1.4 - ~\.bun\bin\bun.EXE
  Browsers:
    Edge: Chromium (123.0.2420.97)
    Internet Explorer: 11.0.19041.3636
  npmPackages:
    vitepress: ^1.1.4 => 1.1.4

Additional context

I want to include some Native Web Components with Lit (like Vaadin UI Components) or simply defineCustomElement with Vue. This is because I found a way to works with VitePress JAM Stack. VitePress is great, simple and powerful. I think this topic is a great feature also.

Please help me. Thanks.

Validations

vue plugin is already loaded, you're adding it twice. Use vue: { ... } in vitepress config directly instead of re-registering it inside vite - https://vitepress.dev/reference/site-config#vue

That's great, it works. I don't know why I didn't understand this in the docs.
So here is how .vitepress/config.mjs looks now...

import { defineConfig } from 'vitepress'

export default defineConfig({
  ...
  vue: {
    template: {
      compilerOptions: {
        isCustomElement: tag => tag.includes('-')
      }
    },
  }
})

I proceed to close this and apreciate your comment and help.
Thanks