Skip to content

Commit c4f1f74

Browse files
committed
relax the grammar of partial names to allow relative paths ../foo
1 parent e1371c7 commit c4f1f74

File tree

3 files changed

+39
-2
lines changed

3 files changed

+39
-2
lines changed

bin/test/errors/parsing-errors.t

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ Delimiter problems:
6262
$ echo "{{>" > $PROBLEM
6363
$ mustache foo.json $PROBLEM
6464
Template parse error:
65-
File "eof-before-partial.mustache", line 2, character 0: ident expected.
65+
File "eof-before-partial.mustache", line 2, character 0: '}}' expected.
6666
[3]
6767
6868
$ PROBLEM=eof-in-comment.mustache

bin/test/partials.t/run.t

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,3 +3,18 @@ Simple test:
33
$ mustache data.json foo.mustache
44
Inside the include is "Foo Bar !"
55

6+
Include in child or parent directory:
7+
$ mkdir subdir
8+
$ echo "Test from {{src}}" > subdir/test.mustache
9+
$ echo "{{> subdir/test }}" > from_parent.mustache
10+
$ echo '{ "src": "parent" }' > from_parent.json
11+
$ mustache from_parent.json from_parent.mustache
12+
Test from parent
13+
14+
15+
$ mkdir subdir/child
16+
$ echo "{{> ../test }}" > subdir/child/from_child.mustache
17+
$ echo '{ "src": "child" }' > subdir/child/from_child.json
18+
$ (cd subdir/child; mustache from_child.json from_child.mustache)
19+
Test from child
20+

lib/mustache_lexer.mll

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,25 @@ let raw = [^ '{' '}' '\n']*
5555
let id = ['a'-'z' 'A'-'Z' '-' '_' '/'] ['a'-'z' 'A'-'Z' '0'-'9' '-' '_' '/']*
5656
let ident = ('.' | id ('.' id)*)
5757

58+
(* The grammar of partials is very relaxed compared to normal
59+
identifiers: we want to allow dots anywhere to express relative
60+
paths such as ../foo (this is consistent with other implementations
61+
such as the 'mustache' binary provided by the Ruby implementation),
62+
and in general we don't know what is going to be used, given that
63+
partials are controlled programmatically.
64+
65+
We forbid spaces, to ensure that the behavior of trimming spaces
66+
around the partial name is consistent with the other tag, and we
67+
forbid newlines and mustaches to avoid simple delimiter mistakes
68+
({{> foo } ... {{bar}}) being parsed as valid partial names.
69+
70+
(Note: if one wishes to interpret partials using lambdas placed
71+
within the data (foo.bar interpreted as looking up 'foo' then 'bar'
72+
in the input data and hoping to find a user-decided representation
73+
of a function, it is of course possible to restrict the valid names
74+
and split on dots on the user side.) *)
75+
let partial_name = [^ ' ' '\t' '\n' '{' '}']*
76+
5877
rule space = parse
5978
| blank newline { new_line lexbuf; space lexbuf }
6079
| blank { () }
@@ -63,6 +82,9 @@ and ident = parse
6382
| ident { lexeme lexbuf }
6483
| "" { raise (Error "ident expected") }
6584

85+
and partial_name = parse
86+
| partial_name { lexeme lexbuf }
87+
6688
and end_on expected = parse
6789
| ("}}" | "}}}" | "") as lexed { check_mustaches ~expected ~lexed }
6890

@@ -80,7 +102,7 @@ and mustache = parse
80102
| "{{#" { OPEN_SECTION (lex_tag lexbuf space ident (end_on "}}") |> split_ident) }
81103
| "{{^" { OPEN_INVERTED_SECTION (lex_tag lexbuf space ident (end_on "}}") |> split_ident) }
82104
| "{{/" { CLOSE_SECTION (lex_tag lexbuf space ident (end_on "}}") |> split_ident) }
83-
| "{{>" { PARTIAL (0, lex_tag lexbuf space ident (end_on "}}")) }
105+
| "{{>" { PARTIAL (0, lex_tag lexbuf space partial_name (end_on "}}")) }
84106
| "{{!" { COMMENT (tok_arg lexbuf (comment [])) }
85107
| raw newline { new_line lexbuf; RAW (lexeme lexbuf) }
86108
| raw { RAW (lexeme lexbuf) }

0 commit comments

Comments
 (0)