Skip to content

Instantly share code, notes, and snippets.

@mwpastore
Last active July 28, 2017 13:03
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save mwpastore/a67ee3018a421dd4742ac45c057e7718 to your computer and use it in GitHub Desktop.
Save mwpastore/a67ee3018a421dd4742ac45c057e7718 to your computer and use it in GitHub Desktop.
ember-cp-validations preprocessor and helper for deferred validations
import Model from 'ember-data/model';
import { validator } from 'ember-cp-validations';
import attr from 'ember-data/attr';
import buildValidations from '../utils/build-validations';
const ValidationsMixin = buildValidations({
street: {
deferred: true, // N.B.
validators: [
validator('presence', true)
]
}
});
export default Model.extend(ValidationsMixin, {
street: attr('string') // e.g. 1060 W Addison St
});
import { buildValidations } from 'ember-cp-validations';
import { not, oneWay, or } from '@ember/object/computed';
const { isArray } = Array;
export default function(locals, global={}) {
let deferredGlobal = false;
if (typeof global.deferred !== 'undefined') {
deferredGlobal = !!global.deferred;
delete global.deferred;
}
Object.keys(locals).forEach((key) => {
if (typeof locals[key].validators === 'undefined') {
locals[key] = {
validators: isArray(locals[key]) ? locals[key] : [locals[key]]
}
}
const local = locals[key];
let deferred = deferredGlobal;
if (typeof local.deferred !== 'undefined') {
deferred = !!local.deferred;
delete local.deferred;
}
if (deferred) {
const
cp = not(`model.validations.attrs2.${key}.shouldValidate`),
disabled = local.disabled || global.disabled;
if (typeof disabled !== 'undefined') {
local._shouldNotValidate = cp;
local._originalDisabled = disabled;
local.disabled = or('_shouldNotValidate', '_originalDisabled');
}
else {
local.disabled = cp;
}
}
});
return buildValidations(locals, global).reopen({
init() {
this._super(...arguments);
const
validations = this.get('validations'),
attrs = validations.set('attrs2', {});
validations.set('shouldValidate', false);
Object.keys(locals).forEach((key) => {
attrs[key] = {
_validations: validations,
shouldValidate: oneWay('_validations.shouldValidate')
};
});
}
});
}
{{input
value=address.street
focus-out=(v-mut address 'street' 'shouldValidate')
has-error=(v-get address 'street' 'isValid')
}}
{{#each (v-get address 'street' 'messages') as |message|}}
<div class="error">
{{message}}
</div>
{{/each}}
{{! form submit will additionally do a (v-mut address 'shouldValidate') before proceeding }}
import { helper } from '@ember/component/helper';
import { assert } from '@ember/debug';
import { get, set } from '@ember/object';
export default helper(([object, ...args], { value=true }) => {
assert('v-mut called on ${object} with wrong number of arguments', !(
args.length < 1 || args.length > 2
));
let
path = get(object, 'validations'),
flag;
if (args.length === 2) {
const key = args[0];
flag = args[1];
path = get(path, `attrs2.${key}`);
assert(`v-mut called for non-existent \`${key}' validation on ${object}`, !(
typeof path === 'undefined'
));
}
else {
flag = args[0];
}
return () => {
set(path, flag, value);
};
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment