Как организовать Vue юнит-тест с заводскими функциями? - PullRequest
1 голос
/ 29 октября 2019

Я пытаюсь написать модульные тесты для моего Dashboard.vue компонента, используя заводские функции, чтобы я мог перезаписать store и wrapper в соответствии с необходимостью.

Вот код

import { mount, createLocalVue } from '@vue/test-utils'
import mergeWith from 'lodash.mergewith'
import mutationobserver from 'mutationobserver-shim'
import Vuex from 'vuex'
import BootstrapVue from 'bootstrap-vue'
import Dashboard from '@/views/dashboard/Dashboard'
import { FontAwesomeIcon } from '@fortawesome/vue-fontawesome'
import { library as faLibrary } from '@fortawesome/fontawesome-svg-core'
import { faUser, faThumbsUp, faSignOutAlt, faBorderAll, faAlignJustify, faTrashAlt, faRandom } from '@fortawesome/free-solid-svg-icons'
import flushPromises from 'flush-promises'

jest.mock('@/services/app.service.js')

faLibrary.add(faUser, faThumbsUp, faSignOutAlt, faBorderAll, faAlignJustify, faTrashAlt, faRandom)

const localVue = createLocalVue()
localVue.use(Vuex)
localVue.use(BootstrapVue)
localVue.use(mutationobserver) // This is a necessary polyfill for Bootstrap-Vue
localVue.component('font-awesome-icon', FontAwesomeIcon)

function customizer (ovjValue, srcValue) {
  /*
      If the property that takes precedence is an array,
      overwrite the value rather than merging the arrays
    */
  if (Array.isArray(srcValue)) {
    return srcValue
  }
  /*
      If the property that takes precedence is an empty object,
      overwrite the property with an empty object
     */
  if (srcValue instanceof Object && Object.keys(srcValue).length === 0) {
    return srcValue
  }
}

describe('DashBoard component tests', () => {
  let state
  // let actions
  // let getters
  let store
  let wrapper

  let dashBoardData = [
    { db_name: 'Jobs', dxp_dashboardref: 1, dxp_hidden: 0, dxp_position: 1, dxp_ref: 926 },
    { db_name: 'Firms', dxp_dashboardref: 2, dxp_hidden: 0, dxp_position: 2, dxp_ref: 927 },
    { db_name: 'CRM', dxp_dashboardref: 5, dxp_hidden: 0, dxp_position: 3, dxp_ref: 987 }
  ]

  // beforeEach(() => {
  state = {
    auth: {
      user: {
        auids: '',
        md_clock: 0,
        md_picture: '',
        ps_fname1: '',
        ps_surname: '',
        psname: 'Test Test',
        psref: 0
      }
    },
    app: {
      dashBoardData: []
    }
  }

  function createStore (overrides) {
    const defaultStoreConfig = {
      // state: {
      //   state
      // },
      getters: {
        getDashBoardData: () => dashBoardData
      },
      actions: {
        loadDashboard: jest.fn(),
        updateDashBoardData: jest.fn()
      }
    }
    return new Vuex.Store(
      state,
      mergeWith(defaultStoreConfig, overrides, customizer)
    )
  }

  function createWrapper (overrrides) {
    const defaultMountingOptions = {
      localVue,
      store: createStore()
    }
    return mount(
      Dashboard,
      mergeWith(
        defaultMountingOptions,
        overrrides,
        customizer)
    )
  }

  // START: Testing existence of DOM Elements tests
  it('is a Vue instance', () => {
    const wrapper = createWrapper({})
    expect(wrapper.isVueInstance).toBeTruthy()
  })
})

По сути, я пытаюсь использовать метод createWrapper, который имеет хранилище по умолчанию, если не переданы overrides или customizer. Когда я запускаю тест, я получаю следующие ошибки

console.error node_modules / vuex / dist / vuex.common.js: 899

[vuex] неизвестный получатель: getDashBoardData

console.error node_modules / vue / dist / vue.runtime.common.dev.js: 621

[Vue warn]: ошибка при рендеринге: «TypeError: Невозможно прочитать свойство« length »из неопределенного«

Теперь у меня два вопроса:

  1. Почему меня бросают unknown getter, когда я объявил это в defaultStoreConfig?
  2. Вторая ошибка происходит от state. По какой-то причине он не распознает переменную состояния, которую я передаю. Есть идеи, почему?

Если я просто объявлю обертку внутри beforeEach, как, например, я могу пройти некоторые из моих испытаний, но для других, которые мне нужно перезаписать либо getters или actions,Я не могу этого сделать, если у меня нет заводских функций

    getters = {
      getDashBoardData: () => dashBoardData
   },
    actions = {
    loadDashboard: jest.fn(),
    updateDashBoardData: jest.fn()
  }

  store = new Vuex.Store({
    state,
    actions,
    getters
  })
  })

Любая помощь будет высоко оценена!

1 Ответ

0 голосов
/ 31 октября 2019

Решается, передавая состояние внутри defaultStoreConfig, а не отдельно при создании магазина

Код:

    const defaultStoreConfig = {
      state: {
        auth: {
          user: {
            auids: '',
            md_clock: 0,
            md_picture: '',
            ps_fname1: '',
            ps_surname: '',
            psname: 'Test Test',
            psref: 0
          }
        },
        app: {
          dashBoardData: []
        }
      },
      getters: {
        getDashBoardData: () => dashBoardData
      },
      actions: {
        loadDashboard: jest.fn(),
        updateDashBoardData: jest.fn()
      }
    }

Тест:

  it('is a Vue instance', () => {
    const wrapper = createWrapper()
    expect(wrapper.isVueInstance).toBeTruthy()
  })
...