diff options
Diffstat (limited to 'spec/frontend/__helpers__')
7 files changed, 115 insertions, 3 deletions
diff --git a/spec/frontend/__helpers__/matchers/index.js b/spec/frontend/__helpers__/matchers/index.js index 76571bafb06..9b83ced10e1 100644 --- a/spec/frontend/__helpers__/matchers/index.js +++ b/spec/frontend/__helpers__/matchers/index.js @@ -1,3 +1,4 @@ export * from './to_have_sprite_icon'; export * from './to_have_tracking_attributes'; export * from './to_match_interpolated_text'; +export * from './to_validate_json_schema'; diff --git a/spec/frontend/__helpers__/matchers/to_validate_json_schema.js b/spec/frontend/__helpers__/matchers/to_validate_json_schema.js new file mode 100644 index 00000000000..ff391f08c55 --- /dev/null +++ b/spec/frontend/__helpers__/matchers/to_validate_json_schema.js @@ -0,0 +1,34 @@ +// NOTE: Make sure to initialize ajv when using this helper + +const getAjvErrorMessage = ({ errors }) => { + return (errors || []).map((error) => { + return `Error with item ${error.instancePath}: ${error.message}`; + }); +}; + +export function toValidateJsonSchema(testData, validator) { + if (!(validator instanceof Function && validator.schema)) { + return { + validator, + message: () => + 'Validator must be a validating function with property "schema", created with `ajv.compile`. See https://ajv.js.org/api.html#ajv-compile-schema-object-data-any-boolean-promise-any.', + pass: false, + }; + } + + const isValid = validator(testData); + + return { + actual: testData, + message: () => { + if (isValid) { + // We can match, but still fail because we're in a `expect...not.` context + return 'Expected the given data not to pass the schema validation, but found that it was considered valid.'; + } + + const errorMessages = getAjvErrorMessage(validator).join('\n'); + return `Expected the given data to pass the schema validation, but found that it was considered invalid. Errors:\n${errorMessages}`; + }, + pass: isValid, + }; +} diff --git a/spec/frontend/__helpers__/matchers/to_validate_json_schema_spec.js b/spec/frontend/__helpers__/matchers/to_validate_json_schema_spec.js new file mode 100644 index 00000000000..fd42c710c65 --- /dev/null +++ b/spec/frontend/__helpers__/matchers/to_validate_json_schema_spec.js @@ -0,0 +1,65 @@ +import Ajv from 'ajv'; +import AjvFormats from 'ajv-formats'; + +const JSON_SCHEMA = { + type: 'object', + properties: { + fruit: { + type: 'string', + minLength: 3, + }, + }, +}; + +const ajv = new Ajv({ + strictTypes: false, + strictTuples: false, + allowMatchingProperties: true, +}); + +AjvFormats(ajv); +const schema = ajv.compile(JSON_SCHEMA); + +describe('custom matcher toValidateJsonSchema', () => { + it('throws error if validator is not compiled correctly', () => { + expect(() => { + expect({}).toValidateJsonSchema({}); + }).toThrow( + 'Validator must be a validating function with property "schema", created with `ajv.compile`. See https://ajv.js.org/api.html#ajv-compile-schema-object-data-any-boolean-promise-any.', + ); + }); + + describe('positive assertions', () => { + it.each` + description | input + ${'valid input'} | ${{ fruit: 'apple' }} + `('schema validation passes for $description', ({ input }) => { + expect(input).toValidateJsonSchema(schema); + }); + + it('throws if not matching', () => { + expect(() => expect(null).toValidateJsonSchema(schema)).toThrowError( + `Expected the given data to pass the schema validation, but found that it was considered invalid. Errors: +Error with item : must be object`, + ); + }); + }); + + describe('negative assertions', () => { + it.each` + description | input + ${'no input'} | ${null} + ${'input with invalid type'} | ${'banana'} + ${'input with invalid length'} | ${{ fruit: 'aa' }} + ${'input with invalid type'} | ${{ fruit: 12345 }} + `('schema validation fails for $description', ({ input }) => { + expect(input).not.toValidateJsonSchema(schema); + }); + + it('throws if matching', () => { + expect(() => expect({ fruit: 'apple' }).not.toValidateJsonSchema(schema)).toThrowError( + 'Expected the given data not to pass the schema validation, but found that it was considered valid.', + ); + }); + }); +}); diff --git a/spec/frontend/__helpers__/mock_apollo_helper.js b/spec/frontend/__helpers__/mock_apollo_helper.js index c07a6d8ef85..bae9f33be87 100644 --- a/spec/frontend/__helpers__/mock_apollo_helper.js +++ b/spec/frontend/__helpers__/mock_apollo_helper.js @@ -1,7 +1,7 @@ import { InMemoryCache } from '@apollo/client/core'; import { createMockClient as createMockApolloClient } from 'mock-apollo-client'; import VueApollo from 'vue-apollo'; -import possibleTypes from '~/graphql_shared/possibleTypes.json'; +import possibleTypes from '~/graphql_shared/possible_types.json'; import { typePolicies } from '~/lib/graphql'; export function createMockClient(handlers = [], resolvers = {}, cacheOptions = {}) { diff --git a/spec/frontend/__helpers__/mock_dom_observer.js b/spec/frontend/__helpers__/mock_dom_observer.js index dd26b594ad9..bc2646be4c2 100644 --- a/spec/frontend/__helpers__/mock_dom_observer.js +++ b/spec/frontend/__helpers__/mock_dom_observer.js @@ -22,14 +22,14 @@ class MockObserver { takeRecords() {} - // eslint-disable-next-line babel/camelcase + // eslint-disable-next-line camelcase $_triggerObserve(node, { entry = {}, options = {} } = {}) { if (this.$_hasObserver(node, options)) { this.$_cb([{ target: node, ...entry }]); } } - // eslint-disable-next-line babel/camelcase + // eslint-disable-next-line camelcase $_hasObserver(node, options = {}) { return this.$_observers.some( ([obvNode, obvOptions]) => node === obvNode && isMatch(options, obvOptions), diff --git a/spec/frontend/__helpers__/vuex_action_helper.js b/spec/frontend/__helpers__/vuex_action_helper.js index 68203b544ef..95a811d0385 100644 --- a/spec/frontend/__helpers__/vuex_action_helper.js +++ b/spec/frontend/__helpers__/vuex_action_helper.js @@ -49,6 +49,7 @@ const noop = () => {}; * expectedActions: [], * }) */ + export default ( actionArg, payloadArg, diff --git a/spec/frontend/__helpers__/yaml_transformer.js b/spec/frontend/__helpers__/yaml_transformer.js new file mode 100644 index 00000000000..a23f9b1f715 --- /dev/null +++ b/spec/frontend/__helpers__/yaml_transformer.js @@ -0,0 +1,11 @@ +/* eslint-disable import/no-commonjs */ +const JsYaml = require('js-yaml'); + +// This will transform YAML files to JSON strings +module.exports = { + process: (sourceContent) => { + const jsonContent = JsYaml.load(sourceContent); + const json = JSON.stringify(jsonContent); + return `module.exports = ${json}`; + }, +}; |