2017-10-19 82 views
1

我想幹涸此控制器:before_action:設置相當於在鳳凰城

defmodule Xyz.ExampleController do 
    use Xyz, :controller 

    alias XyZ.Shops 

    def a(conn, %{"id" => id}) do 
    product = Shops.get_product!(id) 
    tax = product.price * 0.15 

    ... 

    render(conn, "a.html", foobar: foobar, product: product) 
    end 

    def b(conn, %{"id" => id}) do 
    product = Shops.get_product!(id) 
    tax = product.price * 0.15 

    ... 

    render(conn, "b.html", foobar: foobar, tax: tax) 
    end 

    def c(conn, %{"id" => id}) do 
    product = Shops.get_product!(id) 
    tax = product.price * 0.15 

    ... 

    render(conn, "c.html", foobar: foobar) 
    end 

end 

每個函數這個部分開始:

product = Shops.get_product!(id) 
    tax = product.price * 0.15 

在Ruby on Rails的世界,我想把它調用before_action :setup來調用控制器。

在鳳凰城實現這一目標的最佳方法是什麼?

+3

你可以使用一個插件 - > https://hexdocs.pm/phoenix/plug.html,我求求你,不要把商業邏輯放到框架模塊中。 – JustMichael

+2

該邏輯不應位於控制器IMO中。如果是我,我會定義一個像這樣工作的函數:'{product,tax} = Shops.get_product_and_tax!(id)'並且從每個動作調用它。 – Dogbert

+0

比我會那樣做。我認爲將它放在一個插頭中會更清潔。但我很高興在每個操作中保留一行代碼。 – wintermeyer

回答

1

您可以嘗試使用action/2控制器方法。從controller docs

由於控制器是插頭,它們同時實現初始化/ 1和呼叫/ 2, 還提供/ 2命名作用的功能,該功能負責 調度插頭堆疊之後的適當的動作(也可以覆蓋 )。

在書中Programming Phoenix克里斯·麥科德使用這個動作把一個通用參數所有控制器的功能是這樣的:

def​ action(conn, _) ​do​ 
​ apply(__MODULE__, action_name(conn), [conn, conn.params, conn.assigns.current_user]) 
​end​ 

所以像index/2的每一個動作,現在是index/3並具有當前用戶爲第三參數。

也許這可以幫助你?

+1

我不認爲使用這種方法比插頭更好,它不夠靈活,並且在這種情況下不會給插件帶來任何優勢。 – JustMichael