Allows actions to use any expression type

Allow any expression to pass data to an action. Added a test for a ternary statement and a string template.
Fixes #1676
pull/1679/head
Jacob Wright 6 years ago
parent f38bdaaadf
commit ba5ede599a

@ -77,7 +77,7 @@ const DIRECTIVES: Record<string, {
attribute(start, end, type, name, expression) { attribute(start, end, type, name, expression) {
return { start, end, type, name, expression }; return { start, end, type, name, expression };
}, },
allowedExpressionTypes: ['Identifier', 'MemberExpression', 'ObjectExpression', 'Literal', 'CallExpression'], allowedExpressionTypes: ['*'],
error: 'Data passed to actions must be an identifier (e.g. `foo`), a member expression ' + error: 'Data passed to actions must be an identifier (e.g. `foo`), a member expression ' +
'(e.g. `foo.bar` or `foo[baz]`), a method call (e.g. `foo()`), or a literal (e.g. `true` or `\'a string\'`' '(e.g. `foo.bar` or `foo[baz]`), a method call (e.g. `foo()`), or a literal (e.g. `true` or `\'a string\'`'
}, },
@ -163,7 +163,8 @@ export function readDirective(
try { try {
expression = readExpression(parser, expressionStart, quoteMark); expression = readExpression(parser, expressionStart, quoteMark);
if (directive.allowedExpressionTypes.indexOf(expression.type) === -1) { const allowed = directive.allowedExpressionTypes;
if (allowed[0] !== '*' && allowed.indexOf(expression.type) === -1) {
parser.error({ parser.error({
code: `invalid-directive-value`, code: `invalid-directive-value`,
message: directive.error message: directive.error

@ -0,0 +1,20 @@
export default {
data: {
target: 'World!',
display: true,
},
html: `
<h1></h1>
`,
test ( assert, component, target, window ) {
const header = target.querySelector( 'h1' );
const eventClick = new window.MouseEvent( 'click' );
header.dispatchEvent( eventClick );
assert.htmlEqual( target.innerHTML, `
<h1>Hello World!</h1>
` );
}
};

@ -0,0 +1,21 @@
<h1 use:insert="display ? `Hello ${target}` : ''"></h1>
<script>
export default {
actions: {
insert(node, text) {
function onClick() {
node.textContent = text;
}
node.addEventListener('click', onClick);
return {
destroy() {
node.removeEventListener('click', onClick);
}
}
}
}
}
</script>
Loading…
Cancel
Save