private static string GetRoutePrefix(ControllerDescriptor controllerDescriptor) { // this only happens once per controller type, for the lifetime of the application, // so we do not need to cache the results object[] attributes = controllerDescriptor.GetCustomAttributes(typeof(RoutePrefixAttribute), inherit: false); if (attributes.Length > 0) { RoutePrefixAttribute attribute = attributes[0] as RoutePrefixAttribute; if (attribute != null) { string prefix = attribute.Prefix; if (prefix != null) { if (prefix.StartsWith("/", StringComparison.Ordinal) || prefix.EndsWith("/", StringComparison.Ordinal)) { string errorMessage = Error.Format( MvcResources.RoutePrefix_CannotStartOrEnd_WithForwardSlash, prefix, controllerDescriptor.ControllerName); throw new InvalidOperationException(errorMessage); } return(prefix); } } } return(null); }
protected void ValidateRoutePrefix(LocalizationCollectionRoute localizationCollectionRoute) { TActionDescriptor actionDescriptor = ((TActionDescriptor[])localizationCollectionRoute.DataTokens[RouteDataTokenKeys.Actions]).First(); Type controllerType = actionDescriptor.ControllerDescriptor.ControllerType; RoutePrefixAttribute routePrefixAttribute = controllerType.GetCustomAttributes(true).OfType <RoutePrefixAttribute>().SingleOrDefault(); if (routePrefixAttribute == null) { if (!string.IsNullOrEmpty(RoutePrefix) && Configuration.ValidateRoutePrefix) { throw new InvalidOperationException( string.Format( "RoutePrefix is set but Controller '{0}' does not contain any RoutePrefix attributes." + "Set Configuration.ValidateRoutePrefix to false, if you want to skip validation.", controllerType.FullName)); } } else if (string.IsNullOrEmpty(RoutePrefix) && Configuration.UseUntranslatedAttributePrefixes) { // Use untranslated prefix from attribute RoutePrefix = routePrefixAttribute.Prefix; } }
// manually arrange aspnet web api dummies and mocks private ResourceLinkFactory GenerateFullSut(ResourceLinkFactoryTestData data) { var config = new Mock <HttpConfiguration>().Object; var prefix = new RoutePrefixAttribute(data.Prefix); var controllerDescriptor = new TestControllerDescriptor(config, data.ControllerName, typeof(ApiController), prefix); var actionParameters = data.RouteValues.Keys.Aggregate(new Collection <HttpParameterDescriptor>(), (collection, parameterName) => { var mockParameterDescriptor = new Mock <HttpParameterDescriptor>(); mockParameterDescriptor.Setup(x => x.ParameterName).Returns(parameterName); collection.Add(mockParameterDescriptor.Object); return(collection); }); var methodInfo = new TestMethodInfo(new RouteAttribute(data.Template) { Name = data.RouteName }); var actionDescriptor = new TestActionDescriptor(controllerDescriptor, methodInfo, actionParameters); actionDescriptor.SupportedHttpMethods.Add(new HttpMethod(data.Method)); // httpContext var request = new HttpRequest("", data.BaseUrl, ""); var response = new HttpResponse(new StringWriter()); HttpContext.Current = new HttpContext(request, response); return(new ResourceLinkFactory(new[] { actionDescriptor })); }
private static string GetRoutePrefix(HttpControllerDescriptor controller) { Collection <RoutePrefixAttribute> attributes = controller.GetCustomAttributes <RoutePrefixAttribute>(inherit: false); if (attributes.Count > 0) { RoutePrefixAttribute attribute = attributes[0]; if (attribute != null) { string prefix = attribute.Prefix; if (prefix != null) { if (prefix.EndsWith("/", StringComparison.Ordinal)) { throw Error.InvalidOperation(SRResources.AttributeRoutes_InvalidPrefix, prefix, controller.ControllerName); } return(prefix); } } } return(null); }
private static void ValidatePrefixTemplate(RoutePrefixAttribute prefixAttribute, ControllerDescriptor controllerDescriptor) { if (prefixAttribute != null && !IsValidTemplate(prefixAttribute.Prefix)) { string errorMessage = Error.Format(MvcResources.RoutePrefix_CannotStartOrEnd_WithForwardSlash, prefixAttribute.Prefix, controllerDescriptor.ControllerName); throw new InvalidOperationException(errorMessage); } }
internal List <RouteEntry> MapMvcAttributeRoutes(ReflectedAsyncControllerDescriptor controllerDescriptor) { RoutePrefixAttribute prefixAttribute = GetPrefixFrom(controllerDescriptor); ValidatePrefixTemplate(prefixAttribute, controllerDescriptor); RouteAreaAttribute area = GetAreaFrom(controllerDescriptor); string areaName = GetAreaName(controllerDescriptor, area); string areaPrefix = area != null ? area.AreaPrefix ?? area.AreaName : null; ValidateAreaPrefixTemplate(areaPrefix, areaName, controllerDescriptor); string controllerName = controllerDescriptor.ControllerName; AsyncActionMethodSelector actionSelector = controllerDescriptor.Selector; IEnumerable <MethodInfo> actionMethodsInfo = actionSelector.AliasedMethods .Concat(actionSelector.NonAliasedMethods.SelectMany(x => x)) .Where(m => m.DeclaringType == controllerDescriptor.ControllerType); if (actionSelector.AllowLegacyAsyncActions) { // if the ActionAsync / ActionCompleted pattern is used, we need to remove the "Completed" methods // and not look up routing attributes on them actionMethodsInfo = actionMethodsInfo.Where(m => !m.Name.EndsWith("Completed", StringComparison.OrdinalIgnoreCase)); } List <RouteEntry> routeEntries = new List <RouteEntry>(); foreach (var method in actionMethodsInfo) { string actionName = GetCanonicalActionName(method, actionSelector.AllowLegacyAsyncActions); IEnumerable <IDirectRouteInfoProvider> routeAttributes = GetRouteAttributes(method); foreach (var routeAttribute in routeAttributes) { ValidateTemplate(routeAttribute, actionName, controllerDescriptor); string prefix = prefixAttribute != null ? prefixAttribute.Prefix : null; string template = CombinePrefixAndAreaWithTemplate(areaPrefix, prefix, routeAttribute.RouteTemplate); Route route = _routeBuilder.BuildDirectRoute(template, routeAttribute.Verbs, controllerName, actionName, method, areaName); RouteEntry entry = new RouteEntry { Name = routeAttribute.RouteName ?? template, Route = route, RouteTemplate = template, ParsedRoute = RouteParser.Parse(route.Url), Order = routeAttribute.RouteOrder }; routeEntries.Add(entry); } } return(routeEntries); }
public static string GetBaseUri(Type handler) { RoutePrefixAttribute routePrefix = (RoutePrefixAttribute)handler.GetCustomAttributes(typeof(RoutePrefixAttribute), true).FirstOrDefault(); if (routePrefix == null) { throw new InvalidOperationException("Handler should have RoutePrefix attribute in their class declaration"); } return(routePrefix.Prefix); }
private string GetRoutePrefix(HttpControllerDescriptor controller) { RoutePrefixAttribute routePrefix = controller.ControllerType.GetCustomAttributes(typeof(RoutePrefixAttribute), false).FirstOrDefault() as RoutePrefixAttribute; if (routePrefix != null) { return(routePrefix.Prefix); } return(""); }
private static string GetRoutePrefixUrl(RoutePrefixAttribute routePrefixAttribute, Type controllerType) { if (routePrefixAttribute == null) { return(null); } // If we're given route prefix url, use it. // Otherwise, use the controller name as a convention. return(routePrefixAttribute.Url ?? controllerType.GetControllerName()); }
private string GetUrl() { var serverUri = ConfigurationManager.AppSettings["WEBAPI_URI"]; if (string.IsNullOrEmpty(serverUri)) { throw new Exception("WEBAPI_URI is not empty please set it in app.config"); } RoutePrefixAttribute attr = (RoutePrefixAttribute)Attribute.GetCustomAttribute(typeof(TController), typeof(RoutePrefixAttribute)); return(string.Format("{0}{1}", serverUri, attr.Prefix)); }
private static string GetRoutePrefix(RoutePrefixAttribute routePrefixAttribute, MethodInfo actionMethod, RouteConventionAttribute convention) { // Return an explicitly defined route prefix, if defined if (routePrefixAttribute != null) { return(routePrefixAttribute.Url); } // Otherwise, if this is a convention-based controller, get the convention-based prefix if (convention != null) { return(convention.GetDefaultRoutePrefix(actionMethod)); } return(null); }
/// <summary> /// Returns a route prefix which is parsed from the specified MethodInfo. /// </summary> /// <param name="controllerMethodInfo"></param> /// <returns></returns> internal string GetRoutePrefix(MethodInfo controllerMethodInfo) { string prefix = string.Empty; Type controllerType = controllerMethodInfo.ReflectedType; RoutePrefixAttribute routePrefixAttribute = (RoutePrefixAttribute)Attribute.GetCustomAttribute(controllerType, typeof(RoutePrefixAttribute)); if (routePrefixAttribute != null) { prefix = $"/{routePrefixAttribute.RoutePrefix}"; } return(prefix); }
private static string GetPrefixFrom(ReflectedAsyncControllerDescriptor controllerDescriptor) { // this only happens once per controller type, for the lifetime of the application, // so we do not need to cache the results object[] routePrefixAttributes = controllerDescriptor.GetCustomAttributes(typeof(RoutePrefixAttribute), inherit: false); if (routePrefixAttributes.Length > 0) { RoutePrefixAttribute routePrefixAttribute = routePrefixAttributes[0] as RoutePrefixAttribute; if (routePrefixAttribute != null) { return(routePrefixAttribute.Prefix); } } return(null); }
private void MockHttpContextAndActionDescriptors(HateoasTestData mockData) { var config = new Mock <HttpConfiguration>().Object; var prefix = new RoutePrefixAttribute(mockData.Prefix); var controllerDescriptor = new TestControllerDescriptor(config, mockData.ControllerName, typeof(ApiController), prefix); var actionParameters = mockData.RouteValues.Keys.Aggregate(new Collection <HttpParameterDescriptor>(), (collection, parameterName) => { var mockParameterDescriptor = new Mock <HttpParameterDescriptor>(); mockParameterDescriptor.Setup(x => x.ParameterName).Returns(parameterName); collection.Add(mockParameterDescriptor.Object); return(collection); }); var methodInfo = new TestMethodInfo(new RouteAttribute(mockData.Template) { Name = mockData.RouteName }); var actionDescriptor = new TestActionDescriptor(controllerDescriptor, methodInfo, actionParameters); actionDescriptor.SupportedHttpMethods.Add(new HttpMethod(mockData.Method)); var dataTokens = new RouteValueDictionary { { "descriptors", new[] { actionDescriptor } } }; RouteTable.Routes.Add(new Route(mockData.RoutePath, null) { DataTokens = dataTokens }); var request = new HttpRequest("", mockData.BaseUrl, ""); var response = new HttpResponse(new StringWriter()); HttpContext.Current = new HttpContext(request, response); }
public object Execute(MethodInfo targetMethod, object[] args) { var actionContext = new ActionContext(); actionContext.HttpClientSettings = _config.HttpClientSettings; actionContext.MethodDescription = this.GetMethodDescription(targetMethod); _routePrefixAttribute = targetMethod.DeclaringType.GetCustomAttribute <RoutePrefixAttribute>(); var uriBuilder = new UriBuilder(Utility.CombinePaths(_config.Host , _routePrefixAttribute != null ? (_routePrefixAttribute.Prefix + "/") : "" , actionContext.MethodDescription.Route)); actionContext.HttpRequestMessageBuilder = new HttpRequestMessageBuilder(actionContext.MethodDescription.HttpMethod, uriBuilder, _config.HttpClientSettings); actionContext.HttpRequestMessageBuilder.MultiPartAttribute = actionContext.MethodDescription.MultiPartAttribute; if (args.Count() > 0) { var pEnumerator = actionContext.MethodDescription.Parameters.OrderBy(p => p.Order).ToList().GetEnumerator(); foreach (var arg in args) { pEnumerator.MoveNext(); var p = pEnumerator.Current; foreach (var a in p.ScopeAttributes) { a.ProcessParameter(actionContext.HttpRequestMessageBuilder, p.ParameterInfo, arg); } } } var httpResultTaskFunc = HttpRequestTaskFunc(actionContext, 0, () => { return(actionContext.MethodDescription.HttpResultConverter( EasyHttpClient.Utilities.TaskExtensions.Retry <HttpResponseMessage>(() => { actionContext.HttpRequestMessage = actionContext.HttpRequestMessageBuilder.Build(); Task <HttpResponseMessage> httpRequestTask; if (actionContext.MethodDescription.AuthorizeRequired && _config.HttpClientSettings.OAuth2ClientHandler != null) { httpRequestTask = _config.HttpClientSettings.OAuth2ClientHandler.SetAccessToken(actionContext.HttpRequestMessage) .Then(() => DoSendHttpRequestAsync(_httpClient, actionContext)) .Then(async response => { if (_config.HttpClientSettings.OAuth2ClientHandler.IsUnauthorized(response)) { actionContext.HttpRequestMessage = actionContext.HttpRequestMessageBuilder.Build(); if (await _config.HttpClientSettings.OAuth2ClientHandler.RefreshAccessToken(actionContext.HttpRequestMessage)) { response = await DoSendHttpRequestAsync(_httpClient, actionContext).ConfigureAwait(false); } } return response; }); } else { httpRequestTask = DoSendHttpRequestAsync(_httpClient, actionContext); } return httpRequestTask; }, (r) => Task.FromResult((int)r.StatusCode > 500 || r.StatusCode == HttpStatusCode.RequestTimeout), actionContext.MethodDescription.MaxRetry) , actionContext)); }); return(actionContext.MethodDescription.MethodResultConveter(httpResultTaskFunc)); }
public static Dictionary <string, Dictionary <string, HttpActionDescriptor> > LoadRoutes ( HttpConfiguration httpConfiguration ) { var assembliesResolver = httpConfiguration .Services .GetAssembliesResolver(); var httpControllerTypeResolver = httpConfiguration .Services .GetHttpControllerTypeResolver(); var controllersTypes = httpControllerTypeResolver .GetControllerTypes(assembliesResolver); var httpControllerSelector = httpConfiguration .Services .GetHttpControllerSelector(); var controllerMapping = httpControllerSelector .GetControllerMapping(); Dictionary <string, Dictionary <string, HttpActionDescriptor> > result = null; if (controllerMapping != null) { var actions = controllerMapping .Values .SelectMany ( (x) => { var httpActionSelector = x .Configuration .Services .GetActionSelector(); var actionsByName = httpActionSelector .GetActionMapping(x); return (actionsByName .SelectMany ( (xx) => { return xx; } )); } ); RoutePrefixAttribute routePrefixAttribute = null; RouteAttribute routeAttribute = null; SemanticVersionedAttribute semanticVersionedAttribute = null; result = actions .Where ( (x) => { #region RoutePrefix + Route + Version 筛选 var r = false; routePrefixAttribute = x .ControllerDescriptor .GetCustomAttributes <RoutePrefixAttribute>() .FirstOrDefault() as RoutePrefixAttribute; if (routePrefixAttribute != null) { routeAttribute = x .GetCustomAttributes <RouteAttribute>() .FirstOrDefault() as RouteAttribute; if (routeAttribute != null) { semanticVersionedAttribute = x .GetCustomAttributes <SemanticVersionedAttribute>() .FirstOrDefault() as SemanticVersionedAttribute; if (semanticVersionedAttribute != null) { r = true; } } } return(r); #endregion } ) .ToLookup ( (x) => { var key = string .Format ( "{1}{0}{2}" , "/" , routePrefixAttribute.Prefix , routeAttribute.Template ); return(key); } ) .ToDictionary ( (x) => { return(x.Key); } , (x) => { return (x .ToDictionary ( (xx) => { var attribute = xx .GetCustomAttributes <SemanticVersionedAttribute>() .FirstOrDefault() as SemanticVersionedAttribute; return attribute .Version .ToNormalizedString(); } )); } ); } return(result); }
public TestControllerDescriptor(HttpConfiguration configuration, string controllerName, Type controllerType, RoutePrefixAttribute prefix) : base(configuration, controllerName, controllerType) { RoutePrefix = prefix; }
/// <summary> /// Gets a controller's route prefix URL. /// </summary> /// <param name="routePrefixAttribute">The <see cref="RoutePrefixAttribute"/> for the controller.</param> /// <param name="actionMethod">The <see cref="MethodInfo"/> for an action.</param> /// <param name="convention">The <see cref="RouteConventionAttributeBase"/> for the controller.</param> /// <returns>The route prefix URL to apply against the action.</returns> private static string GetRoutePrefix(RoutePrefixAttribute routePrefixAttribute, MethodInfo actionMethod, RouteConventionAttributeBase convention) { // Return an explicitly defined route prefix, if defined if (routePrefixAttribute != null) return routePrefixAttribute.Url; // Otherwise, if this is a convention-based controller, get the convention-based prefix if (convention != null) return convention.GetDefaultRoutePrefix(actionMethod); return null; }
private static string GetRoutePrefixUrl(RoutePrefixAttribute routePrefixAttribute, Type controllerType) { if (routePrefixAttribute == null) { return null; } // If we're given route prefix url, use it. // Otherwise, use the controller name as a convention. return routePrefixAttribute.Url ?? controllerType.GetControllerName(); }
/// <summary> /// Builds a <see cref="RouteSpecification"/> from component parts. /// </summary> /// <param name="controllerIndex">The index of this controller inthe registered controller types.</param> /// <param name="controllerType">The controller type.</param> /// <param name="actionMethod">The action method info.</param> /// <param name="routeAreaAttribute">An applicable <see cref="RouteAreaAttribute"/> for the controller.</param> /// <param name="routePrefixAttribute">An applicable <see cref="RoutePrefixAttribute"/> for the controller.</param> /// <param name="routeAttribute">The <see cref="IRouteAttribute"/> for the action.</param> /// <returns>The route specification.</returns> private RouteSpecification BuildRouteSpecification(int controllerIndex, Type controllerType, MethodInfo actionMethod, RouteAreaAttribute routeAreaAttribute, RoutePrefixAttribute routePrefixAttribute, IRouteAttribute routeAttribute, RouteVersionedAttribute routeVersionedAttribute) { var isAsyncController = controllerType.IsAsyncController(); var subdomain = GetAreaSubdomain(routeAreaAttribute); var actionName = GetActionName(actionMethod, isAsyncController); return new RouteSpecification { ActionMethod = actionMethod, ActionName = actionName, ActionPrecedence = GetSortableOrder(routeAttribute.ActionPrecedence), AppendTrailingSlash = routeAttribute.AppendTrailingSlashFlag, AreaName = GetAreaName(routeAreaAttribute, controllerType), AreaUrl = GetAreaUrl(routeAreaAttribute, subdomain, controllerType), AreaUrlTranslationKey = routeAreaAttribute.SafeGet(a => a.TranslationKey), ControllerIndex = controllerIndex, ControllerName = controllerType.GetControllerName(), ControllerPrecedence = GetSortableOrder(routeAttribute.ControllerPrecedence), ControllerType = controllerType, HttpMethods = routeAttribute.HttpMethods, IgnoreAreaUrl = routeAttribute.IgnoreAreaUrl, IgnoreRoutePrefix = routeAttribute.IgnoreRoutePrefix, IsAbsoluteUrl = routeAttribute.IsAbsoluteUrl, PrefixPrecedence = GetSortableOrder(routePrefixAttribute.SafeGet(a => a.Precedence, int.MaxValue)), PreserveCaseForUrlParameters = routeAttribute.PreserveCaseForUrlParametersFlag, RouteName = routeAttribute.RouteName, RoutePrefixUrl = GetRoutePrefixUrl(routePrefixAttribute, controllerType), RoutePrefixUrlTranslationKey = routePrefixAttribute.SafeGet(a => a.TranslationKey), RouteUrl = routeAttribute.RouteUrl ?? actionName, RouteUrlTranslationKey = routeAttribute.TranslationKey, SitePrecedence = GetSortableOrder(routeAttribute.SitePrecedence), Subdomain = subdomain, UseLowercaseRoute = routeAttribute.UseLowercaseRouteFlag, IsVersioned = routeVersionedAttribute != null && routeVersionedAttribute.IsVersioned, MinVersion = routeAttribute.MinVersion ?? (routeVersionedAttribute != null ? routeVersionedAttribute.MinVersion : null), MaxVersion = routeAttribute.MaxVersion ?? (routeVersionedAttribute != null ? routeVersionedAttribute.MaxVersion : null) }; }
private static void ValidatePrefixTemplate(RoutePrefixAttribute prefixAttribute, ControllerDescriptor controllerDescriptor) { if (prefixAttribute != null && !IsValidTemplate(prefixAttribute.Prefix)) { string errorMessage = Error.Format(MvcResources.RoutePrefix_CannotStartOrEnd_WithForwardSlash, prefixAttribute.Prefix, controllerDescriptor.ControllerName); throw new InvalidOperationException(errorMessage); } }