{"version":3,"file":"index.modern.mjs","sources":["../src/lib/store/index.js","../src/lib/constants/index.js","../src/lib/reducers/index.js","../src/lib/validator/utils.js","../src/lib/validator/methods.js","../src/lib/validator/index.js","../src/lib/dom/index.js","../src/lib/validator/real-time-validation.js","../src/lib/factory/validate.js","../src/lib/validator/post-validation.js","../src/lib/factory/add-method.js","../src/lib/factory/group.js","../src/lib/factory/index.js","../src/lib/defaults/index.js","../src/index.js"],"sourcesContent":["export const createStore = () => {\n    let state = {};\n    \n    const getState = () => state;\n\n    const update = (nextState, effects) => {\n        state = nextState ?? state;\n        if (!effects) return;\n        effects.forEach(effect => effect(state));\n    };\n    \n    return { update, getState };\n};","export const PREHOOK_DELAY = 16;\n\nexport const ACTIONS = {\n    SET_INITIAL_STATE: 'SET_INITIAL_STATE',\n    CLEAR_ERRORS: 'CLEAR_ERRORS',\n    VALIDATION_ERRORS: 'VALIDATION_ERRORS',\n    VALIDATION_ERROR: 'VALIDATION_ERROR',\n    CLEAR_ERROR: 'CLEAR_ERROR',\n    ADD_VALIDATION_METHOD: 'ADD_VALIDATION_METHOD',\n    ADD_GROUP: 'ADD_GROUP',\n    REMOVE_GROUP: 'REMOVE_GROUP',\n    START_REALTIME: 'START_REALTIME'\n};\n\n//https://html.spec.whatwg.org/multipage/forms.html#valid-e-mail-address\nexport const EMAIL_REGEX = /^[A-Za-zŽžÀ-ÿŠ0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$/;\n\n//https://mathiasbynens.be/demo/url-regex\nexport const URL_REGEX = /^(?:(?:(?:https?|ftp):)?\\/\\/)(?:\\S+(?::\\S*)?@)?(?:(?!(?:10|127)(?:\\.\\d{1,3}){3})(?!(?:169\\.254|192\\.168)(?:\\.\\d{1,3}){2})(?!172\\.(?:1[6-9]|2\\d|3[0-1])(?:\\.\\d{1,3}){2})(?:[1-9]\\d?|1\\d\\d|2[01]\\d|22[0-3])(?:\\.(?:1?\\d{1,2}|2[0-4]\\d|25[0-5])){2}(?:\\.(?:[1-9]\\d?|1\\d\\d|2[0-4]\\d|25[0-4]))|(?:(?:[a-z\\u00a1-\\uffff0-9]-*)*[a-z\\u00a1-\\uffff0-9]+)(?:\\.(?:[a-z\\u00a1-\\uffff0-9]-*)*[a-z\\u00a1-\\uffff0-9]+)*(?:\\.(?:[a-z\\u00a1-\\uffff]{2,})).?)(?::\\d{2,5})?(?:[/?#]\\S*)?$/i;\n\nexport const DATE_ISO_REGEX = /^\\d{4}[/-](0?[1-9]|1[012])[/-](0?[1-9]|[12][0-9]|3[01])$/;\n\nexport const NUMBER_REGEX = /^(?:-?\\d+|-?\\d{1,3}(?:,\\d{3})+)?(?:\\.\\d+)?$/;\n\nexport const DIGITS_REGEX = /^\\d+$/;\n\n//data-attribute added to error message span created by .NET MVC\nexport const DOTNET_ERROR_SPAN_DATA_ATTRIBUTE = 'data-valmsg-for';\n\n//validator parameters that require DOM lookup\nexport const DOM_SELECTOR_PARAMS = ['remote-additionalfields', 'equalto-other'];\n\n//.NET MVC validator data-attribute parameters indexed by their validators\n//e.g. <input data-val-length=\"Error messge\" data-val-length-min=\"8\" data-val-length-max=\"10\" type=\"text\"... />\nexport const DOTNET_PARAMS = {\n    length: ['length-min', 'length-max'],\n    stringlength: ['length-max'],\n    range: ['range-min', 'range-max'],\n    min: ['min-min'],\n    max: ['max-max'],\n    minlength: ['minlength-min'],\n    maxlength: ['maxlength-max'],\n    regex: ['regex-pattern'],\n    equalto: ['equalto-other'],\n    remote: ['remote-url', 'remote-additionalfields', 'remote-type']\n};\n\n//.NET MVC data-attributes that identify validators\nexport const DOTNET_ADAPTORS = [\n    'required',\n    'stringlength',\n    'dateISO',\n    'regex',\n    'digits',\n    'email',\n    'number',\n    'url',\n    'length',\n    'min',\n    'max',\n    'minlength',\n    'maxlength',\n    'range',\n    'equalto',\n    // 'password' //-> map to min, nonalphamain, and regex methods\n    'remote'//should be last\n];\n\n//classNames added/updated on .NET MVC error message span\nexport const DOTNET_CLASSNAMES = {\n    VALID: 'field-validation-valid',\n    ERROR: 'error-message'\n};\n\nexport const GROUP_ATTRIBUTE = 'group';\n\nexport const TOKENS = {\n    VALUE: '{{value}}'\n};","import { ACTIONS, DOTNET_ERROR_SPAN_DATA_ATTRIBUTE, GROUP_ATTRIBUTE } from '../constants';\n\nexport default {\n    [ACTIONS.SET_INITIAL_STATE]: (state, data) => Object.assign({}, state, data),\n    [ACTIONS.CLEAR_ERRORS]: state => Object.assign({}, state, {\n        groups: Object.keys(state.groups).reduce((acc, group) => {\n            acc[group] = Object.assign({}, state.groups[group], {\n                errorMessages: [],\n                valid: true\n            });\n            return acc;\n        }, {})\n    }),\n    [ACTIONS.CLEAR_ERROR]: (state, data) => {\n        const nextGroup = {};\n        nextGroup[data] = Object.assign({}, state.groups[data], {\n            errorMessages: [],\n            valid: true\n        });\n        return Object.assign({}, state, {\n            groups: Object.assign({}, state.groups, nextGroup)\n        });\n    },\n    [ACTIONS.ADD_GROUP]: (state, data) => Object.assign({}, state, {\n        groups: Object.assign({}, state.groups, data)\n    }),\n    [ACTIONS.REMOVE_GROUP]: (state, groupName) => Object.assign({}, state, {\n        groups: Object.keys(state.groups).reduce((acc, group) => {\n            if (group !== groupName) acc[group] = state.groups[group];\n            return acc;\n        }, {})\n    }),\n    [ACTIONS.ADD_VALIDATION_METHOD]: (state, data) => {\n        const nextGroup = Object.assign({},\n            state.groups[data.groupName]\n                ? state.groups[data.groupName]\n                : {},\n            state.groups[data.groupName]\n                ?  { validators: [...state.groups[data.groupName].validators, data.validator] }\n                : {\n                    fields: data.fields || (document.querySelector(`[data-val-${GROUP_ATTRIBUTE}=\"${data.groupName}\"]`) ? [].slice.call(document.querySelectorAll(`[data-val-${GROUP_ATTRIBUTE}=\"${data.groupName}\"]`)) : [].slice.call(document.getElementsByName(data.groupName))),\n                    serverErrorNode: document.querySelector(`[${DOTNET_ERROR_SPAN_DATA_ATTRIBUTE}=\"${data.groupName}\"]`) || false,\n                    valid: false,\n                    validators: [data.validator],\n                });\n\n        return Object.assign({}, state, {\n            groups: Object.assign({}, state.groups, { [data.groupName]: nextGroup })\n        });\n    },\n    [ACTIONS.VALIDATION_ERRORS]: (state, data) => Object.assign({}, state, {\n        realTimeValidation: true,\n        groups: Object.keys(state.groups).reduce((acc, group) => {\n            acc[group] = Object.assign({}, state.groups[group], data[group]);\n            return acc;\n        }, {})\n    }),\n    [ACTIONS.VALIDATION_ERROR]: (state, data) => {\n        return Object.assign({}, state, {\n            groups: Object.assign({}, state.groups, {\n                [data.group]: Object.assign({}, state.groups[data.group], {\n                    errorMessages: data.errorMessages,\n                    valid: false\n                })\n            })\n        });\n    },\n    [ACTIONS.START_REALTIME]: (state, data) => Object.assign({}, state, data),\n};\n\n    ","export const isCheckable = field => (/radio|checkbox/i).test(field.type);\n\nexport const isFile = field => field.getAttribute('type') === 'file';\n\nexport const isHidden = field => field.getAttribute('type') === 'hidden';\n\nexport const isSelect = field => field.nodeName.toLowerCase() === 'select';\n\nexport const isSubmitButton = node =>  node.getAttribute('type') === 'submit' || node.nodeName === 'BUTTON';\n\nexport const hasNameValue = node => node.hasAttribute('name') && node.hasAttribute('value');\n\nexport const hasFormactionValue = node => node.hasAttribute('formaction') && node.getAttribute('formaction') !== '';\n\nexport const isRequired = group => group.validators.filter(validator => validator.type === 'required').length > 0;\n\nexport const groupIsAllHidden = fields => fields.reduce((acc, field) => {\n    if (field.type !== 'hidden') acc = false;\n    return acc;\n}, true);\n\nexport const groupIsDisabled = fields => fields.reduce((acc, field) => {\n    if (field.hasAttribute('disabled') && field.getAttribute('disabled') !== \"false\") acc = true;\n    return acc;\n}, false);\n\nexport const hasValue = input => (input.value !== undefined && input.value !== null && input.value.length > 0);\n\nexport const groupValueReducer = (acc, input) => {\n    if (!isCheckable(input) && !isHidden(input) && hasValue(input)) acc = input.value.trim();\n    if (isCheckable(input) && input.checked) {\n        if (Array.isArray(acc)) acc.push(input.value.trim());\n        else acc = [input.value.trim()];\n    }\n    return acc;\n};\n\nexport const resolveGetParams = nodeArrays => nodeArrays.map(nodes => `${encodeURIComponent(nodes[0].getAttribute('name'))}=${encodeURIComponent(extractValueFromGroup(nodes))}`).join('&');\n\nexport const domNodesFromCommaList = list => list.split(',')\n    .map(item => {\n        // const resolvedSelector = escapeAttributeValue(appendStatePrefix(item, getStatePrefix(input.getAttribute('name'))));\n        return [].slice.call(document.querySelectorAll(`[name=${escapeAttributeValue(item)}]`));\n    });\n\nexport const escapeAttributeValue = value => value.replace(/([!\"#$%&'()*+,./:;<=>?@[\\\\\\]^`{|}~])/g, '\\\\$1');\n\n/*\n * Only require below functions and resolvedSelector in domNodesFromCommaList if supporting *. params\n */\n// const getStatePrefix = fieldName => fieldName.substr(0, fieldName.lastIndexOf('.') + 1);\n\n// const appendStatePrefix = (value, prefix) => {\n//     if (value.indexOf(\"*.\") === 0) value = value.replace(\"*.\", prefix);\n//     return value;\n// };\n\nexport const extractValueFromGroup = group => Object.prototype.hasOwnProperty.call(group, 'fields')\n    ? group.fields.reduce(groupValueReducer, '')\n    : group.reduce(groupValueReducer, '');\n\n\n/* istanbul ignore next */\nexport const fetch = (url, props) =>\n    new Promise((resolve, reject) => {\n        let xhr = new XMLHttpRequest();\n        xhr.open(props.method || 'GET', url);\n        if (props.headers) {\n            Object.keys(props.headers).forEach(key => {\n                xhr.setRequestHeader(key, props.headers[key]);\n            });\n        }\n        xhr.onload = () => {\n            if (xhr.status >= 200 && xhr.status < 300) resolve(xhr.response);\n            else reject(xhr.statusText);\n        };\n        xhr.onerror = () => reject(xhr.statusText);\n        xhr.send(props.body);\n    });\n\nexport const findErrors = groups => Object.keys(groups).reduce((errors, groupName) => {\n    if (groups[groupName].serverErrorNode){\n        const serverErrorText = groups[groupName].serverErrorNode.textContent;\n        if (serverErrorText) {\n            errors[groupName] = serverErrorText;\n        }\n    }\n    return errors;\n}, {});\n\n\n/*\n * Converts a passed selector which can be of varying types into an array of DOM Objects\n *\n * @param selector, Can be a string, Array of DOM nodes, a NodeList or a single DOM element.\n */\nexport const getSelection = selector => {\n\n    if (typeof selector === 'string') return [].slice.call(document.querySelectorAll(selector));\n    if (selector instanceof Array) return selector;\n    if (Object.prototype.isPrototypeOf.call(NodeList.prototype, selector)) return [].slice.call(selector);\n    if (selector instanceof HTMLElement) return [selector];\n    return [];\n};","import {\n    EMAIL_REGEX,\n    URL_REGEX,\n    DATE_ISO_REGEX,\n    NUMBER_REGEX,\n    DIGITS_REGEX\n} from '../constants';\nimport {\n    fetch,\n    isRequired,\n    extractValueFromGroup,\n    resolveGetParams\n} from './utils';\n\nconst isOptional = group => !isRequired(group) && extractValueFromGroup(group) === '';\n\nconst extractValidationParams = (group, type) => group.validators.filter(validator => validator.type === type)[0].params;\n\nconst regexMethod = regex => group => isOptional(group)|| group.fields.reduce((acc, input) => (acc = regex.test(input.value), acc), false);\n\nconst paramMethod = (type, reducer) => group => isOptional(group) || group.fields.reduce(reducer(extractValidationParams(group, type)), false);\n\nconst shouldValidateByParam = param => param !== undefined;\n\nexport default {\n    required: group => extractValueFromGroup(group) !== '',\n    email: regexMethod(EMAIL_REGEX),\n    url: regexMethod(URL_REGEX),\n    dateISO: regexMethod(DATE_ISO_REGEX),\n    number: regexMethod(NUMBER_REGEX),\n    digits: regexMethod(DIGITS_REGEX),\n    minlength: paramMethod(\n        'minlength',\n        params => (acc, input) => (acc = +input.value.length >= +params.min, acc)\n    ),\n    maxlength: paramMethod(\n        'maxlength',\n        params => (acc, input) => (acc = +input.value.length <= +params.max, acc)\n    ),\n    equalto: paramMethod('equalto', params => (acc, input) => (acc = params.other.reduce((subgroupAcc, subgroup) => {\n        if (extractValueFromGroup(subgroup) !== input.value) subgroupAcc = false;\n        return subgroupAcc;\n    }, true), acc)),\n    pattern: paramMethod('pattern', params => (acc, input) => (acc = RegExp(params.regex).test(input.value), acc)),\n    regex: paramMethod('regex', params => (acc, input) => (acc = RegExp(params.pattern).test(input.value), acc)),\n    min: paramMethod('min', params => (acc, input) => (acc = !isNaN(parseInt(input.value, 10)) && +input.value >= +params.min, acc)),\n    max: paramMethod('max', params => (acc, input) => (acc = !isNaN(parseInt(input.value, 10)) && +input.value <= +params.max, acc)),\n    stringlength: paramMethod('stringlength', params => (acc, input) => (acc = +input.value.length <= +params.max, acc)),\n    length: paramMethod('length', params => (acc, input) => (acc = (+input.value.length >= +params.min && (params.max === undefined || +input.value.length <= +params.max)), acc)),\n    range: paramMethod('range', params => (acc, input) => (acc = ((!shouldValidateByParam(params.min) || +input.value >= +params.min) && (!shouldValidateByParam(params.max) || +input.value <= +params.max)), acc)),\n    remote: (group, params) => new Promise((resolve, reject) => {\n        const value = extractValueFromGroup(group);\n        fetch((params.type !== 'get' ? params.url : `${params.url}?${group.fields[0].name}=${value}&${resolveGetParams(params.additionalfields)}`), {\n            method: params.type && params.type.toUpperCase() || 'POST',\n            body: params.type !== 'get'\n                ? JSON.stringify({ [group.fields[0].name]: value })\n                : resolveGetParams(params.additionalfields),\n            headers: {\n                'Content-Type': 'application/x-www-form-urlencoded;charset=UTF-8'\n            }\n        })\n            .then(data => resolve(data));\n    }),\n    custom: (method, group) => isOptional(group) || method(extractValueFromGroup(group), group.fields)\n};","import methods from './methods';\nimport {\n    isCheckable,\n    isSelect,\n    isFile,\n    isHidden,\n    domNodesFromCommaList,\n    groupIsDisabled,\n    findErrors,\n    groupIsAllHidden\n} from './utils';\nimport {\n    DOTNET_ADAPTORS,\n    DOTNET_PARAMS,\n    DOTNET_ERROR_SPAN_DATA_ATTRIBUTE,\n    DOM_SELECTOR_PARAMS,\n    GROUP_ATTRIBUTE\n} from '../constants';\n\n/**\n * Resolve validation parameter to a string or array of DOM nodes\n * \n * @param param [String] identifier for the data-attribute `data-val-${param}`\n * @param input [DOM node] the node which contains the data-val- attribute\n * \n * @return validation param [Object] indexed by second part of param name (e.g., 'min' part of length-min') and array of DOM nodes or a string\n */\nexport const resolveParam = (param, input) => {\n    let value = input.getAttribute(`data-val-${param}`);\n    return ({\n        [param.split('-')[1]]: ~DOM_SELECTOR_PARAMS.indexOf(param) ? domNodesFromCommaList(value, input): value\n    });\n};\n\n/**\n * Looks up the data-val property against the known .NET MVC adaptors/validation method\n * runs the matches against the node to find param values, and returns an Object containing all  parameters for that adaptor/validation method\n * \n * @param input [DOM node] the node on which to look for matching adaptors\n * @param adaptor [String] .NET MVC data-attribute that identifies validator\n * \n * @return validation params [Object] Validation param object containing all validation parameters for an adaptor/validation method\n */\nexport const extractParams = (input, adaptor) => DOTNET_PARAMS[adaptor]\n    ? {\n        params: DOTNET_PARAMS[adaptor]\n            .reduce((acc, param) => input.hasAttribute(`data-val-${param}`) ? Object.assign(acc, resolveParam(param, input)) : acc, {})\n    }\n    : false;\n\n/**\n * Reducer that takes all known .NET MVC adaptors (data-attributes that specify a validation method that should be applied to the node)\n * and checks against a DOM node for matches, returning an array of validators\n * \n * @param input [DOM node]\n * \n * @return validators [Array], each validator compposed of \n *                              type [String] naming the validator and matching it to validation method function\n *                              message [String] the error message displayed if the validation method returns false\n *                              params [Object] (optional) \n */\nexport const extractDataValValidators = input => DOTNET_ADAPTORS.reduce((validators, adaptor) =>\n    !input.getAttribute(`data-val-${adaptor}`)\n        ? validators\n        : [...validators,\n            Object.assign({\n                type: adaptor,\n                message: input.getAttribute(`data-val-${adaptor}`) },\n            extractParams(input, adaptor)\n            )\n        ],\n[]);\n\n/**\n * Looks for a data-val attribute matching the validator type and returns the value\n * \n * @param input [DOM node]\n * @param type [String]\n * \n * @return [Object] Error message or empty\n */\nconst resolveMessages = (input, type) => input.getAttribute(`data-val-${type}`) ? { message: input.getAttribute(`data-val-${type}`) } : {};\n\n/**\n * Checks attributes on an input to generate an array of validators the attributes describe\n * \n * @param input [DOM node]\n * \n * @return validators [Array]\n */\nexport const extractAttrValidators = input => {\n    let validators = [];\n    if ((input.hasAttribute('required') || input.hasAttribute('aria-required')) && (input.getAttribute('required') !== 'false' || input.getAttribute('aria-required') !== 'false')){\n        validators.push({ type: 'required', ...resolveMessages(input, 'required') } );\n    }\n    if (input.getAttribute('type') === 'email') validators.push({ type: 'email', ...resolveMessages(input, 'email') });\n    if (input.getAttribute('type') === 'url') validators.push({ type: 'url', ...resolveMessages(input, 'url') });\n    if (input.getAttribute('type') === 'number') validators.push({ type: 'number', ...resolveMessages(input, 'number') });\n    if ((input.getAttribute('minlength') && input.getAttribute('minlength') !== 'false')){\n        validators.push({ type: 'minlength', params: { min: input.getAttribute('minlength') }, ...resolveMessages(input, 'minlength') });\n    }\n    if ((input.getAttribute('maxlength') && input.getAttribute('maxlength') !== 'false')){\n        validators.push({ type: 'maxlength', params: { max: input.getAttribute('maxlength') }, ...resolveMessages(input, 'maxlength') });\n    }\n    if ((input.getAttribute('min') && input.getAttribute('min') !== 'false')){\n        validators.push({ type: 'min', params: { min: input.getAttribute('min') }, ...resolveMessages(input, 'min') });\n    }\n    if ((input.getAttribute('max') && input.getAttribute('max') !== 'false')){\n        validators.push({ type: 'max', params: { max: input.getAttribute('max') }, ...resolveMessages(input, 'max') });\n    }\n    if ((input.getAttribute('pattern') && input.getAttribute('pattern') !== 'false')){\n        validators.push({ type: 'pattern', params: { regex: input.getAttribute('pattern') }, ...resolveMessages(input, 'pattern') });\n    }\n    return validators;\n};\n\n/**\n * Validator checks to extract validators based on HTML5 attributes\n * \n * Each function is so we can seed each fn with an input and pipe the result array through each function\n * Signature: inputDOMNode => validatorArray => updateValidatorArray\n\nconst required = input => (validators = []) => {\n    // console.log(validators);\n    return input.hasAttribute('required') && input.getAttribute('required') !== 'false' ? [...validators, {type: 'required'}] : validators;\n};\nconst email = input => (validators = [])  => input.getAttribute('type') === 'email' ? [...validators, {type: 'email'}] : validators;\nconst url = input => (validators = [])  => input.getAttribute('type') === 'url' ? [...validators, {type: 'url'}] : validators;\nconst number = input => (validators = [])  => input.getAttribute('type') === 'number' ? [...validators, {type: 'number'}] : validators;\nconst minlength = input => (validators = [])  => (input.getAttribute('minlength') && input.getAttribute('minlength') !== 'false') ? [...validators, {type: 'minlength', params: { min: input.getAttribute('minlength')}}] : validators;\nconst maxlength = input => (validators = [])  => (input.getAttribute('maxlength') && input.getAttribute('maxlength') !== 'false') ? [...validators, {type: 'maxlength', params: { max: input.getAttribute('maxlength')}}] : validators;\nconst min = input => (validators = [])  => (input.getAttribute('min') && input.getAttribute('min') !== 'false') ? [...validators, {type: 'min', params: { min: input.getAttribute('min')}}] : validators;\nconst max = input => (validators = [])  => (input.getAttribute('max') && input.getAttribute('max') !== 'false') ? [...validators, {type: 'max', params: { max: input.getAttribute('max')}}] : validators;\nconst pattern = input => (validators = [])  => (input.getAttribute('pattern') && input.getAttribute('pattern') !== 'false') ? [...validators, {type: 'pattern', params: { regex: input.getAttribute('pattern')}}] : validators;\n */\n\n/**\n * Takes an input and returns the array of validators based on either .NET MVC data-val- or HTML5 attributes\n * \n * @param input [DOM node]\n * \n * @return validators [Array]\n */\nexport const normaliseValidators = input => input.getAttribute('data-val') === 'true'\n    ? extractDataValValidators(input)\n    : extractAttrValidators(input);\n\n/**\n * Calls a validation method against an input group\n * \n * @param group [Array] DOM nodes with the same name attribute\n * @param validator [String] The type of validator matching it to validation method function\n * \n * @returns  validityState [Promise]\n * \n */\nexport const validate = (group, validator) => new Promise((resolve, reject) => {\n    try {\n        validator.type === 'custom'\n            ? resolve(methods.custom(validator.method, group))\n            : resolve(methods[validator.type](group, validator.params));\n    } catch (err) {\n        console.warn(err);\n        resolve(err);\n    }\n});\n\n/**\n * Reducer constructing an validation Object for a group of DOM nodes\n *  \n * @param input [DOM node]\n * \n * @returns validation object [Object] consisting of\n *                            valid [Boolean] the validityState of the group\n *                            validators [Array] of validator objects\n *                            fields [Array] DOM nodes in the group\n *                            serverErrorNode [DOM node] .NET MVC server-rendered error message span\n * \n */\nexport const assembleValidationGroup = (acc, input) => {\n    let name = (input.getAttribute('data-val-'+GROUP_ATTRIBUTE)) ? input.getAttribute('data-val-'+GROUP_ATTRIBUTE) : input.getAttribute('name') ;\n    if (!name) return console.warn('Missing data group or name attribute'), acc;\n\n    if (acc[name] && isHidden(input)) return acc;\n\n    const serverErrorNode = document.querySelector(`[${DOTNET_ERROR_SPAN_DATA_ATTRIBUTE}=\"${name}\"]`) || false;\n\n    return acc[name] = acc[name] ? Object.assign(acc[name], { fields: [...acc[name].fields, input] })\n        : {\n            valid: false,\n            validators: normaliseValidators(input),\n            fields: [input],\n            serverErrorNode\n        }, acc;\n};\n\n/**\n * Returns an error message property of the validator Object that has returned false or the corresponding default message\n * \n * @param validator [Object] \n * \n * @return message [String] error message\n * \n */\nexport const extractErrorMessage = (messages, validator) => validator.message || messages[validator.type](validator.params !== undefined ? validator.params : null);\n\n/**\n * Returns a reducer that reduces the resolved response from an array of validation Promises performed against a group\n * into an array of error messages or an empty array\n * \n * @return error messages [Array]\n * \n */\nexport const reduceErrorMessages = (group, state) => (acc, validity, j) => validity === true\n    ? acc\n    : [...acc, typeof validity === 'boolean'\n        ? extractErrorMessage(state.settings.messages, state.groups[group].validators[j])\n        : validity];\n\n/**\n * From all groups found in the current form, thosethat do not require validation (have no assocated validators) are removed\n * \n * @param groups [Object] name-indexed object consisting of all groups found in the current form\n * \n * @return groups [Object] name-indexed object consisting of all validatable groups\n * \n */\nexport const removeUnvalidatableGroups = groups => {\n    let validationGroups = {};\n\n    for (let group in groups){\n        if (groups[group].validators.length > 0 && !groupIsAllHidden(groups[group].fields)){\n            validationGroups[group] = groups[group];\n        }\n    }\n    return validationGroups;\n};\n\n/**\n * Takes a form DOM node and returns the initial form validation state - an object consisting of all the validatable input groups\n * with validityState, fields, validators, and associated data required to perform validation and render errors.\n * \n * @param form [DOM nodes] \n * \n * @return state [Object] consisting of groups [Object] name-indexed validation groups\n * \n */\nexport const getInitialState = (form, settings) => {\n    const groups = removeUnvalidatableGroups([].slice.call(form.querySelectorAll('input:not([type=submit]), textarea, select'))\n        .reduce(assembleValidationGroup, {}));\n    return {\n        form,\n        settings,\n        errors: findErrors(groups),\n        realTimeValidation: false,\n        groups\n    };\n};\n\n/**\n * Reducer run against an array of resolved validation promises to set the overall validityState of a group\n * \n * @return validityState [Boolean] \n * \n */\nexport const reduceGroupValidityState = (acc, curr) => {\n    if (curr !== true) acc = false;\n    return acc;\n};\n\n\nexport const isFormValid = validityState => [].concat(...validityState).reduce(reduceGroupValidityState, true);\n\n/**\n * Aggregates validation promises for all groups into a single promise\n * \n * @params groups [Object]\n * \n * @return validation results [Promise] aggregated promise\n * \n */\nexport const getValidityState = groups => Promise.all(\n    Object.keys(groups)\n        .map(group => getGroupValidityState(groups[group]))\n);\n\n/**\n * Aggregates all of the validation promises for a single group into a single promise\n * \n * @params groups [Object]\n * \n * @return validation results [Promises] aggregated promise\n * \n */\nexport const getGroupValidityState = group => {\n    //check if group is disabled\n    if (groupIsDisabled(group.fields)) return Promise.resolve([true]);\n    return Promise.all(group.validators.map(validator => new Promise((resolve, reject) => {\n        validate(group, validator)\n            .then(res => {\n                if (String(res) !== 'true') resolve(String(res) === 'false' ? false : res);\n                else resolve(true);\n            })\n            .catch(err => console.warn(err));\n    })));\n};\n\n/**\n * Determines the event type to be used for real-time validation a given field based on field type\n * \n * @params input [DOM node]\n * \n * @return event type [String]\n * \n */\nexport const resolveRealTimeValidationEvent = input => ['input', 'change'][Number(isCheckable(input) || isSelect(input) || isFile(input))];","import { DOTNET_CLASSNAMES, TOKENS } from '../constants';\n\n/**\n * Hypertext DOM factory function\n * \n * @param nodeName [String]\n * @param attributes [Object]\n * @param text [String] The innerText of the new node\n * \n * @returns node [DOM node]\n * \n */\nexport const h = (nodeName, attributes, text) => {\n    let node = document.createElement(nodeName);\n\n    for (let prop in attributes) {\n        node.setAttribute(prop, attributes[prop]);\n    }\n    if (text !== undefined && text.length) node.appendChild(document.createTextNode(text));\n\n    return node;\n};\n\n/**\n * Creates and appends a text node error message to a  error container DOM node for a group\n * \n * @param group [Object, vaidation group] \n * @param msg [String] The error message\n * \n * @returns node [Text node]\n * \n */\nexport const createErrorTextNode = (group, msg) => {\n\n    let node = document.createTextNode(msg);\n    group.serverErrorNode.classList.remove(DOTNET_CLASSNAMES.VALID);\n    group.serverErrorNode.classList.add(DOTNET_CLASSNAMES.ERROR);\n    \n    return group.serverErrorNode.appendChild(node);\n};\n\n/**\n * Removes the error message, updates .NET MVC error span classNames and deletes the \n * error from local errors tracking object\n * \n * Signature () => groupName => state => {}\n * (groupName for ease of use as eventListener and in whole form iteration)\n * \n * @param groupName [String, vaidation group] \n * @param state [Object, validation state]\n * \n */\nexport const clearError = groupName => state => {\n    if (state.groups[groupName].serverErrorNode) {\n        state.groups[groupName].serverErrorNode.innerHTML = '';\n        state.groups[groupName].serverErrorNode.classList.remove(DOTNET_CLASSNAMES.ERROR);\n        state.groups[groupName].serverErrorNode.classList.add(DOTNET_CLASSNAMES.VALID);\n    } else {\n        state.errors[groupName].parentNode.removeChild(state.errors[groupName]);\n    }\n    state.groups[groupName].fields.forEach(field => {\n        field.parentNode.classList.remove('is--invalid');\n        field.removeAttribute('aria-invalid');\n        const describedbyid = ((state.groups[groupName].serverErrorNode || state.errors[groupName]).id);\n\n        //check whether the aria-describedby matches the id, if not another id must be present, only replace the removed error id\n        if (field.hasAttribute('aria-describedby')) {\n            if (field.getAttribute('aria-describedby') === describedbyid) field.removeAttribute('aria-describedby');\n            else field.setAttribute('aria-describedby', field.getAttribute('aria-describedby').replace(` ${describedbyid}`, ''));\n        }\n    });\n    delete state.errors[groupName];//shouldn't be doing this here...\n};\n\n/**\n * Iterates over all errors in local scope to remove each error prior to re-validation\n * \n * @param state [Object, validation state]\n * \n */\nexport const clearErrors = state => {\n    state.errors && Object.keys(state.errors).forEach(name => {\n        clearError(name)(state);\n    });\n};\n\n/**\n * Iterates over all groups to render each error post-vaidation\n * \n * @param state [Object, validation state]\n * \n */\nexport const renderErrors = state => {\n    Object.keys(state.groups).forEach(groupName => {\n        if (!state.groups[groupName].valid) renderError(groupName)(state);\n    });\n};\n\n\n/**\n * Looks for any value tokens and replaces them within the error message\n * \n * @param state [Object, validation state]\n * @param groupName [String, validation group] \n * \n */\nexport const updateMessageValues = (state, groupName) => {\n    let msg = state.groups[groupName].errorMessages[0];\n\n    let values = state.groups[groupName].fields.reduce((newMsg, field, index, array) => {\n        if (index === array.length-1) return newMsg + field.value;\n        return newMsg = field.value + ', ';\n    }, '');\n\n    return msg.replace(TOKENS.VALUE, values);\n};\n\n\n/**\n * Adds an error message to the DOM and saves it to local scope\n * \n * If .NET MVC error span is present, it is used with a appended textNode,\n * if not a new DOM node is created\n * \n * Signature () => groupName => state => {}\n * (groupName for ease of use as eventListener and in whole form iteration)\n * \n * @param groupName [String, validation group] \n * @param state [Object, validation state]\n * \n */\nexport const renderError = groupName => state => {\n    if (state.errors[groupName]) clearError(groupName)(state);\n\n    let msg = updateMessageValues(state, groupName);\n\n    //shouldn't be updating state here...\n    //to do: refactor to update state as a side effect afterwards?\n    //would need to pass store instead of state\n    if (state.groups[groupName].serverErrorNode) {\n        state.errors[groupName] = createErrorTextNode(state.groups[groupName], msg);\n    } else {\n        //No server error node found, so attempt to render inside the label.  If no label found, log error to console.\n        const label = document.querySelector(`[for=\"${state.groups[groupName].fields[state.groups[groupName].fields.length-1].getAttribute('id')}\"]`);\n\n        if (label !== null) {\n            state.errors[groupName] = label.parentNode.insertBefore(h('span', { class: DOTNET_CLASSNAMES.ERROR, id: `${groupName}-error-message` }, msg), label.nextSibling);\n        } else {\n            console.error(`No matching HTML label or server error node found for validation group: ${groupName}. Error message: '${msg}' cannot be displayed. Form will not be submitted.`);\n            return;\n        }\n    }\n\n    const errorContainer = state.groups[groupName].serverErrorNode || state.errors[groupName];\n\t\t\t\t\t\t\n    state.groups[groupName].fields.forEach(field => {\n        field.parentNode.classList.add('is--invalid');\n        field.setAttribute('aria-invalid', 'true');\n        if (!field.hasAttribute('aria-describedby') || !hasAriaDescribedbyValue(field, errorContainer.getAttribute('id'))) {\n            field.setAttribute('aria-describedby', (field.hasAttribute('aria-describedby')\n                ? `${field.getAttribute('aria-describedby')} ${errorContainer.getAttribute('id')}`\n                : errorContainer.getAttribute('id'))\n            );\n        }\n    });\n};\n\n\nexport const hasAriaDescribedbyValue = (field, value) => {\n    const describedby = field.getAttribute('aria-describedby').split(' ');\n    return describedby.length > 0\n        && describedby.reduce((acc, curr) => (acc || curr === value), false);\n};\n\n\n/**\n * Set focus on first invalid field after form-level validate()\n * \n * We can assume that there is a group in an invalid state,\n * and that the group has at least one field\n * \n * @param groups [Object, validation group slice of state]\n * \n */\nexport const focusFirstInvalidField = state => {\n    const firstInvalid = Object.keys(state.groups).reduce((acc, curr) => {\n        if (!acc && !state.groups[curr].valid) acc = state.groups[curr].fields[0];\n        return acc;\n    }, false);\n    firstInvalid && firstInvalid.focus();\n};\n\n/**\n * Creates a hidden field duplicate of a given field, for conferring submit button values\n * \n * @param source [Node] A submit input/button\n * @param form [Node] A form node\n * \n */\nexport const createButtonValueNode = (source, form) => {\n    const node = document.createElement('input');\n    node.setAttribute('type', 'hidden');\n    node.setAttribute('name', source.getAttribute('name'));\n    node.setAttribute('value', source.getAttribute('value'));\n    return form.appendChild(node);\n};\n\n/**\n * Removes the node added in createButtonValueNode\n * \n * @param node [Node] A hidden input\n * \n */\nexport const cleanupButtonValueNode = node => {\n    node.parentNode.removeChild(node);\n};\n\n/**\n * Add aria-required attribute to fields if appropriate (has required/data-val-required, is not a checkbox or radio group) \n * \n * @param fields [Array of DOMElements]\n * \n * @returns fields\n */\nexport const addAriaRequired = fields => {\n    fields.forEach(field => {\n        if (\n            (field.hasAttribute('required') || field.hasAttribute('data-val-required'))\n            && ((field.getAttribute('type') !== 'radio' && field.getAttribute('type') !== 'checkbox')\n                || (field.getAttribute('type') === 'checkbox' && fields.length === 1))\n        ) {\n            field.setAttribute('aria-required', 'true');\n        }\n    });\n\n    return fields;\n};\n\n/**\n * Adds attributes to input and error nodes to help accessibility\n * \n * @param state [Object]\n */\nexport const addAXAttributes = state => {\n    Object.keys(state.groups).forEach(groupName => {\n        //ensure error message has an id for aria-describedby\n        if (state.groups[groupName].serverErrorNode && !state.groups[groupName].serverErrorNode.hasAttribute('id')) state.groups[groupName].serverErrorNode.setAttribute('id', `${groupName}-error-message`);\n\n        //Add aria-required to inputs that are not radios, nor checkbox groups (single checkbox gets the attribute added)\n        addAriaRequired(state.groups[groupName].fields);\n    });\n};","import { ACTIONS } from '../constants';\nimport reducers from '../reducers';\nimport {\n    getGroupValidityState,\n    resolveRealTimeValidationEvent,\n    reduceGroupValidityState,\n    reduceErrorMessages\n} from './';\nimport {\n    clearError,\n    renderError\n}  from '../dom';\n\n/**\n * Starts real-time validation on each group, adding an eventListener to each field \n * that resets the validityState for the field's group and acquires the new validity state\n * \n * The event that triggers validation is defined by the field type\n * \n * Only if the new validityState is invalid is the validation error object \n * dispatched to the store to update state and render the error\n * \n */\nexport const initRealTimeValidation = store => {\n    const handler = groupName => () => {\n        const { groups, errors } = store.getState();\n        \n        if (!groups[groupName].valid && errors[groupName]) {\n            store.update(reducers[ACTIONS.CLEAR_ERROR](store.getState(), groupName), [ clearError(groupName) ]);\n        }\n        getGroupValidityState(groups[groupName])\n            .then(res => {\n                if (!res.reduce(reduceGroupValidityState, true)) {\n                    store.update(\n                        reducers[ACTIONS.VALIDATION_ERROR](store.getState(),\n                            {\n                                group: groupName,\n                                errorMessages: res.reduce(reduceErrorMessages(groupName, store.getState()), [])\n                            }),\n                        [ renderError(groupName) ]\n                    );\n                }\n            });\n    };\n\n    Object.keys(store.getState().groups).forEach(groupName => {\n\n        const { groups } = store.getState();\n        const groupUpdate = { ...groups };\n        \n        if (!groupUpdate[groupName].hasEvent) {\n            groupUpdate[groupName].fields.forEach(input => {\n                input.addEventListener(resolveRealTimeValidationEvent(input), handler(groupName));\n            });\n\n            //;_; can do better?\n            const equalToValidator = groupUpdate[groupName].validators.filter(validator => validator.type === 'equalto');\n            \n            if (equalToValidator.length > 0){\n                equalToValidator[0].params.other.forEach(subgroup => {\n                    subgroup.forEach(item => {\n                        item.addEventListener('blur', handler(groupName));\n                    });\n                });\n            }\n            \n            groupUpdate[groupName].hasEvent = true;\n        }\n      \n        store.update(reducers[ACTIONS.START_REALTIME](store.getState(), {\n            groups: groupUpdate\n        }));\n    });\n};","import { ACTIONS } from '../constants';\nimport reducers from '../reducers';\nimport {\n    getValidityState,\n    reduceGroupValidityState,\n    isFormValid,\n    reduceErrorMessages\n} from '../validator';\nimport { postValidation } from '../validator/post-validation';\nimport { initRealTimeValidation } from '../validator/real-time-validation';\nimport {\n    clearErrors,\n    renderErrors,\n    focusFirstInvalidField\n}  from '../dom';\n\n/**\n * Returns a function that extracts the validityState of the entire form\n * can be used as a form submit eventListener or via the API\n * \n * Submits the form if called as a submit eventListener and is valid\n * Dispatches error state to store if errors\n * \n * @param form [DOM node]\n * \n * @returns [Promise] Resolves with boolean validityState of the form\n * \n */\nexport const validate = store => event => {\n    event && event.preventDefault();\n    store.update(reducers[ACTIONS.CLEAR_ERRORS](store.getState()), [clearErrors]);\n\n    return new Promise(resolve => {\n        const state = store.getState();\n        const { groups, realTimeValidation } = state;\n        getValidityState(groups)\n            .then(validityState => {\n                if (isFormValid(validityState)) return postValidation(event, resolve, store);\n\n                if (realTimeValidation === false) initRealTimeValidation(store);\n\n                store.update(\n                    reducers[ACTIONS.VALIDATION_ERRORS](store.getState(), Object.keys(groups)\n                        .reduce((acc, group, i) => (acc[group] = {\n                            valid: validityState[i].reduce(reduceGroupValidityState, true),\n                            errorMessages: validityState[i].reduce(reduceErrorMessages(group, state), [])\n                        }, acc), {})),\n                    [renderErrors, focusFirstInvalidField]\n                );\n\n                return resolve(false);\n            }).catch(err => console.warn(err));\n    });\n};","import { isSubmitButton, hasNameValue, hasFormactionValue } from './utils';\nimport {\n    createButtonValueNode,\n    cleanupButtonValueNode\n}  from '../dom';\nimport { PREHOOK_DELAY } from '../constants';\n\nexport const postValidation = (event, resolve, store) => {\n    const { settings, form } = store.getState();\n    let buttonValueNode = false;\n    let cachedAction = false;\n    const submit = () => {\n        if (settings.submit) settings.submit();\n        else form.submit();\n    };\n    if (isSubmitButton(document.activeElement)) {\n        if (hasNameValue(document.activeElement)) {\n            buttonValueNode = createButtonValueNode(document.activeElement, form);\n        }\n        if (hasFormactionValue(document.activeElement)) {\n            cachedAction = form.getAttribute('action');\n            form.setAttribute('action', document.activeElement.getAttribute('formaction'));\n        }\n    }\n    if (event && event.target) {\n        if (settings.preSubmitHook) {\n            settings.preSubmitHook();\n            window.setTimeout(submit, PREHOOK_DELAY);\n        } else submit();\n    }\n    buttonValueNode && cleanupButtonValueNode(buttonValueNode);\n    cachedAction && form.setAttribute('action', cachedAction);\n    return resolve(true);\n};","import { ACTIONS } from '../constants';\nimport reducers from '../reducers';\n\n/**\n * Adds a custom validation method to the validation model, used via the API\n * Dispatches add validation method to store to update the validators in a group\n * \n * @param groupName [String] The name attribute shared by the DOM nodes in the group\n * @param method [Function] The validation method (function that returns true or false) that is called on the group\n * @param message [String] Te error message displayed if the validation method returns false\n * \n */\nexport const addMethod = store => (groupName, method, message, fields) => {\n    if ((groupName === undefined || method === undefined || message === undefined) || !store.getState()[groupName] && (document.getElementsByName(groupName).length === 0  && [].slice.call(document.querySelectorAll(`[data-val-group=\"${groupName}\"]`)).length === 0) && !fields) {\n        return console.warn('Custom validation method cannot be added.');\n    }\n    store.update(reducers[ACTIONS.ADD_VALIDATION_METHOD](store.getState(), { groupName, fields, validator: { type: 'custom', method, message } }));\n};","import {\n    removeUnvalidatableGroups,\n    assembleValidationGroup,\n    getGroupValidityState,\n    reduceGroupValidityState,\n    reduceErrorMessages } from '../validator';\nimport { initRealTimeValidation } from '../validator/real-time-validation';\nimport { renderError, clearError, addAXAttributes } from '../dom';\nimport { ACTIONS } from '../constants';\nimport reducers from '../reducers';\n\n/**\n * Adds a group to the validation model, used via the API\n * Dispatches add group method to store \n * \n * @param nodes [Array], nodes comprising the group\n * \n */\nexport const addGroup = store => nodes => {\n    const groups = removeUnvalidatableGroups(nodes.reduce(assembleValidationGroup, {}));\n    if (Object.keys(groups).length === 0) return console.warn('Group cannot be added.');\n\n    store.update(reducers[ACTIONS.ADD_GROUP](store.getState(), groups), [ addAXAttributes, () => {\n        if (store.getState().realTimeValidation) {\n            //if we're already in realtime validation then we need to re-start it with the newly added group\n            initRealTimeValidation(store);\n        }\n    }]);\n};\n\n/**\n * Validates a group individually, used via the API\n * \n * @param groupName, nodes comprising the group to be validated\n * \n * @returns [Promise] Resolves with boolean validityState of the group\n */\nexport const validateGroup = store => groupName => new Promise(resolve => {\n    if (!store.getState().groups[groupName].valid && store.getState().errors[groupName]) {\n        store.update(reducers[ACTIONS.CLEAR_ERROR](store.getState(), groupName), [clearError(groupName)]);\n    }\n    getGroupValidityState(store.getState().groups[groupName])\n        .then(res => {\n            if (!res.reduce(reduceGroupValidityState, true)) {\n                store.update(\n                    reducers[ACTIONS.VALIDATION_ERROR](store.getState(), {\n                        group: groupName,\n                        errorMessages: res.reduce(reduceErrorMessages(groupName, store.getState()), [])\n                    }),\n                    [renderError(groupName)]\n                );\n                return resolve(false);\n            }\n            return resolve(true);\n        });\n});\n\n/**\n * Removes a group from the validation model, used via the API\n * Dispatches remove group method to store \n * \n * @param groupName, nodes comprising the group\n * \n */\nexport const removeGroup = store => groupName => {\n    const state = store.getState();\n    if (state.errors[groupName]) clearError(groupName)(state);\n    store.update(reducers[ACTIONS.REMOVE_GROUP](store.getState(), groupName));\n};","import { createStore } from '../store';\nimport { ACTIONS } from '../constants';\nimport reducers from '../reducers';\nimport { getInitialState } from '../validator';\nimport { validate }  from './validate';\nimport { clearErrors, addAXAttributes }  from '../dom';\nimport { addMethod } from './add-method';\nimport { addGroup, validateGroup, removeGroup } from './group';\n\n\n/**\n * Default function, sets initial state and adds form-level event listeners\n * \n * @param form [DOM node] the form to validate\n * \n * @returns [Object] The API for the instance\n * *\n */\nexport default (form, settings) => {\n    const store = createStore();\n    store.update(reducers[ACTIONS.SET_INITIAL_STATE](getInitialState(form, settings)), [ addAXAttributes ]);\n    form.addEventListener('submit', validate(store));\n    form.addEventListener('reset', () => store.update(reducers[ACTIONS.CLEAR_ERRORS](store.getState()), [ clearErrors ]));\n\n    return {\n        getState: store.getState,\n        validate: validate(store),\n        addMethod: addMethod(store),\n        addGroup: addGroup(store),\n        validateGroup: validateGroup(store),\n        removeGroup: removeGroup(store)\n    };\n};","export default {\n    messages: {\n        required() { return 'You must answer this question.'; } ,\n        email() { return 'Enter a valid email address, for example: example@example.com.'; },\n        pattern() { return 'The value must match the pattern'; },\n        url(){ return 'Enter a valid URL'; },\n        number() { return 'Enter a valid number'; },\n        maxlength(props) { return `Enter no more than ${props.max} characters`; },\n        minlength(props) { return `Enter at least ${props.min} characters`; },\n        max(props){ return `Enter a number lower than or equal to ${props.max}`; },\n        min(props){ return `Enter a number higher than or equal to ${props.min}`;}\n    }\n};","import factory from './lib/factory';\nimport defaults from './lib/defaults';\nimport { getSelection } from './lib/validator/utils';\n\n/*\n * Returns an array of objects augmenting DOM elements that match a selector\n *\n * @param selector, Can be a string, Array of DOM nodes, a NodeList or a single DOM element.\n * @params options, Object, to be merged with defaults to become the settings propery of each returned object\n */\nexport default (selector, options) => {\n    let nodes = getSelection(selector);\n\t\n    return nodes.reduce((acc, el) => {\n        if (!el.hasAttribute('novalidate')) {\n            acc.push(Object.create(factory(el, { ...defaults, ...options })));\n            el.setAttribute('novalidate', 'novalidate');\n        }\n        return acc;\n    }, []);\n\n};"],"names":["ACTIONS","DOTNET_ERROR_SPAN_DATA_ATTRIBUTE","DOM_SELECTOR_PARAMS","DOTNET_PARAMS","length","stringlength","range","min","max","minlength","maxlength","regex","equalto","remote","DOTNET_ADAPTORS","DOTNET_CLASSNAMES","GROUP_ATTRIBUTE","reducers","ACTIONS_SET_INITIAL_STATE","state","data","Object","assign","ACTIONS_CLEAR_ERRORS","groups","keys","reduce","acc","group","errorMessages","valid","ACTIONS_CLEAR_ERROR","nextGroup","ACTIONS_ADD_GROUP","ACTIONS_REMOVE_GROUP","groupName","ACTIONS_ADD_VALIDATION_METHOD","validators","validator","fields","document","querySelector","slice","call","querySelectorAll","getElementsByName","serverErrorNode","ACTIONS_VALIDATION_ERRORS","realTimeValidation","ACTIONS_VALIDATION_ERROR","ACTIONS_START_REALTIME","isCheckable","field","test","type","isHidden","getAttribute","groupValueReducer","input","value","hasValue","trim","checked","Array","isArray","push","resolveGetParams","nodeArrays","map","nodes","encodeURIComponent","extractValueFromGroup","join","prototype","hasOwnProperty","findErrors","errors","serverErrorText","textContent","isOptional","filter","isRequired","regexMethod","paramMethod","reducer","extractValidationParams","params","shouldValidateByParam","param","undefined","required","email","url","dateISO","number","digits","other","subgroupAcc","subgroup","pattern","RegExp","isNaN","parseInt","Promise","resolve","reject","fetch","props","name","additionalfields","method","toUpperCase","body","JSON","stringify","headers","xhr","XMLHttpRequest","open","forEach","key","setRequestHeader","onload","status","response","statusText","onerror","send","then","custom","extractParams","adaptor","hasAttribute","resolveParam","split","indexOf","list","item","replace","escapeAttributeValue","resolveMessages","message","normaliseValidators","extractDataValValidators","_extends","extractAttrValidators","assembleValidationGroup","console","warn","reduceErrorMessages","validity","j","messages","settings","extractErrorMessage","removeUnvalidatableGroups","validationGroups","reduceGroupValidityState","curr","getGroupValidityState","all","validate","methods","err","res","String","catch","clearError","innerHTML","classList","remove","add","parentNode","removeChild","removeAttribute","describedbyid","id","setAttribute","clearErrors","renderErrors","renderError","msg","updateMessageValues","values","newMsg","index","array","createErrorTextNode","node","createTextNode","appendChild","label","error","insertBefore","h","nodeName","attributes","text","createElement","prop","class","nextSibling","errorContainer","hasAriaDescribedbyValue","describedby","focusFirstInvalidField","firstInvalid","focus","addAXAttributes","initRealTimeValidation","store","handler","getState","update","groupUpdate","hasEvent","addEventListener","Number","toLowerCase","isFile","resolveRealTimeValidationEvent","equalToValidator","event","preventDefault","getValidityState","validityState","concat","isFormValid","postValidation","form","buttonValueNode","cachedAction","submit","activeElement","hasNameValue","createButtonValueNode","source","hasFormactionValue","target","preSubmitHook","window","setTimeout","cleanupButtonValueNode","i","addMethod","addGroup","validateGroup","removeGroup","defaults","selector","options","isPrototypeOf","NodeList","HTMLElement","getSelection","el","create","createStore","nextState","effects","effect","getInitialState","factory"],"mappings":"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"}