Looking at the code it seems like that’s not something you can do. A macro transforms AST at compile time, and you’re trying to gate it on something that exists only at runtime.
How exactly you have to use variables in a macro depends on the Macro. You already see it in ecto where the names are used to build the query, except when you pin (^), then you use the variables value in the query.
Though, passing in the operator like that is not possible. I think you’ll have to limit yourt choices to a handfull of operators and branch on them, eg:
case op do
:">=" -> Ecto.Query.where(query, [..., r], field(r, ^field) >= ^value)
:"<" -> Ecto.Query.where(query, [..., r], field(r, ^field) < ^value)
end