Маршрут, который я здесь выбрал, - это отражение и словарь, содержащий все действительные действия в соответствующем контроллере, который хранится в приложении []. Действительное действие определяется путем проверки метода ReturnType и проверки того, что он является (или является производным от) ActionResult и не является частным. Я мог бы сделать еще несколько проверок, но пока их достаточно.
public static bool MethodIsAction(MethodInfo method)
{
if (method == null)
throw new ArgumentNullException("Invalid Parameter: method cannot be null.");
if (method.ReturnType != typeof(ActionResult) && method.ReturnType.BaseType != typeof(ActionResult))
return false;
if (method.IsPrivate)
return false;
return true;
}
Словарь действий построен с помощью следующего метода внутри Application_Start:
public static Dictionary<string, MethodInfo> GetActionDictionary(Type controller)
{
Dictionary<string, MethodInfo> dict = null;
var methods = controller.GetMethods().Where(MethodIsAction);
if (methods.Any())
{
dict = new Dictionary<string, MethodInfo>(StringComparer.OrdinalIgnoreCase);
foreach (var action in methods)
dict.Add(action.Name, action);
}
return dict;
}
Когда пользователь запрашивает квалифицирующее действие, я просто указываю имя действия в Словаре, и если для этого имени действия существует MethodInfo, я вызываю его. Хотя он все еще требует отражения, он по крайней мере оптимизирован, так что это происходит только один раз во время работы приложения.