絶対!DefaultControllerFactory
カスタムコントローラーが存在しない場合は、をオーバーライドしてカスタムコントローラーを見つける必要があります。IActionInvoker
次に、動的アクション名を処理するためのを作成する必要があります。
コントローラファクトリは次のようになります。
public class DynamicControllerFactory : DefaultControllerFactory
{
private readonly IServiceLocator _Locator;
public DynamicControllerFactory(IServiceLocator locator)
{
_Locator = locator;
}
protected override Type GetControllerType(string controllerName)
{
var controllerType = base.GetControllerType(controllerName);
// if a controller wasn't found with a matching name, return our dynamic controller
return controllerType ?? typeof (DynamicController);
}
protected override IController GetControllerInstance(Type controllerType)
{
var controller = base.GetControllerInstance(controllerType) as Controller;
var actionInvoker = _Locator.GetInstance<IActionInvoker>();
if (actionInvoker != null)
{
controller.ActionInvoker = actionInvoker;
}
return controller;
}
}
次に、アクションの呼び出し元は次のようになります。
public class DynamicActionInvoker : ControllerActionInvoker
{
private readonly IServiceLocator _Locator;
public DynamicActionInvoker(IServiceLocator locator)
{
_Locator = locator;
}
protected override ActionDescriptor FindAction(ControllerContext controllerContext,
ControllerDescriptor controllerDescriptor, string actionName)
{
// try to match an existing action name first
var action = base.FindAction(controllerContext, controllerDescriptor, actionName);
if (action != null)
{
return action;
}
// @ray247 The remainder of this you'd probably write on your own...
var actionFinders = _Locator.GetAllInstances<IFindAction>();
if (actionFinders == null)
{
return null;
}
return actionFinders
.Select(f => f.FindAction(controllerContext, controllerDescriptor, actionName))
.Where(d => d != null)
.FirstOrDefault();
}
}
このコードの多くはここで見ることができます。これは、完全に動的なMVCパイプラインを作成するための私と同僚による古い最初のドラフトの試みです。あなたはそれを参照として自由に使用し、あなたが望むものをコピーすることができます。
編集
私は、そのコードが何をするかについての背景を含めるべきだと考えました。ドメインモデルを中心にMVCレイヤーを動的に構築しようとしていました。したがって、ドメインにProductクラスが含まれている場合は、に移動しproducts\alls
てすべての製品のリストを表示できます。製品を追加する場合は、に移動しproduct\add
ます。product\edit\1
あなたは製品を編集するために行くことができます。エンティティのプロパティを編集できるようにするなどの方法も試しました。したがってproduct\editprice\1?value=42
、製品#1の価格プロパティを42に設定します(私のパスは少しずれている可能性があり、正確な構文はもう思い出せません)。これがお役に立てば幸いです。