Size: a a a

2021 June 16

LL

Lama Lover in pro.elixir
Макросы 101

1. Код представлен в виде AST. То есть AST для x + 1 это {:+, [], [{:x, [], Elixir}, 1]}

2. То что  между quote do и end — возвращается как AST. То есть iex> quote(do: 1 + 2) вернёт {:+, [], [1, 2]}

3. То что внутри unquote — вставляется в AST по значению
То есть
iex> x = 1
iex> quote(do: unquote(x) + 2)
{:+, [], [1, 2]}

4. defmacro my_macro(input_ast), где my_macro это фукнция, которая принимает AST (input_ast) и возвращает AST, которое будет вставлено в код.

Конец
источник

LL

Lama Lover in pro.elixir
Лучше мне расскажите почему у меня не компилируется yaml_elixir

Компиляция падает на
==> yaml_elixir
Compiling 6 files (.ex)
Generated yaml_elixir app
===> Fetching pc v1.12.0
===> Analyzing applications...
===> Compiling pc
===> Compiling c_src/crc32c.c
===> Compiling c_src/crc32c_nif.c
===> Linking /home/user/project/deps/crc32cer/priv/crc32cer_nif.so
** (Mix) Could not compile dependency :crc32cer, "/home/user/.mix/rebar3 bare compile --paths="/home/user/project/_build/dev/lib/*/ebin"" command failed. You can recompile this dependency with "mix deps.compile crc32cer", update it with "mix deps.update crc32cer" or clean it with "mix deps.clean crc32cer"

Если вызвать
/home/user/.mix/rebar3 bare compile --paths="/home/user/project/_build/dev/lib/*/ebin"
===> Compilation failed: there is no code in this directory (/home/user/project), it is unreadable or for some other reason is not a recognizable application structure.

rebar 3.15.2, erlang 23.4, elixir 1.11
источник

ММ

Максим Мартынов... in pro.elixir
а mix deps.compile crc32cer пробовал?
источник

LL

Lama Lover in pro.elixir
Пробовал, то же самое
источник

ММ

Максим Мартынов... in pro.elixir
а какой он версии
источник

ММ

Максим Мартынов... in pro.elixir
гуглится вот это https://github.com/dantswain/kayrock/issues/6
источник

A ß in pro.elixir
а нифка собралась?
источник

LL

Lama Lover in pro.elixir
А хрен его знает. .so файлика нет
источник

A ß in pro.elixir
версия с erl_interface правдоподобна
источник

A ß in pro.elixir
скорее всего на линковке падает из-за -lerl_interface
источник

ММ

Максим Мартынов... in pro.elixir
DEBUG=1 mix deps.compile crc32cer
источник

LL

Lama Lover in pro.elixir
===> sh(gcc c_src/crc32c.o c_src/crc32c_nif.o $LDFLAGS $LDLIBS -shared  -L"/nix/store/fyxryax4nf2d1a7v9piydncnx8jhnaks-erlang-23.3.4.1/lib/erlang/lib/erl_interface-4.0.3.1/lib" -lei -o /home/user/project/deps/crc32cer/priv/crc32cer_nif.so)
failed with return code 1 and the following output:
impure path `/home/user/project/deps/crc32cer/priv/crc32cer_nif.so' used in link
collect2: error: ld returned 1 exit status
источник

LL

Lama Lover in pro.elixir
А какие ещё есть волшебные переменные?
источник

ММ

Максим Мартынов... in pro.elixir
он похоже орет на symlink
источник

LL

Lama Lover in pro.elixir
Хым, посмотрим
источник

LL

Lama Lover in pro.elixir
А, это мой дистрибутив на это ругается, ложная тревога
источник

DS

Dmitry Shpagin in pro.elixir
Когда-то давно, когда разбирался в макросах - пару статей с примерами наваял, пытался по-простому разложить, надеюсь поможет разобраться
https://sofakingcode.medium.com/e1cb313979c8
источник

B

Bogdan in pro.elixir
Спасибо всем) теперь точно разберусь!
источник

LL

Lama Lover in pro.elixir
Хорошая статья

Только вот в следующей статье плохой пример с use для роутеров. Роутер это плаг, поэтому можно просто в одном роуетере передавать запрос в другой роутер
источник

V

V in pro.elixir
макросы - это код, "пишушие" другой код.
допустим ты хочешь наплодить функций вида
def greet_vasya, do: "Hello, vasya!"
def greet_lena, do: "Hello, lena!"
...

Ты пишешь функцию
def generate_greet(name) do
   "def greet_#{name}, do: \"Hello, #{name}!\""
end
и можешь использовать её в генерации кода
File.write("greets.ex", "defmodule Greets do")
File.write("greets.ex", generate_greet("vasya"), :append)
File.write("greets.ex", generate_greet("lena"), :append)
File.write("greets.ex", "end", :append)

Обрати внимание, что в "def greet_#{name}, do: \"Hello, #{name}!\"" есть цитируемые и подставляемые части.
цитируемые - это def greet_, , do:\"Hello, , !\"
подставляемые - это два раза #{name}

Макрос делает по сути то же самое, только а) сразу в AST, б) цитируемые части вместо кавычек обрамляются quote do ... end, а подставляемые - unquote(...)

defmacro generate_greet(name) do
   fun_name = "greet_#{name}"
   greet_string = "Hello, #{name}!"
   quote do
       def unquote(fun_name), do: unquote(greet_string)
   end
end
источник