Skip to content

Commit 63238fc

Browse files
authored
refactor: allow more flexible parsing of expression attributes (#1197)
1 parent 27dd1a4 commit 63238fc

File tree

4 files changed

+56
-5
lines changed

4 files changed

+56
-5
lines changed

.version

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
0.3.896
1+
0.3.903

cmd/templ/fmtcmd/testdata.txtar

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,3 +52,15 @@ templ c() {
5252
</p>
5353
</div>
5454
}
55+
-- d.templ --
56+
package test
57+
58+
templ c(s string) {
59+
<div s= {s}/>
60+
}
61+
-- d.templ --
62+
package test
63+
64+
templ c(s string) {
65+
<div s={ s }/>
66+
}

parser/v2/elementparser.go

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -123,13 +123,13 @@ func (avp attributeValueParser) Parse(pi *parse.Input) (value string, ok bool, e
123123
var (
124124
attributeValueParsers = []attributeValueParser{
125125
// Double quoted.
126-
{EqualsAndQuote: parse.String(`="`), Suffix: parse.String(`"`), UseSingleQuote: false},
126+
{EqualsAndQuote: parse.StringFrom(parse.OptionalWhitespace, parse.String(`="`)), Suffix: parse.String(`"`), UseSingleQuote: false},
127127
// Single quoted.
128-
{EqualsAndQuote: parse.String(`='`), Suffix: parse.String(`'`), UseSingleQuote: true},
128+
{EqualsAndQuote: parse.StringFrom(parse.OptionalWhitespace, parse.String(`='`)), Suffix: parse.String(`'`), UseSingleQuote: true},
129129
// Unquoted.
130130
// A valid unquoted attribute value in HTML is any string of text that is not an empty string,
131131
// and that doesn’t contain spaces, tabs, line feeds, form feeds, carriage returns, ", ', `, =, <, or >.
132-
{EqualsAndQuote: parse.String("="), Suffix: parse.Any(parse.RuneIn(" \t\n\r\"'`=<>/"), parse.EOF[string]()), UseSingleQuote: false},
132+
{EqualsAndQuote: parse.StringFrom(parse.OptionalWhitespace, parse.String("=")), Suffix: parse.Any(parse.RuneIn(" \t\n\r\"'`=<>/"), parse.EOF[string]()), UseSingleQuote: false},
133133
}
134134
constantAttributeParser = parse.Func(func(pi *parse.Input) (attr *ConstantAttribute, ok bool, err error) {
135135
start := pi.Index()
@@ -288,6 +288,8 @@ var boolExpressionAttributeParser = parse.Func(func(pi *parse.Input) (r *BoolExp
288288
return r, true, nil
289289
})
290290

291+
var expressionAttributeStartParser = parse.StringFrom(parse.OptionalWhitespace, parse.String("="), parse.OptionalWhitespace, parse.String("{"), parse.OptionalWhitespace)
292+
291293
var expressionAttributeParser = parse.Func(func(pi *parse.Input) (attr *ExpressionAttribute, ok bool, err error) {
292294
start := pi.Index()
293295

@@ -305,7 +307,7 @@ var expressionAttributeParser = parse.Func(func(pi *parse.Input) (attr *Expressi
305307
}
306308

307309
// ={
308-
if _, ok, err = parse.Or(parse.String("={ "), parse.String("={")).Parse(pi); err != nil || !ok {
310+
if _, ok, err = expressionAttributeStartParser.Parse(pi); err != nil || !ok {
309311
pi.Seek(start)
310312
return
311313
}

parser/v2/elementparser_test.go

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1791,6 +1791,43 @@ func TestElementParser(t *testing.T) {
17911791
},
17921792
},
17931793
},
1794+
{
1795+
name: "element: space before name= { is still parsed as an expression",
1796+
input: `<div hx-vals= { "test" }></div>`,
1797+
expected: &Element{
1798+
Name: "div",
1799+
NameRange: Range{
1800+
From: Position{Index: 1, Line: 0, Col: 1},
1801+
To: Position{Index: 4, Line: 0, Col: 4},
1802+
},
1803+
Attributes: []Attribute{
1804+
&ExpressionAttribute{
1805+
Key: ConstantAttributeKey{
1806+
Name: "hx-vals",
1807+
NameRange: Range{
1808+
From: Position{Index: 5, Line: 0, Col: 5},
1809+
To: Position{Index: 12, Line: 0, Col: 12},
1810+
},
1811+
},
1812+
Expression: Expression{
1813+
Value: `"test"`,
1814+
Range: Range{
1815+
From: Position{
1816+
Index: 16,
1817+
Line: 0,
1818+
Col: 16,
1819+
},
1820+
To: Position{
1821+
Index: 22,
1822+
Line: 0,
1823+
Col: 22,
1824+
},
1825+
},
1826+
},
1827+
},
1828+
},
1829+
},
1830+
},
17941831
}
17951832
for _, tt := range tests {
17961833
t.Run(tt.name, func(t *testing.T) {

0 commit comments

Comments
 (0)