// See these docs for details on Jest's matcher utils: // https://facebook.github.io/jest/docs/en/expect.html#thisutils const _ = require('lodash') const customMatchers = {} customMatchers.toBeAComponent = function(options) { if (isAComponent()) { return { message: () => `expected ${this.utils.printReceived( options )} not to be a Vue component`, pass: true, } } else { return { message: () => `expected ${this.utils.printReceived( options )} to be a valid Vue component, exported from a .vue file`, pass: false, } } function isAComponent() { return _.isPlainObject(options) && typeof options.render === 'function' } } customMatchers.toBeAViewComponent = function(options, mockInstance = {}) { if (usesALayout() && definesAPageTitleAndDescription()) { return { message: () => `expected ${this.utils.printReceived( options )} not to register a local Layout component nor define a page title and meta description`, pass: true, } } else { return { message: () => `expected ${this.utils.printReceived( options )} to register a local Layout component and define a page title and meta description`, pass: false, } } function usesALayout() { return options.components && options.components.Layout } function definesAPageTitleAndDescription() { if (!options.page) return false const pageObject = typeof options.page === 'function' ? options.page.apply(mockInstance) : options.page if (!Object.prototype.hasOwnProperty.call(pageObject, 'title')) return false if (!pageObject.meta) return false const hasMetaDescription = pageObject.meta.some( (metaObject) => metaObject.name === 'description' && Object.prototype.hasOwnProperty.call(metaObject, 'content') ) if (!hasMetaDescription) return false return true } } customMatchers.toBeAViewComponentUsing = function(options, mockInstance) { return customMatchers.toBeAViewComponent.apply(this, [options, mockInstance]) } customMatchers.toBeAVuexModule = function(options) { if (isAVuexModule()) { return { message: () => `expected ${this.utils.printReceived(options)} not to be a Vuex module`, pass: true, } } else { return { message: () => `expected ${this.utils.printReceived( options )} to be a valid Vuex module, include state, getters, mutations, and actions`, pass: false, } } function isAVuexModule() { return ( _.isPlainObject(options) && _.isPlainObject(options.state) && _.isPlainObject(options.getters) && _.isPlainObject(options.mutations) && _.isPlainObject(options.actions) ) } } // https://facebook.github.io/jest/docs/en/expect.html#expectextendmatchers global.expect.extend(customMatchers)