feat!: configure runtime attributes function (#202)
This commit is contained in:
parent
8a9e06448b
commit
dc57221bc9
|
@ -42,13 +42,16 @@ Temple works out of the box without any configuration, but here are a couple of
|
|||
|
||||
### Engine
|
||||
|
||||
By default, Temple uses the built in `EEx.SmartEngine`. If you want to use a different engine, this is as easy as setting the `:engine` configuration option.
|
||||
By default, Temple uses the built in `Phoenix.HTML.Engine`. If you want to use a different engine, this is as easy as setting the `:engine` configuration option.
|
||||
|
||||
You can also configure the function that is used for runtime attributes. By default, Temple uses `Phoenix.HTML.attributes_escape/1`.
|
||||
|
||||
```elixir
|
||||
# config/config.exs
|
||||
|
||||
config :temple,
|
||||
engine: Phoenix.HTML.Engine
|
||||
engine: EEx.SmartEngine,
|
||||
attributes: {Temple, :attributes}
|
||||
```
|
||||
|
||||
### Aliases
|
||||
|
|
|
@ -96,16 +96,40 @@ defmodule Temple do
|
|||
require Temple.Renderer
|
||||
|
||||
Temple.Renderer.compile(unquote(block))
|
||||
|> then(fn
|
||||
{:safe, template} ->
|
||||
template
|
||||
|
||||
template ->
|
||||
template
|
||||
end)
|
||||
end
|
||||
end
|
||||
|
||||
@doc false
|
||||
defdelegate engine, to: Temple.Renderer
|
||||
|
||||
@doc """
|
||||
Compiles runtime attributes.
|
||||
|
||||
To use this function, you set it in application config.
|
||||
|
||||
By default, Temple uses `{Phoenix.HTML, :attributes_escape}`. This is useful if you want to use `EEx.SmartEngine`.
|
||||
|
||||
```elixir
|
||||
config :temple,
|
||||
engine: EEx.SmartEngine,
|
||||
attributes: {Temple, :attributes}
|
||||
```
|
||||
|
||||
> #### Note {: .info}
|
||||
>
|
||||
> This function does not do any HTML escaping
|
||||
|
||||
> #### Note {: .info}
|
||||
>
|
||||
> This function is used by the compiler and shouldn't need to be used directly.
|
||||
"""
|
||||
def attributes(attributes) do
|
||||
for {key, value} <- attributes, into: "" do
|
||||
case value do
|
||||
true -> ~s| #{key}|
|
||||
false -> ""
|
||||
value -> ~s| #{key}="#{value}"|
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -1,6 +1,12 @@
|
|||
defmodule Temple.Ast.Utils do
|
||||
@moduledoc false
|
||||
|
||||
@attributes Application.compile_env(
|
||||
:temple,
|
||||
:attributes,
|
||||
{Phoenix.HTML, :attributes_escape}
|
||||
)
|
||||
|
||||
def snake_to_kebab(stringable),
|
||||
do: stringable |> to_string() |> String.replace_trailing("_", "") |> String.replace("_", "-")
|
||||
|
||||
|
@ -34,7 +40,7 @@ defmodule Temple.Ast.Utils do
|
|||
[
|
||||
{:expr,
|
||||
quote do
|
||||
Phoenix.HTML.attributes_escape(unquote(List.first(attrs)))
|
||||
unquote(__MODULE__).__attributes__(unquote(List.first(attrs)))
|
||||
end}
|
||||
]
|
||||
end
|
||||
|
@ -57,7 +63,7 @@ defmodule Temple.Ast.Utils do
|
|||
def build_attr("rest!", {_, _, _} = value) do
|
||||
expr =
|
||||
quote do
|
||||
Phoenix.HTML.attributes_escape(unquote(value))
|
||||
unquote(__MODULE__).__attributes__(unquote(value))
|
||||
end
|
||||
|
||||
[{:expr, expr}]
|
||||
|
@ -66,7 +72,7 @@ defmodule Temple.Ast.Utils do
|
|||
def build_attr(name, {_, _, _} = value) do
|
||||
expr =
|
||||
quote do
|
||||
Phoenix.HTML.attributes_escape([{unquote(name), unquote(value)}])
|
||||
unquote(__MODULE__).__attributes__([{unquote(name), unquote(value)}])
|
||||
end
|
||||
|
||||
[{:expr, expr}]
|
||||
|
@ -154,4 +160,10 @@ defmodule Temple.Ast.Utils do
|
|||
|
||||
ast
|
||||
end
|
||||
|
||||
def __attributes__(attributes) do
|
||||
{mod, func} = @attributes
|
||||
|
||||
apply(mod, func, [attributes])
|
||||
end
|
||||
end
|
||||
|
|
|
@ -55,7 +55,7 @@ defmodule Temple.Component do
|
|||
import Temple
|
||||
@doc false
|
||||
def component(func, assigns, _) do
|
||||
{:safe, apply(func, [assigns])}
|
||||
apply(func, [assigns])
|
||||
end
|
||||
|
||||
defmacro inner_block(_name, do: do_block) do
|
||||
|
|
|
@ -1,13 +1,22 @@
|
|||
defmodule Temple.Support.Helpers do
|
||||
defmacro assert_html(expected, actual) do
|
||||
quote do
|
||||
assert unquote(expected) == Phoenix.HTML.safe_to_string(unquote(actual)), """
|
||||
--- Expected ---
|
||||
#{unquote(expected)}----------------
|
||||
import ExUnit.Assertions
|
||||
|
||||
--- Actual ---
|
||||
#{Phoenix.HTML.safe_to_string(unquote(actual))}--------------
|
||||
"""
|
||||
defmacro assert_html(expected, actual) do
|
||||
quote location: :keep do
|
||||
unquote(__MODULE__).__assert_html__(unquote_splicing([expected, actual]))
|
||||
end
|
||||
end
|
||||
|
||||
def __assert_html__(expected, actual) do
|
||||
actual = actual |> Phoenix.HTML.Engine.encode_to_iodata!() |> IO.iodata_to_binary()
|
||||
|
||||
assert expected == actual,
|
||||
"""
|
||||
--- Expected ---
|
||||
#{expected}----------------
|
||||
|
||||
--- Actual ---
|
||||
#{actual}--------------
|
||||
"""
|
||||
end
|
||||
end
|
||||
|
|
|
@ -25,7 +25,7 @@ defmodule Temple.Ast.UtilsTest do
|
|||
|
||||
assert Macro.to_string(
|
||||
quote do
|
||||
Phoenix.HTML.attributes_escape([{"class", unquote(class_ast)}])
|
||||
Temple.Ast.Utils.__attributes__([{"class", unquote(class_ast)}])
|
||||
end
|
||||
) == Macro.to_string(actual)
|
||||
end
|
||||
|
@ -74,7 +74,7 @@ defmodule Temple.Ast.UtilsTest do
|
|||
|
||||
assert Macro.to_string(
|
||||
quote do
|
||||
Phoenix.HTML.attributes_escape(unquote(rest_ast))
|
||||
Temple.Ast.Utils.__attributes__(unquote(rest_ast))
|
||||
end
|
||||
) == Macro.to_string(rest_actual)
|
||||
end
|
||||
|
|
|
@ -14,7 +14,7 @@ defmodule TempleTest do
|
|||
end
|
||||
end
|
||||
end
|
||||
|> :erlang.iolist_to_binary()
|
||||
|> Phoenix.HTML.safe_to_string()
|
||||
|
||||
# heex
|
||||
expected = """
|
||||
|
@ -30,4 +30,10 @@ defmodule TempleTest do
|
|||
assert expected == result
|
||||
end
|
||||
end
|
||||
|
||||
describe "attributes/1" do
|
||||
test "compiles runtime attributes" do
|
||||
assert ~s| disabled class="foo"| == attributes(disabled: true, checked: false, class: "foo")
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
Reference in New Issue