add True, False, None
This commit is contained in:
1 parent
c0a2e0099c
commit
913ca69e6c
9 files changed
+40372
-39523
No files matched your search
@@ -277,6 +277,12 @@ documentation or memory. Both checks are worth repeating whenever tags, filters
|
||||
|
||||
- Django has no number token: `[\w.]+` is one lexeme and `int()`/`float()` decides whether it is a literal,
|
||||
so `1a`, `1e`, `0x1f`, `1.2.3`, `1__0` and `1.` are variable _lookups_ there and errors here.
|
||||
- Django has no boolean or `None` token either. `True`, `False` and `None` are lookups, which resolve
|
||||
because `BaseContext._reset_dicts` seeds every context with `{"True": True, "False": False, "None": None}`.
|
||||
They are `boolean` and `none` literals here, so that a tool reading `queries/locals.scm` does not count
|
||||
them as references to something the template never defines. Shadowing still parses — `{% with True=1 %}`
|
||||
binds an `identifier`, because the keyword is not valid where a binding name is — but `{{ True.x }}` is
|
||||
an error here and an ordinary two-part lookup in Django, which renders `string_if_invalid`.
|
||||
- A `with` binding written twice (`{% with a=1 a=2 %}`, and the same in `{% include %}` and
|
||||
`{% blocktranslate %}`) is an error here and not in Django, where `token_kwargs` builds a dict and the
|
||||
later value wins. It has no use, so it is treated as the mistake it almost certainly is.
|
||||
|
||||
+4
-1
@@ -342,7 +342,8 @@ const django = grammar({
|
||||
seq($.value, optional(seq("|", $.filter_expression))),
|
||||
filter_expression: ($) => seq($.filter, repeat(seq("|", $.filter))),
|
||||
value: ($) => choice($.literal, $.variable_attribute),
|
||||
literal: ($) => choice($.number, $.string, $.translated_string),
|
||||
literal: ($) =>
|
||||
choice($.number, $.string, $.translated_string, $.boolean, $.none),
|
||||
// digits, with single underscores allowed between them, as Python's
|
||||
// int() and float() accept ("1_000") and Django's Variable relies on
|
||||
number: ($) =>
|
||||
@@ -354,6 +355,8 @@ const django = grammar({
|
||||
* string: "_( 'a' )" is a syntax error there, not a translated literal.
|
||||
*/
|
||||
translated_string: ($) => seq("_(", $.string, ")"),
|
||||
boolean: ($) => choice("True", "False"),
|
||||
none: ($) => "None",
|
||||
attribute: ($) => /[a-zA-Z0-9][a-zA-Z0-9_]*(?:\.[a-zA-Z0-9][a-zA-Z0-9_]*)*/,
|
||||
variable_attribute: ($) =>
|
||||
seq($.identifier, optional(seq(".", $.attribute))),
|
||||
|
||||
@@ -41,6 +41,8 @@ variable: (identifier) @variable.parameter
|
||||
|
||||
(number) @number
|
||||
(string) @string
|
||||
(boolean) @constant.builtin
|
||||
(none) @constant.builtin
|
||||
|
||||
(library
|
||||
(identifier) @module)
|
||||
|
||||
@@ -122,6 +122,14 @@
|
||||
{
|
||||
"type": "SYMBOL",
|
||||
"name": "translated_string"
|
||||
},
|
||||
{
|
||||
"type": "SYMBOL",
|
||||
"name": "boolean"
|
||||
},
|
||||
{
|
||||
"type": "SYMBOL",
|
||||
"name": "none"
|
||||
}
|
||||
]
|
||||
},
|
||||
@@ -150,6 +158,23 @@
|
||||
}
|
||||
]
|
||||
},
|
||||
"boolean": {
|
||||
"type": "CHOICE",
|
||||
"members": [
|
||||
{
|
||||
"type": "STRING",
|
||||
"value": "True"
|
||||
},
|
||||
{
|
||||
"type": "STRING",
|
||||
"value": "False"
|
||||
}
|
||||
]
|
||||
},
|
||||
"none": {
|
||||
"type": "STRING",
|
||||
"value": "None"
|
||||
},
|
||||
"attribute": {
|
||||
"type": "PATTERN",
|
||||
"value": "[a-zA-Z0-9][a-zA-Z0-9_]*(?:\\.[a-zA-Z0-9][a-zA-Z0-9_]*)*"
|
||||
|
||||
@@ -396,6 +396,11 @@
|
||||
]
|
||||
}
|
||||
},
|
||||
{
|
||||
"type": "boolean",
|
||||
"named": true,
|
||||
"fields": {}
|
||||
},
|
||||
{
|
||||
"type": "cache_clause",
|
||||
"named": true,
|
||||
@@ -1699,6 +1704,14 @@
|
||||
"multiple": false,
|
||||
"required": true,
|
||||
"types": [
|
||||
{
|
||||
"type": "boolean",
|
||||
"named": true
|
||||
},
|
||||
{
|
||||
"type": "none",
|
||||
"named": true
|
||||
},
|
||||
{
|
||||
"type": "number",
|
||||
"named": true
|
||||
@@ -2650,6 +2663,14 @@
|
||||
"type": ">=",
|
||||
"named": false
|
||||
},
|
||||
{
|
||||
"type": "False",
|
||||
"named": false
|
||||
},
|
||||
{
|
||||
"type": "True",
|
||||
"named": false
|
||||
},
|
||||
{
|
||||
"type": "_(",
|
||||
"named": false
|
||||
@@ -3074,6 +3095,10 @@
|
||||
"type": "media",
|
||||
"named": false
|
||||
},
|
||||
{
|
||||
"type": "none",
|
||||
"named": true
|
||||
},
|
||||
{
|
||||
"type": "noop",
|
||||
"named": false
|
||||
|
||||
+40163
-39522
File diff suppressed because it is too large.
Load diff
@@ -156,3 +156,29 @@ If Operator Adjacent To Value
|
||||
{% if 1and 2 %}yes{% endif %}
|
||||
|
||||
---
|
||||
|
||||
==================
|
||||
If Is Not None
|
||||
==================
|
||||
|
||||
{% if status is not None %}yes{% endif %}
|
||||
|
||||
---
|
||||
|
||||
(template
|
||||
(content)
|
||||
(if_group
|
||||
(if_clause
|
||||
(predicate
|
||||
(filtered_value
|
||||
(value
|
||||
(variable_attribute
|
||||
(identifier))))
|
||||
(binaryOperator)
|
||||
(filtered_value
|
||||
(value
|
||||
(literal
|
||||
(none)))))
|
||||
(template
|
||||
(content))))
|
||||
(content))
|
||||
@@ -361,3 +361,103 @@ Template Variable With Spaced Filter
|
||||
(filter_expression
|
||||
(filter))))
|
||||
(content))
|
||||
|
||||
==================
|
||||
Template Variable True
|
||||
==================
|
||||
|
||||
{{ True }}
|
||||
|
||||
---
|
||||
|
||||
(template
|
||||
(content)
|
||||
(template_variable
|
||||
(filtered_value
|
||||
(value
|
||||
(literal
|
||||
(boolean)))))
|
||||
(content))
|
||||
|
||||
==================
|
||||
Template Variable False
|
||||
==================
|
||||
|
||||
{{ False }}
|
||||
|
||||
---
|
||||
|
||||
(template
|
||||
(content)
|
||||
(template_variable
|
||||
(filtered_value
|
||||
(value
|
||||
(literal
|
||||
(boolean)))))
|
||||
(content))
|
||||
|
||||
==================
|
||||
Template Variable None
|
||||
==================
|
||||
|
||||
{{ None }}
|
||||
|
||||
---
|
||||
|
||||
(template
|
||||
(content)
|
||||
(template_variable
|
||||
(filtered_value
|
||||
(value
|
||||
(literal
|
||||
(none)))))
|
||||
(content))
|
||||
|
||||
==================
|
||||
Template Variable Boolean As Filter Argument
|
||||
==================
|
||||
|
||||
{{ value|default:True }}
|
||||
|
||||
---
|
||||
|
||||
(template
|
||||
(content)
|
||||
(template_variable
|
||||
(filtered_value
|
||||
(value
|
||||
(variable_attribute
|
||||
(identifier)))
|
||||
(filter_expression
|
||||
(filter
|
||||
argument: (value
|
||||
(literal
|
||||
(boolean)))))))
|
||||
(content))
|
||||
|
||||
==================
|
||||
Template Variable Name Beginning With A Literal
|
||||
==================
|
||||
|
||||
{{ Truest }}
|
||||
|
||||
---
|
||||
|
||||
(template
|
||||
(content)
|
||||
(template_variable
|
||||
(filtered_value
|
||||
(value
|
||||
(variable_attribute
|
||||
(identifier)))))
|
||||
(content))
|
||||
|
||||
==================
|
||||
Template Variable Attribute Of A Literal
|
||||
:error
|
||||
==================
|
||||
|
||||
{{ None.x }}
|
||||
|
||||
---
|
||||
|
||||
@@ -111,3 +111,24 @@ With Repeating A Binding Of The Tag Before It
|
||||
(template
|
||||
(content))))
|
||||
(content))
|
||||
|
||||
==================
|
||||
With A Binding Named After A Literal
|
||||
==================
|
||||
|
||||
{% with True=1 %}a{% endwith %}
|
||||
|
||||
---
|
||||
|
||||
(template
|
||||
(content)
|
||||
(with_group
|
||||
(with_clause
|
||||
variable: (identifier)
|
||||
(filtered_value
|
||||
(value
|
||||
(literal
|
||||
(number))))
|
||||
(template
|
||||
(content))))
|
||||
(content))
|
||||
Reference in new issue
Block a user