Jest unit tests in Shopware Plugin's administration
Tags: shopware, plugin, jest, ecommerce
Published: 2022-04-27 17:33:49

---
title: Jest unit tests in Shopware Plugin's administration
published: true
description: How to setup Jest tests in Shopware Plugin
tags: shopware, plugin, jest, ecommerce

---

## Table of Contents

- [What is Shopware?](#what-is-shopware)
- [Folder structure](#folder-structure)
- [Installation](#installation)
- [Setup](#setup)
- [Writing Test](#writing-test)
- [Running Test](#running-test)

---

## What is Shopware?

[Shopware 6](http://shopware.com/) is an open commerce platform based on Symfony Framework and Vue and is supported by a worldwide community and more than 1.500 community extensions.

## Folder structure

The test folder structure should match the source folder structure. You add a test for a file in the same path as the source path.

```html
└── <pluginRoot>/src/Resources/app/administration
    ├── src
    │   └── module
    │       └── custom-cms
    │          └── component
    │              └── custom-cms-sidebar
    │                  ├── index.js
    │                  └── custom-cms-sidebar.html.twig
    ├── test
    │   ├── _mocks_
    │   │   └── entity-schema.json
    │   │ 
    │   └── module
    │       └── custom-cms
    │           └── component
    │               └── custom-cms-sidebar.spec.js
    │
    ├── babel.config.json
    ├── jest.config.js
    └── package.json
```

## Installation

Let’s grab all the dependencies we will need for the setup in `package.json`

```json
{
    // ...
    "devDependencies": {
        "@babel/plugin-proposal-class-properties": "^7.16.7",
        "@babel/plugin-transform-runtime": "7.13.15",
        "@babel/preset-env": "7.13.15",
        "@shopware-ag/jest-preset-sw6-admin": "^2.0.1",
        "@vue/test-utils": "1.1.0",
        "jest": "26.4.2"
    }
}
```

@shopware-ag/jest-preset-sw6-admin

> Default Jest preset for Shopware 6 administration development.

@vue/test-utils

> We are using the Vue Test Utils for easier testing of Vue components. It provides some methods to mount and interact with Vue components in an isolated manner.

## Setup

After installing the required dependency packages, please create a file called `babel.config.json` right next to your own package.json with the following content:

```json
{
    "presets": ["@babel/preset-env"],
    "plugins": [
        "@babel/plugin-transform-runtime",
        "@babel/plugin-proposal-class-properties"
    ]
}
```

Next up, create a file `jest.config.js` which should contain the following content:

```js
const { resolve, join } = require('path');

const ADMIN_PATH = resolve('../../../../vendor/shopware/administration/Resources/app/administration');
process.env.ADMIN_PATH = process.env.ADMIN_PATH || ADMIN_PATH;

module.exports = {
    preset: '@shopware-ag/jest-preset-sw6-admin',

    globals: {
        adminPath: process.env.ADMIN_PATH,
    },

    collectCoverageFrom: [
        'src/**/*.js',
    ],

    moduleNameMapper: {
        '^plugin-admin(.*)$': '<rootDir>$1',
        '\@vue/test-utils': '<rootDir>/node_modules/@vue/test-utils',
        '../../_mocks_/entity-schema.json': '<rootDir>/test/_mocks_/entity-schema.json',
    },

    setupFilesAfterEnv: [
        resolve(join(process.env.ADMIN_PATH, 'test/_setup/prepare_environment.js')),
    ],
};
```

The file `entity-schema.json` could be generated by running this command:
```bash
bin/console framework:schema -s 'entity-schema' custom/plugins/<your_plugin>/src/Resources/app/administration/test/_mocks_/entity-schema.json
```

## Writing Test

> We are using a global object as an interface for the whole administration. Every component gets registered to this object, e.g. Shopware.Component.register(). Therefore, we have access to Component with the Shopware.Component.build() method. This creates a native Vue component with a working template. Every override and extension from another component are resolved in the built component.

Your component might look like this:

```js
// src/module/custom-cms/component/custom-cms-sidebar/index.js
Component.extend('custom-cms-sidebar', 'sw-cms-sidebar', {
    // The vue component
});
```

Create test file `custom-cms-sidebar.spec.js` for `custom-cms-sidebar` component.

When you want to mount your component it needs to be imported first:

```js
import 'plugin-admin/src/module/custom-cms/component/custom-cms-sidebar';
```

Then import it's related components:

```js
import 'src/module/sw-cms/mixin/sw-cms-state.mixin';
import 'src/module/sw-cms/component/sw-cms-sidebar';
import 'src/app/component/base/sw-button';
```

In the next step we can mount our Vue component which we get from the global Shopware object:

```js
shallowMount(Shopware.Component.build('custom-cms-sidebar'));
```

Now you can test the component like any other component. Let's try to write our first test:

```js
import { shallowMount } from '@vue/test-utils';
import 'src/module/sw-cms/mixin/sw-cms-state.mixin';
import 'src/module/sw-cms/component/sw-cms-sidebar';
import 'src/app/component/base/sw-button';

import 'plugin-admin/src/module/custom-cms/component/custom-cms-sidebar';

function createWrapper() {
    return shallowMount(Shopware.Component.build('custom-cms-sidebar'), {
        propsData: {
            page: {
                sections: []
            }
        },
        stubs: {
            'sw-button': Shopware.Component.build('sw-button'),
            'sw-sidebar': true,
            'sw-sidebar-item': true,
            'sw-sidebar-collapse': true,
            'sw-text-field': true,
            'sw-select-field': true,
            'sw-cms-block-config': true,
            'sw-cms-block-layout-config': true,
            'sw-cms-section-config': true,
            'sw-context-button': true,
            'sw-context-menu-item': true,
            'sw-cms-sidebar-nav-element': true,
            'sw-entity-single-select': true,
            'sw-modal': true,
            'sw-checkbox-field': true
        },
        provide: {
            repositoryFactory: {
                create: () => ({
                    create: () => ({
                        id: null,
                        slots: []
                    }),
                    save: () => {}
                })
            },
            cmsService: {
                getCmsBlockRegistry: () => ({
                    'foo-bar': {}
                })
            }
        }
    });
}

describe('module/custom-cms/component/custom-cms-sidebar', () => {
    beforeAll(() => {
        Shopware.State.registerModule('cmsPageState', {
            namespaced: true,
            state: {
                isSystemDefaultLanguage: true
            }
        });
    });

    it('should be a Vue.js component', async () => {
        const wrapper = createWrapper();

        expect(wrapper.vm).toBeTruthy();
    });
});
```

## Running Test

Create a script in `package.json`

```json
"scripts": {
    "jest": "jest --config=jest.config.js",
}
```

Open a terminal and run this command:

```bash
npm run jest
```

---

*I hope this post helps you with the config testing environment for your plugin. I am really happy to receive your feedback on this article. Thanks for your precious time reading this.*

**Source:** https://viennt.me/jest-unit-tests-in-shopware-plugins-administration