2

しばらくの間、この質問に対する答えを見つけようとしていましたが、新しい質問をする価値があると判断しました...

class Transport次のように定義された、ポリモーフィックな複数のモデルがありますclass Transport::Car < Transportclass Transport::Plane < Transport

baseTransportControllerがあり、すべてのタイプにTransport対応するコントローラーがあります (すべてTransport名前空間の下にあります)、Transport::CarControllerつまりTransport::PlaneController.

さまざまなアクションのルーティングを作成する方法を理解したいTransport...

  • Transportサブクラスがいくつあるかは先験的にわかりません(これは、データベース呼び出しを介して初期化子の一部として行われます)。
  • すべてTransportの には、 と を呼び出す 2 つの共有コントローラ アクションが#boardあり#departます。これらのメソッドはTransportController、Transport のタイプに関係なく、同じアクションを実行し、同じビューを表示するため、内部に存在する必要があります。
  • 異なるTransportタイプは、独自のアクションの異なる実装を持つことができます。たとえば#choose_seat、車と飛行機は異なる制約と異なるビューで異なりますが、アクションは同じです。
  • さまざまTransportなタイプが独自のアクションを持つ資格があります。たとえば、 にはアクションTransport::PlaneControllerが必要ですが、#landing_gear_upこれは には意味がありませんTransport::CarController

私が好きかもしれないのは、次のようなルーティングファイルです:

# for an action landing_gear_up only inside plane
match '/transport/plane/landing_gear_up',
      :controller => "Transport::PlaneController",
      :action => "landing_gear_up"

# for an action on every transport type that are handled differently
match '/transport/:type/choose_seat',
      :controller => "Transport::<type>Controller",
      :action => "choose_seat"

# for the actions that are handled commonly across every type of transport
match '/transport/:type/board', :to => "transport#board"
match '/transport/:type/depart', :to => "transport#depart"

これは「動的セグメント」で可能であるべきだと思いますが、うまく機能させることができません。助言がありますか?

4

2 に答える 2

1

メソッドと変数を定義しroutes.rbて、コードをより DRY にすることができます。私がそれをやろうとする方法の例:

Your::Application.routes.draw do
  ## other routes

  ## helper method to define transport route
  def route_transport action, types
    match "/transport/:type/#{action}", :to => "transport##{action}" and return if types == :common
    [types].flatten.each { |t| match "/transport/#{t}/#{action}", :controller => "Transport::#{t}Controller", :action => action }
  end

  {
    :board => :common,
    :depart => :common,
    :landing_gear_up => :plane,
    :choose_seat => [:car, :plane],
    # action name => :common or transport type(s)
  }.each { |action, types| route_transport action, types }

  ## other routes
end

コードを確認していません。エラーが含まれている可能性があります。実行rake routesして、正しいルートが生成されているかどうかを確認します。

また、RESTful ルートも検討してください。長期的には、 RESTful ルートを使用すると作業が楽になる可能性があります。

于 2012-06-07T11:44:32.173 に答える
0

コントローラーに同じ継承階層がある場合、特別なことをする必要はありません。リソースを宣言し、各コントローラーの非 RESTful ルートを宣言するだけで完了です。PlaneController#board は自動的に TransportController#board を呼び出します。また、PlaneController に固有のアクションは、そのコントローラーに固有のままです。

于 2012-06-08T01:37:32.957 に答える