mirror of
https://github.com/Reuh/anselme.git
synced 2025-10-27 08:39:30 +00:00
[internal] clean up format calls in interpolations, add format(val::is string) without quotes
This commit is contained in:
parent
bdc4f8a13a
commit
02fa9d075d
8 changed files with 39 additions and 31 deletions
|
|
@ -36,10 +36,10 @@ local StringInterpolation = ast.abstract.Node {
|
|||
local t = {}
|
||||
for _, e in ipairs(self.list) do
|
||||
local r = e:eval(state)
|
||||
if String:is(r) then
|
||||
r = r.string
|
||||
else
|
||||
r = r:format(state)
|
||||
if String:is(e) then -- raw string
|
||||
r = e.string
|
||||
else -- interpolation
|
||||
r = e:format_custom(state)
|
||||
end
|
||||
table.insert(t, r)
|
||||
end
|
||||
|
|
|
|||
|
|
@ -39,14 +39,14 @@ local TextInterpolation = ast.abstract.Node {
|
|||
local tags = tag_manager:get(state)
|
||||
for _, e in ipairs(self.list) do
|
||||
local r = e:eval(state)
|
||||
if String:is(r) then
|
||||
if String:is(e) then -- raw string
|
||||
t:insert(r, tags)
|
||||
elseif Text:is(r) then
|
||||
elseif Text:is(r) then -- interpolation
|
||||
for _, v in ipairs(r.list) do
|
||||
t:insert(v[1], v[2])
|
||||
end
|
||||
else
|
||||
t:insert(String:new(r:format(state)), tags)
|
||||
t:insert(String:new(r:format_custom(state)), tags)
|
||||
end
|
||||
end
|
||||
return t
|
||||
|
|
|
|||
|
|
@ -2,10 +2,6 @@ local ast = require("anselme.ast")
|
|||
|
||||
local operator_priority = require("anselme.common").operator_priority
|
||||
|
||||
local format_identifier
|
||||
|
||||
local ArgumentTuple
|
||||
|
||||
local Typed
|
||||
Typed = ast.abstract.Runtime {
|
||||
type = "typed",
|
||||
|
|
@ -19,15 +15,6 @@ Typed = ast.abstract.Runtime {
|
|||
end,
|
||||
|
||||
_format = function(self, state, prio, ...)
|
||||
-- try custom format
|
||||
if state and state.scope:defined(format_identifier) then
|
||||
local custom_format = format_identifier:eval(state)
|
||||
local args = ArgumentTuple:new(self)
|
||||
local fn, d_args = custom_format:dispatch(state, args)
|
||||
if fn then
|
||||
return custom_format:call(state, d_args):format(state, prio, ...)
|
||||
end
|
||||
end
|
||||
return ("type(%s, %s)"):format(self.expression:format(state, operator_priority["_,_"], ...), self.type_expression:format_right(state, operator_priority["_,_"], ...))
|
||||
end,
|
||||
|
||||
|
|
@ -37,8 +24,4 @@ Typed = ast.abstract.Runtime {
|
|||
end
|
||||
}
|
||||
|
||||
package.loaded[...] = Typed
|
||||
format_identifier = ast.Identifier:new("format")
|
||||
ArgumentTuple = ast.ArgumentTuple
|
||||
|
||||
return Typed
|
||||
|
|
|
|||
|
|
@ -14,10 +14,10 @@ local unpack = table.unpack or unpack
|
|||
|
||||
local uuid = require("anselme.common").uuid
|
||||
|
||||
local Call, Identifier, Struct, Tuple, String, Pair
|
||||
local Call, Identifier, Struct, Tuple, String, Pair, ArgumentTuple
|
||||
local resume_manager
|
||||
|
||||
local custom_call_identifier
|
||||
local custom_call_identifier, custom_format_identifier
|
||||
|
||||
local context_max_length = 50
|
||||
local function cutoff_text(str)
|
||||
|
|
@ -372,6 +372,18 @@ Node = class {
|
|||
_format_priority_cache = nil, -- cached priority
|
||||
from_symbol = nil, -- last symbol this node was retrived from
|
||||
|
||||
-- return a human-readable, string representation of the node
|
||||
-- this works by calling the `format(node)` anselme method (if the method returns a non-string value, it is converted to a string using :format)
|
||||
format_custom = function(self, state)
|
||||
local custom_format = custom_format_identifier:eval(state)
|
||||
local r = custom_format:call(state, ArgumentTuple:new(self))
|
||||
if String:is(r) then
|
||||
return r.string
|
||||
else
|
||||
return r:format(state)
|
||||
end
|
||||
end,
|
||||
|
||||
-- return Lua value
|
||||
-- this should probably be only called on a Node that is already evaluated
|
||||
-- redefine if you want, probably only for nodes that are already evaluated
|
||||
|
|
@ -430,8 +442,9 @@ Node = class {
|
|||
-- Thus, any require here that may require other Nodes shall be done here. This method is called in anselme.lua after everything else is required.
|
||||
_i_hate_cycles = function(self)
|
||||
local ast = require("anselme.ast")
|
||||
Call, Identifier, Struct, Tuple, String, Pair = ast.Call, ast.Identifier, ast.Struct, ast.Tuple, ast.String, ast.Pair
|
||||
Call, Identifier, Struct, Tuple, String, Pair, ArgumentTuple = ast.Call, ast.Identifier, ast.Struct, ast.Tuple, ast.String, ast.Pair, ast.ArgumentTuple
|
||||
custom_call_identifier = Identifier:new("_!")
|
||||
custom_format_identifier = Identifier:new("format")
|
||||
|
||||
resume_manager = require("anselme.state.resume_manager")
|
||||
end,
|
||||
|
|
|
|||
|
|
@ -5,12 +5,18 @@ return {
|
|||
{
|
||||
"print", "(a)",
|
||||
function(state, a)
|
||||
print(a:format(state))
|
||||
print(a:format_custom(state))
|
||||
return Nil:new()
|
||||
end
|
||||
},
|
||||
{
|
||||
"hash", "(a)",
|
||||
"format", "(val)",
|
||||
function(state, val)
|
||||
return String:new(val:format(state))
|
||||
end
|
||||
},
|
||||
{
|
||||
function(state, a)
|
||||
return String:new(a:hash())
|
||||
end
|
||||
|
|
|
|||
|
|
@ -9,5 +9,11 @@ return {
|
|||
function(state, s)
|
||||
return Number:new(utf8.len(s.string))
|
||||
end
|
||||
},
|
||||
{
|
||||
"format", "(val::is string)",
|
||||
function(state, val)
|
||||
return val
|
||||
end
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -485,7 +485,7 @@ Strings literal starts with a `"` and end with a `"`. Specials characters, inclu
|
|||
* `\n` is replaced with a newline
|
||||
* `\t` is replaced with a tab character
|
||||
|
||||
Non-escaped `{` in the string start an interpolated expression; any expression can then follow, but a closing `}` is expected after it. When the string literal is evaluated, each interpolated expression will be evaluated, the returned value will be formatted to a string and appear in the string where the `{` expression `}` appeared in the literal.
|
||||
Non-escaped `{` in the string start an interpolated expression; any expression can then follow, but a closing `}` is expected after it. When the string literal is evaluated, each interpolated expression will be evaluated, the returned value will be converted to a string using `format` and appear in the string where the `{` expression `}` appeared in the literal.
|
||||
|
||||
Strings can contain newlines.
|
||||
|
||||
|
|
@ -680,7 +680,7 @@ var!type // returns "$"
|
|||
var!value // returns 10
|
||||
```
|
||||
|
||||
When trying to convert the custom type to a string, for example in a string interpolation, the `format(custom type)` function call will be tried. If the function can be called, its return value will be used as the string representation of the value.
|
||||
When trying to convert the custom type to a string, for example in a string interpolation, the `format(custom type)` function will be called. How custom types appear in strings can therefore be changed by overloading the `format` function.
|
||||
|
||||
```
|
||||
:var = type(10, "$")
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
--# run #--
|
||||
--- text ---
|
||||
| {}"" {}"\"Name: Darmanin\nAge: 38\"" {}"" |
|
||||
| {}"" {}"Name: Darmanin\nAge: 38" {}"" |
|
||||
--- return ---
|
||||
()
|
||||
--# saved #--
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue