Thore
Thore

Reputation: 1838

Easier way to use plugins with the composition api in vue 3

When adding vuex or vue-router as plugin in vue and using the options api you could access these plugins with the this keyword.

main.js

import { createApp } from 'vue';
import i18n from '@/i18n';
import router from './router';
import store from './store';

app.use(i18n);
app.use(store);
app.use(router);

RandomComponent.vue

<script>
    export default {
        mounted() {
            this.$store.dispatch('roles/fetchPermissions');
        },
    }
</script>

The this keyword is no longer available with the composition api which leads to a lot of repetitive code. To use the store, vue-router or the i18n library I have to import and define the following:

RandomComponent.vue with composition api

<script setup>
    import { useStore } from 'vuex';
    import { useRouter } from 'vue-router';
    import { useI18n } from 'vue-i18n';

    const router = useRouter();
    const store = useStore();
    const { t } = useI18n();

    const { handleSubmit, isSubmitting, errors } = useForm('/roles/create', role, CreateRoleValidationSchema, () => {
        store.dispatch('notifications/addNotification', {
            type: 'success',
            title: t('create_success', { field: t('role', 1) }),
        });

        router.push({ name: 'roles' });
    });
</script>

Is there a way to avoid these imports and definitions and have a way to easily use these plugins like I could do with the options api?

Upvotes: 3

Views: 6396

Answers (1)

Roland
Roland

Reputation: 27719

There is no built-in way of doing that in Composition API and script setup.

What you could do is:

Create a plugins.js file that exports common bindings you want to import. For example:

export * from 'vuex'
export * from 'vue-router'
export * from 'vue-i18n'

And then you have only 1 import to do:

<script setup>
    import { useStore, useRouter, useI18n } from './plugins'

    const router = useRouter();
    const store = useStore();
    const { t } = useI18n();

    const { handleSubmit, isSubmitting, errors } = useForm('/roles/create', role, CreateRoleValidationSchema, () => {
        store.dispatch('notifications/addNotification', {
            type: 'success',
            title: t('create_success', { field: t('role', 1) }),
        });

        router.push({ name: 'roles' });
    });
</script>

You can go even further by initiating the plugins like:

import { useStore, useRouter, useI18n } from './plugins'

export function initiateCommonPlugins() {
    const router = useRouter();
    const store = useStore();
    const { t } = useI18n();

    return { router, store, t }
}

And your code then will look like this:

<script setup>
    import { router, store, t } from './initiate-plugins'

    const { handleSubmit, isSubmitting, errors } = useForm('/roles/create', role, CreateRoleValidationSchema, () => {
        store.dispatch('notifications/addNotification', {
            type: 'success',
            title: t('create_success', { field: t('role', 1) }),
        });

        router.push({ name: 'roles' });
    });
</script>

Use unplugin-auto-import plugin

This plugin can eliminate all imports you want and is highly customizable. Haven't tried it yet but I have seen people recommend it.

Stick to Options API

Using Vue 3 doesn't mean that you have to use Composition API for creating components. You can use Options API along with script setup for composables instead of Mixins. So Options API for components, Composition API for reusing code or advanced use-cases.

Upvotes: 5

Related Questions