private void PopulateLookupTables() { MethodInfo[] allMethods = ControllerType.GetMethods(BindingFlags.InvokeMethod | BindingFlags.Instance | BindingFlags.Public); MethodInfo[] actionMethods = Array.FindAll(allMethods, IsValidActionMethod); AliasedMethods = Array.FindAll(actionMethods, IsMethodDecoratedWithAliasingAttribute); NonAliasedMethods = actionMethods.Except(AliasedMethods).ToLookup(method => method.Name, StringComparer.OrdinalIgnoreCase); }
public void Register() { List <MethodInfo> ms = ControllerType.GetMethods(BindingFlags.Static | BindingFlags.NonPublic) .Where(x => ControllerRegistrationAttribute.HasAttribute(x)).ToList(); foreach (MethodInfo m in ms) { m.Invoke(null, new object[] { Server }); } }
private List <MethodInfo> GetAllActionMethods() { var allMethods = ControllerType.GetMethods(BindingFlags.InvokeMethod | BindingFlags.Instance | BindingFlags.Public | BindingFlags.DeclaredOnly); var actionMethods = Array.FindAll(allMethods, IsValidActionMethod); var aliasedMethods = Array.FindAll(actionMethods, IsMethodDecoratedWithAliasingAttribute); var nonAliasedMethods = actionMethods.Except(aliasedMethods).ToLookup(method => method.Name, StringComparer.OrdinalIgnoreCase); var allValidMethods = new List <MethodInfo>(); allValidMethods.AddRange(aliasedMethods); allValidMethods.AddRange(nonAliasedMethods.SelectMany(g => g)); return(allValidMethods); }
private void DiscoverRoutes() { var methods = ControllerType.GetMethods(); foreach (var mt in methods) { var routeAttr = mt.GetCustomAttribute <RouteAttribute>(); if (null == routeAttr) { continue; } ApiServiceCall call = new ApiServiceCall(this, mt); Calls.Add(call); } }
private void PopulateLookupTables() { MethodInfo[] allMethods = ControllerType.GetMethods(BindingFlags.InvokeMethod | BindingFlags.Instance | BindingFlags.Public); MethodInfo[] actionMethods = Array.FindAll(allMethods, IsValidActionMethodNoDirectRoute); if (_hasRouteAttributeOnController) { // Short circuit these tables when there's a direct route attribute on the controller, none of these // will be reachable by-name. AliasedMethods = _emptyMethodInfo; NonAliasedMethods = _emptyMethodInfoLookup; } else { AliasedMethods = Array.FindAll(actionMethods, IsMethodDecoratedWithAliasingAttribute); NonAliasedMethods = actionMethods.Except(AliasedMethods).ToLookup(GetCanonicalMethodName, StringComparer.OrdinalIgnoreCase); } DirectRouteMethods = Array.FindAll(allMethods, IsValidActionMethodWithDirectRoute); StandardRouteMethods = actionMethods; }
internal IEnumerable <ActionDescriptor> FindActions(ControllerContext context) { if (ControllerType == null) { yield break; } var actionMethods = ControllerType.GetMethods( BindingFlags.Public | BindingFlags.Instance | BindingFlags.IgnoreCase | BindingFlags.InvokeMethod) .OrderByDescending(x => x.GetParameters().Length) .OrderByDescending(x => x.IsDefined(typeof(HttpMethodAttribute))); if (actionMethods == null && !actionMethods.Any()) { yield break; } foreach (var method in actionMethods) { // Action方法不支持泛型参数 if (method.IsGenericMethod) { continue; } // Action方法返回值约束: // 1. 返回不准为void或为ref引用返回 // 2. IActionResult或其实现类型 // 3. Task<T>,其中T为IActionResult或其实现类型 var result = method.ReturnType; if (result == typeof(void) || result.IsByRef) { continue; } if (!typeof(IActionResult).IsAssignableFrom(result)) { if (!result.IsGenericType) { continue; } if ((result.GetGenericTypeDefinition() != typeof(Task <>) || !typeof(IActionResult).IsAssignableFrom(result.GetGenericArguments()[0]))) { continue; } } var parameters = method.GetParameters(); if (parameters != null || parameters.Any()) { // Action方法中参数不能有ref和out修饰符 if (parameters.FirstOrDefault(x => x.IsOut || x.ParameterType.IsByRef) != null) { continue; } } var actionName = context.RouteEntity.Action; var paramName = context.RouteEntity.DefaultParameter; if (method.IsDefined(typeof(RouteActionAttribute))) { var routeActionAttribute = method.GetCustomAttribute <RouteActionAttribute>(); if (!String.Equals(routeActionAttribute.RouteAction, actionName, StringComparison.OrdinalIgnoreCase)) { continue; } } else if (!String.Equals(method.Name, actionName, StringComparison.OrdinalIgnoreCase)) { continue; } if (!Enum.TryParse <HttpMethod>(context.HttpContext.Request.HttpMethod.ToUpper(), out var routeMethod)) { routeMethod = HttpMethod.GET; } var methods = method.GetCustomAttributes <HttpMethodAttribute>(); if (methods == null || methods.Count() == 0) { if (routeMethod == HttpMethod.GET) { yield return(new ActionDescriptor { Action = method, ActionName = method.Name.ToLower(), Services = Services }); } else { continue; } } if (methods.FirstOrDefault(x => x.HttpMethod == routeMethod) != null) { yield return(new ActionDescriptor { Action = method, ActionName = method.Name.ToLower(), Services = Services }); } } }