2016-09-25 1 views
0

Ecto documentationには補間値の計算方法が示されています。しかし、私はクエリに動的なフィールドが必要です。私は数十のフィールドを持っていて、それらのそれぞれに対してクエリを書くことは密着していないようです。自動翻訳Ectoの内挿フィールドはどのようにしてクエリしますか?

** (Ecto.QueryError) web/controllers/search.ex:8: field `Hedone.User.campo` in `where` does not exist in the schema in query: 

from u in Hedone.User, 
    where: u.campo > ^18 and u.campo < ^40, 
    select: u.name 

defmodule Hedone.SearchController do 
    use Hedone.Web, :controller 

    alias Hedone.User 

    def idade(conn, %{"idade+" => maior, "idade-" => menor, "campo" => campo}) do 
    IO.inspect campo 
    query = from u in User, where: u.campo > ^maior and u.campo < ^menor, select: u.name 
    pesquisa = Repo.all query 
    IO.inspect pesquisa 
    text conn, "Works" 
end 

end 

このコントローラは、次のエラーが発生します。

答えて

2

campoには、使用したいフィールドの名前の文字列が含まれているものとします。 "age"。あなたは、このためのクエリでfieldを使用することができます。

def idade(conn, %{"idade+" => maior, "idade-" => menor, "campo" => campo}) do 
    campo = String.to_existing_atom(campo) 
    query = from u in User, where: field(u, ^campo) > ^maior and field(u, ^campo) < ^menor, select: u.name 
    pesquisa = Repo.all query 
    IO.inspect pesquisa 
    text conn, "Works" 
end 

fieldフィールドは原子であることを期待ので、私は無事原子に文字列を変換するためにString.to_existing_atomを使用しました。モデルのスキーマにフィールドを定義しておく必要があるため、String.to_existing_atomは有効なフィールド名では失敗しません。

+0

ダイナミックfields_の_dozensのために私はむしろマクロとなるだろう。 – mudasobwa

+0

申し訳ありませんが、私はプログラムに着手しており、私のアイデアをオンラインにすることを楽しみにしています。私はマクロセッションを読んでいない。なぜそれが良いのでしょうか?それはとてもうまくいく。 –

+0

@mudasobwaここでどのようにマクロを使用しますか?少し拡大できますか?私はここでそれをする理由は考えられませんが、多分私は何かを逃しています。 – Dogbert

1

問題の別のアプローチの例として、これを投稿しています。

defmacro idade(conn, formula, campo: binding) do 
    q = formula |> String.replace "campo", binding 
    quote do 
    from u in User, where: unquote(q), select: u.name 
     |> Repo.all 
    text conn, "Works" 
    end 
end 

をして好きなことを呼び出します:一つは、マクロはコンパイル時に解決されているので、この変換を処理するためのマクロを使用する場合があります

idade(nil, "u.campo > ^maior and u.campo < ^menor", campo: "age") 
関連する問題