{"id":12622,"library":"vue-web-component-wrapper","title":"Vue Web Component Wrapper","description":"vue-web-component-wrapper is a Vue 3 plugin that facilitates the creation of reusable web components (custom elements) from full-fledged Vue applications. The current stable version is 1.7.7, with frequent patch and minor releases addressing bug fixes and introducing new features. This library differentiates itself by providing comprehensive support for the broader Vue ecosystem, including seamless integration with state management (Vuex, Pinia), routing (Vue Router), internationalization (Vue I18n), and validation (VeeValidate). It also offers robust compatibility with popular CSS frameworks like Tailwind CSS, Bootstrap, and Vuetify, alongside support for CSS preprocessors and scoped styles. Key features include Shadow DOM encapsulation, Vue DevTools integration, full slot and `v-model` support, event emitting, `provide`/`inject`, and options for fine-grained control over Shadow DOM behavior and CSS styling (e.g., `:root` to `:host` replacement). It also supports async initialization and loader mechanisms.","status":"active","version":"1.7.7","language":"javascript","source_language":"en","source_url":"https://github.com/EranGrin/vue3-web-component-wrapper#main","tags":["javascript","vue","web-component","custom-element","vue3","vue3-plugin","vue3-web-component-wrapper","vue3-web-component","vue3-custom-element","typescript"],"install":[{"cmd":"npm install vue-web-component-wrapper","lang":"bash","label":"npm"},{"cmd":"yarn add vue-web-component-wrapper","lang":"bash","label":"yarn"},{"cmd":"pnpm add vue-web-component-wrapper","lang":"bash","label":"pnpm"}],"dependencies":[{"reason":"Required as a peer dependency to define and build Vue 3 applications that are subsequently wrapped into web components.","package":"vue","optional":false}],"imports":[{"note":"The primary function used to convert a Vue application instance and a Vue component definition into a custom element. This library is ESM-first, so use `import`.","wrong":"const wrap = require('vue-web-component-wrapper');","symbol":"wrap","correct":"import { wrap } from 'vue-web-component-wrapper';"},{"note":"TypeScript type import for configuring the behavior of the `wrap` function. Use `import type` for type-only imports to ensure proper tree-shaking and bundle size optimization.","symbol":"WebComponentWrapperOptions","correct":"import type { WebComponentWrapperOptions } from 'vue-web-component-wrapper';"},{"note":"While not directly exported by `vue-web-component-wrapper`, `defineComponent` and `createApp` from the `vue` package are fundamental for creating the Vue component and application instance that this wrapper consumes. These should also be imported using ESM syntax.","symbol":"defineComponent, createApp","correct":"import { defineComponent, createApp } from 'vue';"}],"quickstart":{"code":"import { createApp, defineComponent } from 'vue';\nimport { wrap } from 'vue-web-component-wrapper';\n\nconst MyVueComponent = defineComponent({\n  props: {\n    message: String,\n    count: { type: Number, default: 0 }\n  },\n  emits: ['increment'],\n  data() {\n    return {\n      internalCount: this.count\n    };\n  },\n  methods: {\n    increment() {\n      this.internalCount++;\n      this.$emit('increment', this.internalCount);\n    }\n  },\n  template: `\n    <div style=\"padding: 1rem; border: 1px solid #1a73e8; border-radius: 4px; margin-bottom: 1rem;\">\n      <h3>Hello from Vue Web Component!</h3>\n      <p>Prop Message: <strong>{{ message }}</strong></p>\n      <p>Current Count: <strong>{{ internalCount }}</strong></p>\n      <button @click=\"increment\" style=\"padding: 8px 16px; background-color: #4CAF50; color: white; border: none; border-radius: 4px; cursor: pointer;\">Increment Count</button>\n      <slot name=\"footer\"></slot>\n    </div>\n  `,\n});\n\nconst app = createApp(MyVueComponent);\n\nconst WebComponent = wrap(app, MyVueComponent, {\n  props: {\n    message: { type: String, default: 'Default Message' },\n    count: { type: Number, default: 0 }\n  },\n  emits: ['increment'],\n  // Example of wrapper options\n  disableShadowDOM: false, // Keep Shadow DOM for encapsulation\n  replaceCssRootToHost: true // Essential for :root styles within Shadow DOM\n});\n\n// Register the custom element in the browser's CustomElementRegistry\ncustomElements.define('my-vue-counter', WebComponent);\n\n// Example HTML usage:\n// <my-vue-counter message=\"Initial Web Component\" count=\"5\"></my-vue-counter>\n// <my-vue-counter message=\"Another instance with slot content\">\n//   <p slot=\"footer\" style=\"color: gray; font-size: 0.9em;\">This is content for the footer slot.</p>\n// </my-vue-counter>","lang":"typescript","description":"This quickstart demonstrates how to define a basic Vue 3 component, create a Vue application instance from it, and then use `vue-web-component-wrapper` to register it as a custom element. It showcases prop passing, event emitting, and slot handling within the web component context."},"warnings":[{"fix":"Understand the implications of `disableShadowDOM` and `replaceCssRootToHost` options on your component's styling. Adjust the wrapper configuration or component styles to achieve the desired encapsulation or global styling behavior, and thoroughly test for style conflicts.","message":"Careful consideration of CSS scoping is required when utilizing or opting to disable Shadow DOM. By default, styles are encapsulated within Shadow DOM, preventing them from affecting the global document. However, if `disableShadowDOM` is set to `true`, component styles may bleed into the global document. Additionally, the `replaceCssRootToHost` option is crucial for correctly scoping `:root` selectors within Shadow DOM, as `:root` otherwise targets the document root.","severity":"gotcha","affected_versions":">=1.0.0"},{"fix":"Upgrade to `vue-web-component-wrapper@1.7.7` or newer to leverage the built-in CSP `nonce` handling feature. For projects unable to upgrade, ensure your CSP explicitly permits inline styles and scripts, or implement a custom solution for CSP compatibility.","message":"Prior to version 1.7.7, integrating web components created with this wrapper into environments with strict Content Security Policies (CSPs) might have required manual adjustments or led to issues with script and style execution due to the injection of inline styles and scripts. Version 1.7.7 introduced `nonce`/CSP handling to mitigate these problems.","severity":"gotcha","affected_versions":"<1.7.7"},{"fix":"Familiarize yourself with your browser's developer tools settings for inspecting Shadow DOM. Utilize the Vue DevTools extension for component-specific debugging, but be prepared for the added layer of encapsulation when inspecting the DOM structure.","message":"While `vue-web-component-wrapper` includes support for Vue DevTools, debugging components encapsulated within a Shadow DOM can be more challenging than in a standard Vue application. Browser developer tools often require specific settings to inspect Shadow DOM content effectively.","severity":"gotcha","affected_versions":"*"}],"env_vars":null,"last_verified":"2026-04-19T00:00:00.000Z","next_check":"2026-07-18T00:00:00.000Z","problems":[{"fix":"Upgrade to `vue-web-component-wrapper@1.6.9` or newer, which includes a specific fix addressing this warning when building with Vite.","cause":"During the Vite build process, earlier versions of `vue-web-component-wrapper` could trigger warnings related to `__NO_SIDE_EFFECTS__` due to how the package's module side effects were interpreted.","error":"Warning: __NO_SIDE_EFFECTS__ after building with vite"},{"fix":"Upgrade to `vue-web-component-wrapper@1.6.5` or newer to resolve known TypeScript definition issues and ensure proper type inference and compilation.","cause":"Earlier versions of the package had incomplete or incorrect TypeScript type definitions, leading to compilation errors or warnings in TypeScript projects when importing or using its exports.","error":"TypeScript errors when importing package (e.g., 'Cannot find module 'vue-web-component-wrapper' or missing type definitions for exports')"},{"fix":"Upgrade to `vue-web-component-wrapper@1.6.11` or newer. This version includes a fix that addresses issues with slot processing and nested elements when Shadow DOM is disabled.","cause":"A bug existed in earlier versions that specifically affected the processing of slot content, especially with nested elements, when the `disableShadowDOM` option was enabled, leading to incorrect rendering.","error":"Slot content not rendering correctly or unexpectedly disappearing when `disableShadowDOM: true`."}],"ecosystem":"npm"}