Format TypeScript expressions in Vue template attributes (#14506)

Co-authored-by: fisker <lionkay@gmail.com>
This commit is contained in:
Seiyaandfisker authored and GitHub committed 2023-03-24 09:10:49 +08:00
1 parent 6d21de11fd
commit e154250e19
23 files changed
+724 -169

No files matched your search

+22
View File
@@ -0,0 +1,22 @@
#### Format TypeScript expression in attribute bindings (#14506 by @seiyab)
<!-- prettier-ignore -->
```vue
<!-- Input -->
<script lang="ts"></script>
<template>
<comp :foo=" (a:string)=>1"/>
</template>
<!-- Prettier stable -->
<script lang="ts"></script>
<template>
<comp :foo=" (a:string)=>1" />
</template>
<!-- Prettier main -->
<script lang="ts"></script>
<template>
<comp :foo="(a: string) => 1" />
</template>
```
+17 -6
View File
@@ -57,7 +57,8 @@ async function printEmbeddedAttributeValue(node, htmlTextToDoc, options) {
rootNode &&
(rootNode.type === "ObjectExpression" ||
rootNode.type === "ArrayExpression" ||
(options.parser === "__vue_expression" &&
((options.parser === "__vue_expression" ||
options.parser === "__vue_ts_expression") &&
(rootNode.type === "TemplateLiteral" ||
rootNode.type === "StringLiteral")))
) {
@@ -105,11 +106,11 @@ async function printEmbeddedAttributeValue(node, htmlTextToDoc, options) {
if (options.parser === "vue") {
if (node.fullName === "v-for") {
return printVueFor(getValue(), attributeTextToDoc);
return printVueFor(getValue(), attributeTextToDoc, options);
}
if (isVueSlotAttribute(node) || isVueSfcBindingsAttribute(node, options)) {
return printVueBindings(getValue(), attributeTextToDoc);
return printVueBindings(getValue(), attributeTextToDoc, options);
}
/**
@@ -132,7 +133,9 @@ async function printEmbeddedAttributeValue(node, htmlTextToDoc, options) {
if (isKeyMatched(vueEventBindingPatterns)) {
const value = getValue();
const parser = isVueEventBindingExpression(value)
? "__js_expression"
? options.__should_parse_vue_template_with_ts
? "__ts_expression"
: "__js_expression"
: options.__should_parse_vue_template_with_ts
? "__vue_ts_event_binding"
: "__vue_event_binding";
@@ -141,13 +144,21 @@ async function printEmbeddedAttributeValue(node, htmlTextToDoc, options) {
if (isKeyMatched(vueExpressionBindingPatterns)) {
return printMaybeHug(
await attributeTextToDoc(getValue(), { parser: "__vue_expression" })
await attributeTextToDoc(getValue(), {
parser: options.__should_parse_vue_template_with_ts
? "__vue_ts_expression"
: "__vue_expression",
})
);
}
if (isKeyMatched(jsExpressionBindingPatterns)) {
return printMaybeHug(
await attributeTextToDoc(getValue(), { parser: "__js_expression" })
await attributeTextToDoc(getValue(), {
parser: options.__should_parse_vue_template_with_ts
? "__ts_expression"
: "__js_expression",
})
);
}
}
+22 -5
View File
@@ -1,24 +1,35 @@
import { group } from "../document/builders.js";
/**
* @typedef {import("../document/builders.js").Doc} Doc
*/
/**
* v-for="... in ..."
* v-for="... of ..."
* v-for="(..., ...) in ..."
* v-for="(..., ...) of ..."
*
* @param {*} value
* @param {(code: string, opts: *) => Doc} attributeTextToDoc
* @param {*} options
* @returns {Promise<Doc>}
*/
async function printVueFor(value, attributeTextToDoc) {
async function printVueFor(value, attributeTextToDoc, options) {
const { left, operator, right } = parseVueFor(value);
const parseWithTs = options.__should_parse_vue_template_with_ts;
return [
group(
await attributeTextToDoc(`function _(${left}) {}`, {
parser: "babel",
parser: parseWithTs ? "babel-ts" : "babel",
__isVueForBindingLeft: true,
})
),
" ",
operator,
" ",
await attributeTextToDoc(right, { parser: "__js_expression" }),
await attributeTextToDoc(right, {
parser: parseWithTs ? "__ts_expression" : "__js_expression",
}),
];
}
@@ -68,9 +79,15 @@ function parseVueFor(value) {
};
}
function printVueBindings(value, attributeTextToDoc) {
/**
* @param {*} value
* @param {(code: string, opts: *) => Doc} attributeTextToDoc
* @param {*} options
* @returns {Doc}
*/
function printVueBindings(value, attributeTextToDoc, options) {
return attributeTextToDoc(`function _(${value}) {}`, {
parser: "babel",
parser: options.__should_parse_vue_template_with_ts ? "babel-ts" : "babel",
__isVueBindings: true,
});
}
+1
View File
@@ -252,6 +252,7 @@ export default {
"babel-ts": babelTs,
/** @internal */
__js_expression: babelExpression,
__ts_expression: babelTSExpression,
/** for vue filter */
__vue_expression: babelExpression,
/** for vue filter written in TS */
+2 -1
View File
@@ -339,7 +339,8 @@ const isBitwiseOrExpression = (node) =>
function isVueFilterSequenceExpression(path, options) {
return (
options.parser === "__vue_expression" &&
(options.parser === "__vue_expression" ||
options.parser === "__vue_ts_expression") &&
isBitwiseOrExpression(path.node) &&
!path.hasAncestor(
(node) => !isBitwiseOrExpression(node) && node.type !== "JsExpressionRoot"
+1
View File
@@ -180,6 +180,7 @@ function attachComments(ast, options) {
options.parser === "json" ||
options.parser === "json5" ||
options.parser === "__js_expression" ||
options.parser === "__ts_expression" ||
options.parser === "__vue_expression" ||
options.parser === "__vue_ts_expression"
) {
+1
View File
@@ -9,6 +9,7 @@ export const parsers = createParsers([
"babel-flow",
"babel-ts",
"__js_expression",
"__ts_expression",
"__vue_expression",
"__vue_ts_expression",
"__vue_event_binding",
@@ -41,3 +41,39 @@ function log(...args) {
================================================================================
`;
exports[`function-expression.vue format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
| printWidth
=====================================input======================================
<script setup lang="ts"></script>
<template>
<div @click=" ( x : never) => null">arrow</div>
<div @click=" function( a : unknown[]) {
console.log( 'abcdefg');
return;
}">anonymous function</div>
</template>
=====================================output=====================================
<script setup lang="ts"></script>
<template>
<div @click="(x: never) => null">arrow</div>
<div
@click="
function (a: unknown[]) {
console.log('abcdefg');
return;
}
"
>
anonymous function
</div>
</template>
================================================================================
`;
@@ -0,0 +1,9 @@
<script setup lang="ts"></script>
<template>
<div @click=" ( x : never) => null">arrow</div>
<div @click=" function( a : unknown[]) {
console.log( 'abcdefg');
return;
}">anonymous function</div>
</template>
@@ -1,5 +1,41 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`attribute-expr.vue format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
| printWidth
=====================================input======================================
<script lang="ts"></script>
<template>
<comp :foo=" (a:string)=>1"/>
<comp :foo=" <X extends Something & AnothoerOne, Y extends unknown[]>(x:X,y:Y)=>y.length + x.foobar.abcdefg"/>
<comp :foo="(myFunction<T |U>(qwerty,qwerty.qwerty?.qwerty)as any) + x.filter(abcdefg as never).join(xxx)"/>
</template>
=====================================output=====================================
<script lang="ts"></script>
<template>
<comp :foo="(a: string) => 1" />
<comp
:foo="
<X extends Something & AnothoerOne, Y extends unknown[]>(x: X, y: Y) =>
y.length + x.foobar.abcdefg
"
/>
<comp
:foo="
(myFunction<T | U>(qwerty, qwerty.qwerty?.qwerty) as any) +
x.filter(abcdefg as never).join(xxx)
"
/>
</template>
================================================================================
`;
exports[`basic.vue format 1`] = `
====================================options=====================================
parsers: ["vue"]
@@ -8,6 +44,7 @@ printWidth: 80
=====================================input======================================
<template>
<p v-if="isFolder(file)">{{ ( file as mymodule.Folder ).deadline }}</p>
<prettier :format=" myFunc( o as unknown )" />
</template>
<script lang="ts"></script>
@@ -15,6 +52,7 @@ printWidth: 80
=====================================output=====================================
<template>
<p v-if="isFolder(file)">{{ (file as mymodule.Folder).deadline }}</p>
<prettier :format="myFunc(o as unknown)" />
</template>
<script lang="ts"></script>
@@ -22,6 +60,123 @@ printWidth: 80
================================================================================
`;
exports[`comment.vue format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
| printWidth
=====================================input======================================
<template>
<div v-if="
// leading comment
isFolder( /* NOTE: I like pizza */file)
// trailing comment
"
:format=" /* leading comment */ myFunc( /* NOTE: I like banana */ o as unknown ) /* trailing comment */"
>{{ /* leading comment */ ( file as /* NOTE: I like sushi */ mymodule.Folder ).deadline /* trailing comment */ }}</div>
</template>
<script lang="ts"></script>
=====================================output=====================================
<template>
<div
v-if="
// leading comment
isFolder(/* NOTE: I like pizza */ file)
// trailing comment
"
:format="
/* leading comment */ myFunc(
/* NOTE: I like banana */ o as unknown,
) /* trailing comment */
"
>
{{
/* leading comment */ (file as /* NOTE: I like sushi */ mymodule.Folder)
.deadline /* trailing comment */
}}
</div>
</template>
<script lang="ts"></script>
================================================================================
`;
exports[`filter.vue format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
| printWidth
=====================================input======================================
<script setup lang="ts"></script>
<!-- vue filters are only allowed in v-bind and interpolation -->
<template>
<div>
<div class="allowed">{{
value | thisIsARealSuperLongFilterPipe("arg1", arg2 as unknown) | anotherPipeLongJustForFun | pipeTheThird
}}</div>
<div class="allowed" v-bind:something='
value | thisIsARealSuperLongFilterPipe("arg1", arg2 as unknown) | anotherPipeLongJustForFun | pipeTheThird
'></div>
<div class="allowed" :class='
value | thisIsARealSuperLongFilterPipe("arg1", arg2 as unknown) | anotherPipeLongJustForFun | pipeTheThird'
></div>
<div class="not-allowed" v-if='
value | thisIsARealSuperLongBitwiseOr("arg1", arg2 as unknown) | anotherBitwiseOrLongJustForFun | bitwiseOrTheThird
'></div>
</div>
</template>
=====================================output=====================================
<script setup lang="ts"></script>
<!-- vue filters are only allowed in v-bind and interpolation -->
<template>
<div>
<div class="allowed">
{{
value
| thisIsARealSuperLongFilterPipe("arg1", arg2 as unknown)
| anotherPipeLongJustForFun
| pipeTheThird
}}
</div>
<div
class="allowed"
v-bind:something="
value
| thisIsARealSuperLongFilterPipe('arg1', arg2 as unknown)
| anotherPipeLongJustForFun
| pipeTheThird
"
></div>
<div
class="allowed"
:class="
value
| thisIsARealSuperLongFilterPipe('arg1', arg2 as unknown)
| anotherPipeLongJustForFun
| pipeTheThird
"
></div>
<div
class="not-allowed"
v-if="
value |
thisIsARealSuperLongBitwiseOr('arg1', arg2 as unknown) |
anotherBitwiseOrLongJustForFun |
bitwiseOrTheThird
"
></div>
</div>
</template>
================================================================================
`;
exports[`not-working-with-non-ts-script.vue format 1`] = `
====================================options=====================================
parsers: ["vue"]
@@ -30,6 +185,7 @@ printWidth: 80
=====================================input======================================
<template>
<p v-if="isFolder(file)">{{ ( file as mymodule.Folder ).deadline }}</p>
<prettier :format=" myFunc( o as unknown )" />
</template>
<script></script>
@@ -37,6 +193,7 @@ printWidth: 80
=====================================output=====================================
<template>
<p v-if="isFolder(file)">{{ ( file as mymodule.Folder ).deadline }}</p>
<prettier :format=" myFunc( o as unknown )" />
</template>
<script></script>
@@ -0,0 +1,7 @@
<script lang="ts"></script>
<template>
<comp :foo=" (a:string)=>1"/>
<comp :foo=" <X extends Something & AnothoerOne, Y extends unknown[]>(x:X,y:Y)=>y.length + x.foobar.abcdefg"/>
<comp :foo="(myFunction<T |U>(qwerty,qwerty.qwerty?.qwerty)as any) + x.filter(abcdefg as never).join(xxx)"/>
</template>
+1
View File
@@ -1,5 +1,6 @@
<template>
<p v-if="isFolder(file)">{{ ( file as mymodule.Folder ).deadline }}</p>
<prettier :format=" myFunc( o as unknown )" />
</template>
<script lang="ts"></script>
@@ -0,0 +1,11 @@
<template>
<div v-if="
// leading comment
isFolder( /* NOTE: I like pizza */file)
// trailing comment
"
:format=" /* leading comment */ myFunc( /* NOTE: I like banana */ o as unknown ) /* trailing comment */"
>{{ /* leading comment */ ( file as /* NOTE: I like sushi */ mymodule.Folder ).deadline /* trailing comment */ }}</div>
</template>
<script lang="ts"></script>
+19
View File
@@ -0,0 +1,19 @@
<script setup lang="ts"></script>
<!-- vue filters are only allowed in v-bind and interpolation -->
<template>
<div>
<div class="allowed">{{
value | thisIsARealSuperLongFilterPipe("arg1", arg2 as unknown) | anotherPipeLongJustForFun | pipeTheThird
}}</div>
<div class="allowed" v-bind:something='
value | thisIsARealSuperLongFilterPipe("arg1", arg2 as unknown) | anotherPipeLongJustForFun | pipeTheThird
'></div>
<div class="allowed" :class='
value | thisIsARealSuperLongFilterPipe("arg1", arg2 as unknown) | anotherPipeLongJustForFun | pipeTheThird'
></div>
<div class="not-allowed" v-if='
value | thisIsARealSuperLongBitwiseOr("arg1", arg2 as unknown) | anotherBitwiseOrLongJustForFun | bitwiseOrTheThird
'></div>
</div>
</template>
@@ -1,5 +1,6 @@
<template>
<p v-if="isFolder(file)">{{ ( file as mymodule.Folder ).deadline }}</p>
<prettier :format=" myFunc( o as unknown )" />
</template>
<script></script>
@@ -19,3 +19,57 @@ printWidth: 80
================================================================================
`;
exports[`ts.vue format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
| printWidth
=====================================input======================================
<script lang="ts"></script>
<template>
<div
v-for="a:number of x as number[]"
v-for="[ a , b] : [ string,string ] of x as Array< [string, string]>"
v-for=" a of list.map( (x:any): unknown => x.foo.bar)"
v-for="([longLongProp, longLongProp, [longLongProp, longLongProp='Hello, Prettier!', [longLongProp, longLongProp, anotherLongLongProp=[longLongProp, longLongProp, anotherLongLongProp, yetAnotherLongLongProp], yetAnotherLongLongProp], yetAnotherLongLongProp], yetAnotherLongLongProp], index) of longLongLongLongLongLongLongLongList"
>
</div>
</template>
=====================================output=====================================
<script lang="ts"></script>
<template>
<div
v-for="a: number of x as number[]"
v-for="[a, b]: [string, string] of x as Array<[string, string]>"
v-for="a of list.map((x: any): unknown => x.foo.bar)"
v-for="(
[
longLongProp,
longLongProp,
[
longLongProp,
longLongProp = 'Hello, Prettier!',
[
longLongProp,
longLongProp,
anotherLongLongProp = [
longLongProp,
longLongProp,
anotherLongLongProp,
yetAnotherLongLongProp,
],
yetAnotherLongLongProp,
],
yetAnotherLongLongProp,
],
yetAnotherLongLongProp,
],
index
) of longLongLongLongLongLongLongLongList"
></div>
</template>
================================================================================
`;
+10
View File
@@ -0,0 +1,10 @@
<script lang="ts"></script>
<template>
<div
v-for="a:number of x as number[]"
v-for="[ a , b] : [ string,string ] of x as Array< [string, string]>"
v-for=" a of list.map( (x:any): unknown => x.foo.bar)"
v-for="([longLongProp, longLongProp, [longLongProp, longLongProp='Hello, Prettier!', [longLongProp, longLongProp, anotherLongLongProp=[longLongProp, longLongProp, anotherLongLongProp, yetAnotherLongLongProp], yetAnotherLongLongProp], yetAnotherLongLongProp], yetAnotherLongLongProp], index) of longLongLongLongLongLongLongLongList"
>
</div>
</template>
@@ -1752,63 +1752,35 @@ semi: false
=====================================input======================================
<!-- #7396 -->
<template>
<MyComponent :attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"/>
</template>
<template>
<MyComponent :attr="\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
+\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`"/>
</template>
<template>
<MyComponent :attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo + bar} template literal value\`"/>
</template>
<template>
<MyComponent :src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"/>
</template>
<template>
<MyComponent :src="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"/>
</template>
<template>
<MyComponent :src="100000000000000000000000000000000000000000000000000000000000000000000000000"/>
<MyComponent
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
+\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`"
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo + bar} template literal value\`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"
:num="100000000000000000000000000000000000000000000000000000000000000000000000000"
/>
</template>
=====================================output=====================================
<!-- #7396 -->
<template>
<MyComponent
:attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
/>
</template>
<template>
<MyComponent
:attr="
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="
\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\` +
\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
"
/>
</template>
<template>
<MyComponent
:attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${
foo + bar
} template literal value\`"
/>
</template>
<template>
<MyComponent
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
/>
</template>
<template>
<MyComponent
:src="
:add="
'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' +
'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'
"
/>
</template>
<template>
<MyComponent
:src="
:num="
100000000000000000000000000000000000000000000000000000000000000000000000000
"
/>
@@ -1826,63 +1798,35 @@ trailingComma: "es5"
=====================================input======================================
<!-- #7396 -->
<template>
<MyComponent :attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"/>
</template>
<template>
<MyComponent :attr="\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
+\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`"/>
</template>
<template>
<MyComponent :attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo + bar} template literal value\`"/>
</template>
<template>
<MyComponent :src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"/>
</template>
<template>
<MyComponent :src="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"/>
</template>
<template>
<MyComponent :src="100000000000000000000000000000000000000000000000000000000000000000000000000"/>
<MyComponent
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
+\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`"
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo + bar} template literal value\`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"
:num="100000000000000000000000000000000000000000000000000000000000000000000000000"
/>
</template>
=====================================output=====================================
<!-- #7396 -->
<template>
<MyComponent
:attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
/>
</template>
<template>
<MyComponent
:attr="
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="
\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\` +
\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
"
/>
</template>
<template>
<MyComponent
:attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${
foo + bar
} template literal value\`"
/>
</template>
<template>
<MyComponent
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
/>
</template>
<template>
<MyComponent
:src="
:add="
'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' +
'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'
"
/>
</template>
<template>
<MyComponent
:src="
:num="
100000000000000000000000000000000000000000000000000000000000000000000000000
"
/>
@@ -1900,63 +1844,35 @@ trailingComma: "none"
=====================================input======================================
<!-- #7396 -->
<template>
<MyComponent :attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"/>
</template>
<template>
<MyComponent :attr="\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
+\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`"/>
</template>
<template>
<MyComponent :attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo + bar} template literal value\`"/>
</template>
<template>
<MyComponent :src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"/>
</template>
<template>
<MyComponent :src="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"/>
</template>
<template>
<MyComponent :src="100000000000000000000000000000000000000000000000000000000000000000000000000"/>
<MyComponent
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
+\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`"
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo + bar} template literal value\`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"
:num="100000000000000000000000000000000000000000000000000000000000000000000000000"
/>
</template>
=====================================output=====================================
<!-- #7396 -->
<template>
<MyComponent
:attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
/>
</template>
<template>
<MyComponent
:attr="
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="
\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\` +
\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
"
/>
</template>
<template>
<MyComponent
:attr="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${
foo + bar
} template literal value\`"
/>
</template>
<template>
<MyComponent
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
/>
</template>
<template>
<MyComponent
:src="
:add="
'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' +
'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'
"
/>
</template>
<template>
<MyComponent
:src="
:num="
100000000000000000000000000000000000000000000000000000000000000000000000000
"
/>
@@ -1965,6 +1881,150 @@ trailingComma: "none"
================================================================================
`;
exports[`expression-binding-ts.vue - {"semi":false} format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
semi: false
| printWidth
=====================================input======================================
<!-- #7396 -->
<template>
<MyComponent
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
+\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`"
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo + bar} template literal value\`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"
:num="100000000000000000000000000000000000000000000000000000000000000000000000000"
/>
</template>
<script lang="ts"></script>
=====================================output=====================================
<!-- #7396 -->
<template>
<MyComponent
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="
\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\` +
\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
"
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${
foo + bar
} template literal value\`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="
'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' +
'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'
"
:num="
100000000000000000000000000000000000000000000000000000000000000000000000000
"
/>
</template>
<script lang="ts"></script>
================================================================================
`;
exports[`expression-binding-ts.vue - {"trailingComma":"es5"} format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
trailingComma: "es5"
| printWidth
=====================================input======================================
<!-- #7396 -->
<template>
<MyComponent
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
+\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`"
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo + bar} template literal value\`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"
:num="100000000000000000000000000000000000000000000000000000000000000000000000000"
/>
</template>
<script lang="ts"></script>
=====================================output=====================================
<!-- #7396 -->
<template>
<MyComponent
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="
\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\` +
\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
"
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${
foo + bar
} template literal value\`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="
'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' +
'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'
"
:num="
100000000000000000000000000000000000000000000000000000000000000000000000000
"
/>
</template>
<script lang="ts"></script>
================================================================================
`;
exports[`expression-binding-ts.vue - {"trailingComma":"none"} format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
trailingComma: "none"
| printWidth
=====================================input======================================
<!-- #7396 -->
<template>
<MyComponent
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
+\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`"
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo + bar} template literal value\`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"
:num="100000000000000000000000000000000000000000000000000000000000000000000000000"
/>
</template>
<script lang="ts"></script>
=====================================output=====================================
<!-- #7396 -->
<template>
<MyComponent
:foo="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${foo} template literal value\`"
:bar="
\`\${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\` +
\`\${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${template} \${literal}\`
"
:baz="\`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog \${
foo + bar
} template literal value\`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="
'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' +
'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'
"
:num="
100000000000000000000000000000000000000000000000000000000000000000000000000
"
/>
</template>
<script lang="ts"></script>
================================================================================
`;
exports[`filter.vue - {"semi":false} format 1`] = `
====================================options=====================================
parsers: ["vue"]
@@ -1977,7 +2037,7 @@ semi: false
<div class="allowed">{{value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird}}</div>
<div class="allowed" v-bind:something='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="allowed" :class='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="not-allowed" v-if='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="not-allowed" v-if='value | thisIsARealSuperLongBitwiseOr("arg1", arg2) | anotherBitwiseOrLongJustForFun | bitwiseOrTheThird'></div>
</template>
=====================================output=====================================
@@ -2013,9 +2073,9 @@ semi: false
class="not-allowed"
v-if="
value |
thisIsARealSuperLongFilterPipe('arg1', arg2) |
anotherPipeLongJustForFun |
pipeTheThird
thisIsARealSuperLongBitwiseOr('arg1', arg2) |
anotherBitwiseOrLongJustForFun |
bitwiseOrTheThird
"
></div>
</template>
@@ -2035,7 +2095,7 @@ trailingComma: "es5"
<div class="allowed">{{value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird}}</div>
<div class="allowed" v-bind:something='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="allowed" :class='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="not-allowed" v-if='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="not-allowed" v-if='value | thisIsARealSuperLongBitwiseOr("arg1", arg2) | anotherBitwiseOrLongJustForFun | bitwiseOrTheThird'></div>
</template>
=====================================output=====================================
@@ -2071,9 +2131,9 @@ trailingComma: "es5"
class="not-allowed"
v-if="
value |
thisIsARealSuperLongFilterPipe('arg1', arg2) |
anotherPipeLongJustForFun |
pipeTheThird
thisIsARealSuperLongBitwiseOr('arg1', arg2) |
anotherBitwiseOrLongJustForFun |
bitwiseOrTheThird
"
></div>
</template>
@@ -2093,7 +2153,7 @@ trailingComma: "none"
<div class="allowed">{{value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird}}</div>
<div class="allowed" v-bind:something='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="allowed" :class='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="not-allowed" v-if='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="not-allowed" v-if='value | thisIsARealSuperLongBitwiseOr("arg1", arg2) | anotherBitwiseOrLongJustForFun | bitwiseOrTheThird'></div>
</template>
=====================================output=====================================
@@ -2129,9 +2189,9 @@ trailingComma: "none"
class="not-allowed"
v-if="
value |
thisIsARealSuperLongFilterPipe('arg1', arg2) |
anotherPipeLongJustForFun |
pipeTheThird
thisIsARealSuperLongBitwiseOr('arg1', arg2) |
anotherBitwiseOrLongJustForFun |
bitwiseOrTheThird
"
></div>
</template>
@@ -3480,6 +3540,123 @@ trailingComma: "none"
================================================================================
`;
exports[`slot-ts.vue - {"semi":false} format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
semi: false
| printWidth
=====================================input======================================
<script lang="ts"></script>
<template>
<comp>
<template
v-slot="x: unknown []"
v-slot:named=" y : never"
slot-scope=" { des: {truc: tured } } : any "
#shorthand=" abc : string "
>
{{ x[1] }}
</template>
</comp>
</template>
=====================================output=====================================
<script lang="ts"></script>
<template>
<comp>
<template
v-slot="x: unknown[]"
v-slot:named="y: never"
slot-scope="{ des: { truc: tured } }: any"
#shorthand="abc: string"
>
{{ x[1] }}
</template>
</comp>
</template>
================================================================================
`;
exports[`slot-ts.vue - {"trailingComma":"es5"} format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
trailingComma: "es5"
| printWidth
=====================================input======================================
<script lang="ts"></script>
<template>
<comp>
<template
v-slot="x: unknown []"
v-slot:named=" y : never"
slot-scope=" { des: {truc: tured } } : any "
#shorthand=" abc : string "
>
{{ x[1] }}
</template>
</comp>
</template>
=====================================output=====================================
<script lang="ts"></script>
<template>
<comp>
<template
v-slot="x: unknown[]"
v-slot:named="y: never"
slot-scope="{ des: { truc: tured } }: any"
#shorthand="abc: string"
>
{{ x[1] }}
</template>
</comp>
</template>
================================================================================
`;
exports[`slot-ts.vue - {"trailingComma":"none"} format 1`] = `
====================================options=====================================
parsers: ["vue"]
printWidth: 80
trailingComma: "none"
| printWidth
=====================================input======================================
<script lang="ts"></script>
<template>
<comp>
<template
v-slot="x: unknown []"
v-slot:named=" y : never"
slot-scope=" { des: {truc: tured } } : any "
#shorthand=" abc : string "
>
{{ x[1] }}
</template>
</comp>
</template>
=====================================output=====================================
<script lang="ts"></script>
<template>
<comp>
<template
v-slot="x: unknown[]"
v-slot:named="y: never"
slot-scope="{ des: { truc: tured } }: any"
#shorthand="abc: string"
>
{{ x[1] }}
</template>
</comp>
</template>
================================================================================
`;
exports[`style.vue - {"semi":false} format 1`] = `
====================================options=====================================
parsers: ["vue"]
@@ -0,0 +1,13 @@
<!-- #7396 -->
<template>
<MyComponent
:foo="`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${foo} template literal value`"
:bar="`${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${template} ${literal}`
+`${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${template} ${literal}`"
:baz="`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${foo + bar} template literal value`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"
:num="100000000000000000000000000000000000000000000000000000000000000000000000000"
/>
</template>
<script lang="ts"></script>
+9 -17
View File
@@ -1,20 +1,12 @@
<!-- #7396 -->
<template>
<MyComponent :attr="`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${foo} template literal value`"/>
</template>
<template>
<MyComponent :attr="`${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${template} ${literal}`
+`${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${template} ${literal}`"/>
</template>
<template>
<MyComponent :attr="`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${foo + bar} template literal value`"/>
</template>
<template>
<MyComponent :src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"/>
</template>
<template>
<MyComponent :src="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"/>
</template>
<template>
<MyComponent :src="100000000000000000000000000000000000000000000000000000000000000000000000000"/>
<MyComponent
:foo="`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${foo} template literal value`"
:bar="`${first} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${template} ${literal}`
+`${second} loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${template} ${literal}`"
:baz="`loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog ${foo + bar} template literal value`"
:src="'loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog literal string value'"
:add="'first loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog' + 'second loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooog'"
:num="100000000000000000000000000000000000000000000000000000000000000000000000000"
/>
</template>
+1 -1
View File
@@ -3,5 +3,5 @@
<div class="allowed">{{value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird}}</div>
<div class="allowed" v-bind:something='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="allowed" :class='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="not-allowed" v-if='value | thisIsARealSuperLongFilterPipe("arg1", arg2) | anotherPipeLongJustForFun | pipeTheThird'></div>
<div class="not-allowed" v-if='value | thisIsARealSuperLongBitwiseOr("arg1", arg2) | anotherBitwiseOrLongJustForFun | bitwiseOrTheThird'></div>
</template>
+13
View File
@@ -0,0 +1,13 @@
<script lang="ts"></script>
<template>
<comp>
<template
v-slot="x: unknown []"
v-slot:named=" y : never"
slot-scope=" { des: {truc: tured } } : any "
#shorthand=" abc : string "
>
{{ x[1] }}
</template>
</comp>
</template>
@@ -1,6 +1,6 @@
import loadBuiltinPlugins from "../../src/common/load-builtin-plugins.js";
// Snapshot to avoid mistakes
// Snapshot to prevent mistakes
test("builtin parsers", async () => {
const parserNames = (await loadBuiltinPlugins())
.flatMap((plugin) => (plugin.parsers ? Object.keys(plugin.parsers) : []))
@@ -14,6 +14,7 @@ test("builtin parsers", async () => {
"__ng_binding",
"__ng_directive",
"__ng_interpolation",
"__ts_expression",
"__vue_event_binding",
"__vue_expression",
"__vue_ts_event_binding",