Hey everyone, hope you are doing well. I'm officially marking this repository as archived since from the beginning I wasn't able to give this project the love it deserved. All the code here is open source so feel free to fork and use it as you wish. Thanks for your understanding and see you around!
A Vue 3 compatible component to handle cookie consent
- 🔹 Small bundle size (2.2kb minified + gziped)
- 🙅♂️ No external depedencies
- 🤖 Opinated and customizable data structure for the modal content
- 👐 Emit events on user actions so you can use your handlers
- 📱 Default responsive layout
- 🗄️ Highly customizable through slots
- 🚪 Usage of Vue 3 Teleport to render the modal anywhere in your app
- 💅 Write your own CSS or use the default styles
Heavily inspired by Airbnb's cookie consent UI
Check out a demo page using Vue 3, Vite and vue-cookie-comply: DEMO PAGE
This package is only compatible with Vue 3.x
First install vue-cookie-comply
as a dependency of your Vue app:
yarn add vue-cookie-comply
# or
npm install vue-cookie-comply
Then, install vue-cookie-comply
as a plugin wherever you create your Vue app:
import { createApp } from 'vue'
import App from './App.vue'
import VueCookieComply from 'vue-cookie-comply'
import 'vue-cookie-comply/dist/style.css'
const app = createApp(App)
app.use(VueCookieComply)
app.mount('#app')
Don't forget to import the css
file if you want to leverage the default style 😉
Now you're ready to use the component <vue-cookie-comply />
it in your app:
<template>
<main>
<header />
<div />
<vue-cookie-comply
:preferences="preferences"
@on-accept-all-cookies="onAccept"
@on-save-cookie-preferences="onSavePreferences"
/>
<footer />
</main>
</template>
vue-cookie-comply
automatically places the component at the bottom of your page
A string that goes into the component header. It defaults to "Cookie settings".
A string that gives more context to the user about your cookie policies. It defaults to the following text:
We use cookies and similar technologies to help personalize content and offer a better experience. You can opt to customize them by clicking the preferences button.
A string that controls the button label for the preferences button. It defaults to "Preferences".
A string that controls the button label for the acceptance button. It defaults to "Accept All".
An array of objects to display the options of cookie preferences in the modal. The user may or may not be able to interact with a preference option (see isRequired
field):
[
{
title: 'Performance',
description:
'Bla bla serviços que podemos oferecer erviços que podemos oferecer erviços que podemos oferecer erviços que podemos oferecer serviços que podemos oferecer.',
items: [{ label: 'Active', value: 'performance', isRequired: true }],
},
{
title: 'Analytics',
description:
'Bla bla serviços que podemos oferecer erviços que podemos oferecer erviços que podemos oferecer erviços que podemos oferecer serviços que podemos oferecer.',
items: [
{ label: 'GoogleAnalytics', value: 'ga' },
{ label: 'Sentry', value: 'sentry', isEnable: true },
{ label: 'Mapbox', value: 'mapbox' },
{ label: 'New Relic', value: 'newRelic', isEnable: true },
{ label: 'Dog Food', value: 'dogfood' },
],
},
];
Each object is a section of the preference's modal. Each section consists of the following values:
-
title: the cookie preference name to be displayed
-
description: the cookie preference description to be displayed along with the title
-
items: array of objects displaying the preference's options the user may interact with
- label: name of the option
- value: value to be dispatched once the user select this option
- isEnable: if
true
, means the options will be enabled when the user first opens the modal. It defaults tofalse
- isRequired: if
true
, means the preference is obligatory and such cookies cannot be opted out
A string in form of a css selector to target where the preference modal will be placed in your app. It is used for the Teleport
feature of Vue 3. It defaults to body
, but you can attach any selector such as #app
, .my-class
, etc...
This event is dispatched when the user clicks the Accept All
button. You can call your own handler to do whatever you might do in this case:
<template>
<vue-cookie-comply
:preferences="preferences"
@on-accept-all-cookies="onAccept"
/>
</template>
<script>
export default {
methods: {
onAccept() {
console.log('User has accepted all cookies')
}
}
}
</script>
After on-accept-all-cookies
is dispatched, a item with key cookie-comply
is placed in the localStorage
, with the value all
. You can use the presence of this key and value to do some logic on the client. Once the cookie-comply
key exists in the localStorage
, the vue-cookie-comply
won't show anymore in the page.
This event is dispatched when the user open the modal and saves their preferences. The handler will receive an Array containing the values
of preferences the user opted in:
<template>
<vue-cookie-comply
:preferences="preferences"
@on-save-cookie-preferences="onSavePreferences"
/>
</template>
<script>
export default {
methods: {
onSavePreferences(preferences) {
console.log(preferences) // ['performance', 'ga', 'newRelic']
}
}
}
</script>
After on-save-cookie-preferences
is dispatched, a item with key cookie-comply
is placed in the localStorage
, with the value of an array containing the values the user opted in, eg. ['performance', 'ga', 'newRelic']
. You can use the presence of this key and value to do some logic on the client. Once the cookie-comply
key exists in the localStorage
, the vue-cookie-comply
won't show anymore in the page.
You can use slots to leverage composition and customize vue-cookie-comply
with your own components. If the slots are not used, it will default to the internal components.
<vue-cookie-comply
:preferences="preferences"
@on-accept-all-cookies="onAcceptAll"
@on-save-cookie-preferences="onSavePreferences"
>
<template v-slot:header>
<header>Custom header</header>
</template>
<template v-slot:modal-header>
<h3>My custom modal header</h3>
</template>
<template v-slot:modal-body="{ preference, index }">
<div>{{ preference.title }}</div>
</template>
<template v-slot:modal-footer>
<footer>
My custom modal footer
</footer>
</template>
</vue-cookie-comply>
There are 4 slots to be customized: v-slot:header
, v-slot:modal-header
, v-slot:modal-body
, v-slot:modal-footer
.
Note that v-slot:modal-body
is a scoped slot so you can have access to the preference's values 🤩.
Since the modal it's using the Vue Teleport feature and it targets the <body>
tag by default, if you have any global styles make sure they are applied to the body, so the modal can inherit styles such as font-family, color, etc..
body {
font-family: Avenir, Helvetica, Arial, sans-serif;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
text-align: center;
color: #2c3e50;
margin-top: 60px;
}
Feel free to open an issue with bugs, suggestions for features, enhancements, weird behaviours, questions and more. Also, feel more than welcome to open an PR to fix something you came across or improve the code 🚀