From e6d088d753982a7549d6284ce462c4289206ba95 Mon Sep 17 00:00:00 2001 From: Rich Harris Date: Fri, 17 Mar 2017 15:31:54 -0400 Subject: [PATCH] implement :shorthand attributes --- src/parse/state/tag.js | 28 ++++++++++++- .../attribute-dynamic-shorthand/_config.js | 10 +++++ .../attribute-dynamic-shorthand/main.html | 9 +++++ .../Widget.html | 1 + .../_config.js | 17 ++++++++ .../main.html | 11 +++++ .../samples/attribute-shorthand/input.html | 1 + .../samples/attribute-shorthand/output.json | 40 +++++++++++++++++++ 8 files changed, 115 insertions(+), 2 deletions(-) create mode 100644 test/generator/samples/attribute-dynamic-shorthand/_config.js create mode 100644 test/generator/samples/attribute-dynamic-shorthand/main.html create mode 100644 test/generator/samples/component-data-dynamic-shorthand/Widget.html create mode 100644 test/generator/samples/component-data-dynamic-shorthand/_config.js create mode 100644 test/generator/samples/component-data-dynamic-shorthand/main.html create mode 100644 test/parser/samples/attribute-shorthand/input.html create mode 100644 test/parser/samples/attribute-shorthand/output.json diff --git a/src/parse/state/tag.js b/src/parse/state/tag.js index c6007318af..f315ef69e4 100644 --- a/src/parse/state/tag.js +++ b/src/parse/state/tag.js @@ -204,7 +204,7 @@ function readTagName ( parser ) { function readAttribute ( parser, uniqueNames ) { const start = parser.index; - const name = parser.readUntil( /(\s|=|\/|>)/ ); + let name = parser.readUntil( /(\s|=|\/|>)/ ); if ( !name ) return null; if ( uniqueNames.has( name ) ) { parser.error( 'Attributes need to be unique', start ); @@ -232,7 +232,15 @@ function readAttribute ( parser, uniqueNames ) { }; } - const value = parser.eat( '=' ) ? readAttributeValue( parser ) : true; + let value; + + // :foo is shorthand for foo='{{foo}}' + if ( /^:\w+$/.test( name ) ) { + name = name.slice( 1 ); + value = getShorthandValue( start + 1, name ); + } else { + value = parser.eat( '=' ) ? readAttributeValue( parser ) : true; + } return { start, @@ -312,3 +320,19 @@ function readAttributeValue ( parser ) { parser.error( `Unexpected end of input` ); } + +function getShorthandValue ( start, name ) { + const end = start + name.length; + + return [{ + type: 'AttributeShorthand', + start, + end, + expression: { + type: 'Identifier', + start, + end, + name + } + }]; +} \ No newline at end of file diff --git a/test/generator/samples/attribute-dynamic-shorthand/_config.js b/test/generator/samples/attribute-dynamic-shorthand/_config.js new file mode 100644 index 0000000000..1ecd6c650a --- /dev/null +++ b/test/generator/samples/attribute-dynamic-shorthand/_config.js @@ -0,0 +1,10 @@ +export default { + html: `
`, + + test ( assert, component, target ) { + component.set({ id: 'bar' }); + assert.equal( target.innerHTML, `
` ); + + component.teardown(); + } +}; diff --git a/test/generator/samples/attribute-dynamic-shorthand/main.html b/test/generator/samples/attribute-dynamic-shorthand/main.html new file mode 100644 index 0000000000..25b468a8f1 --- /dev/null +++ b/test/generator/samples/attribute-dynamic-shorthand/main.html @@ -0,0 +1,9 @@ +
+ + diff --git a/test/generator/samples/component-data-dynamic-shorthand/Widget.html b/test/generator/samples/component-data-dynamic-shorthand/Widget.html new file mode 100644 index 0000000000..d465e83f81 --- /dev/null +++ b/test/generator/samples/component-data-dynamic-shorthand/Widget.html @@ -0,0 +1 @@ +

foo: {{foo}}

\ No newline at end of file diff --git a/test/generator/samples/component-data-dynamic-shorthand/_config.js b/test/generator/samples/component-data-dynamic-shorthand/_config.js new file mode 100644 index 0000000000..c0a53c333c --- /dev/null +++ b/test/generator/samples/component-data-dynamic-shorthand/_config.js @@ -0,0 +1,17 @@ +export default { + data: { + foo: 42 + }, + + html: `

foo: 42

`, + + test ( assert, component, target ) { + component.set({ + foo: 99 + }); + + assert.equal( target.innerHTML, `

foo: 99

` ); + + component.teardown(); + } +}; diff --git a/test/generator/samples/component-data-dynamic-shorthand/main.html b/test/generator/samples/component-data-dynamic-shorthand/main.html new file mode 100644 index 0000000000..816def2c2f --- /dev/null +++ b/test/generator/samples/component-data-dynamic-shorthand/main.html @@ -0,0 +1,11 @@ +
+ +
+ + diff --git a/test/parser/samples/attribute-shorthand/input.html b/test/parser/samples/attribute-shorthand/input.html new file mode 100644 index 0000000000..e26deafb3a --- /dev/null +++ b/test/parser/samples/attribute-shorthand/input.html @@ -0,0 +1 @@ +
\ No newline at end of file diff --git a/test/parser/samples/attribute-shorthand/output.json b/test/parser/samples/attribute-shorthand/output.json new file mode 100644 index 0000000000..979a8820ad --- /dev/null +++ b/test/parser/samples/attribute-shorthand/output.json @@ -0,0 +1,40 @@ +{ + "hash": 4120363214, + "html": { + "start": 0, + "end": 10, + "type": "Fragment", + "children": [ + { + "start": 0, + "end": 10, + "type": "Element", + "name": "div", + "attributes": [ + { + "start": 5, + "end": 8, + "type": "Attribute", + "name": "id", + "value": [ + { + "start": 6, + "end": 8, + "type": "AttributeShorthand", + "expression": { + "type": "Identifier", + "start": 6, + "end": 8, + "name": "id" + } + } + ] + } + ], + "children": [] + } + ] + }, + "css": null, + "js": null +} \ No newline at end of file