public class newDomainRoute : Route
{
private Regex domainRegex;
private Regex pathRegex;
public string Domain { get; set; }
public newDomainRoute(string domain, string url, RouteValueDictionary defaults) : base(url, defaults, new MvcRouteHandler())
{
Domain = domain;
}
public newDomainRoute(string domain, string url, RouteValueDictionary defaults, IRouteHandler routeHandler)
: base(url, defaults, routeHandler)
{
Domain = domain;
}
public newDomainRoute(string domain, string url, object defaults)
: base(url, new RouteValueDictionary(defaults), new MvcRouteHandler())
{
Domain = domain;
}
public newDomainRoute(string domain, string url, object defaults, object constraints)
: base(url, new RouteValueDictionary(defaults), new RouteValueDictionary(constraints), new MvcRouteHandler())
{
Domain = domain;
}
public newDomainRoute(string domain, string url, object defaults, IRouteHandler routeHandler)
: base(url, new RouteValueDictionary(defaults), routeHandler)
{
Domain = domain;
}
public newDomainRoute(string domain, string url, object defaults, object constraints, IRouteHandler routeHandler)
: base(url, new RouteValueDictionary(defaults),new RouteValueDictionary(constraints), routeHandler)
{
Domain = domain;
}
public override RouteData GetRouteData(HttpContextBase httpContext)
{
try
{
// 构造 regex
domainRegex = CreateRegex(Domain);
string strregUrl = CreateRegexstring(Url);
if (Constraints != null)
{
foreach (KeyValuePair<string, object> conitem in Constraints)
{
string strrepalce = CreateRegexReplace("{" + conitem.Key + "}");
strregUrl = strregUrl.Replace(strrepalce, CreateRegexOther("{" + conitem.Key + "}", conitem.Value + ""));// CreateRegexOther("{" + conitem.Key + "}", conitem.Value + "");
}
}
//pathRegex = new Regex("^" + strregUrl + "$", RegexOptions.IgnoreCase);
pathRegex = new Regex(strregUrl, RegexOptions.IgnoreCase);
// 请求信息
string requestDomain = httpContext.Request.Headers["host"];
if (!string.IsNullOrEmpty(requestDomain))
{
if (requestDomain.IndexOf(":") > 0)
{
requestDomain = requestDomain.Substring(0, requestDomain.IndexOf(":"));
}
}
else
{
requestDomain = httpContext.Request.Url.Host;
}
string requestPath = httpContext.Request.AppRelativeCurrentExecutionFilePath.Substring(2) + httpContext.Request.PathInfo;
// 匹配域名和路由
Match domainMatch = domainRegex.Match(requestDomain);
Match pathMatch = pathRegex.Match(requestPath);
// 路由数据
RouteData data = null;
if ((domainMatch.Success || requestDomain == "localhost") && pathMatch.Success)//&&pathMatch.Success
{
data = new RouteData(this, RouteHandler);
// 添加默认选项
if (Defaults != null)
{
foreach (KeyValuePair<string, object> item in Defaults)
{
data.Values[item.Key] = item.Value;
}
}
// 匹配域名路由
for (int i = 1; i < domainMatch.Groups.Count; i++)
{
Group group = domainMatch.Groups[i];
if (group.Success)
{
string key = domainRegex.GroupNameFromNumber(i);
if (!string.IsNullOrEmpty(key) && !char.IsNumber(key, 0))
{
if (!string.IsNullOrEmpty(group.Value))
{
data.Values[key] = group.Value;
}
}
}
}
// 匹配域名路径
for (int i = 1; i < pathMatch.Groups.Count; i++)
{
Group group = pathMatch.Groups[i];
if (group.Success)
{
string key = pathRegex.GroupNameFromNumber(i);
if (!string.IsNullOrEmpty(key) && !char.IsNumber(key, 0))
{
if (!string.IsNullOrEmpty(group.Value))
{
data.Values[key] = group.Value;
}
}
}
}
}
if (data == null)
{
}
return data;
}
catch (Exception ex)
{
}
return null;
}
public override VirtualPathData GetVirtualPath(RequestContext requestContext, RouteValueDictionary values)
{
return base.GetVirtualPath(requestContext, RemoveDomainTokens(values));
}
public DomainData GetDomainData(RequestContext requestContext, RouteValueDictionary values)
{
// 获得主机名
string hostname = Domain;
foreach (KeyValuePair<string, object> pair in values)
{
hostname = hostname.Replace("{" + pair.Key + "}", pair.Value.ToString());
}
// Return 域名数据
return new DomainData
{
Protocol = "http",
HostName = hostname,
Fragment = ""
};
}
private Regex CreateRegex(string source)
{
// 替换
source = source.Replace("/", @"/?");
source = source.Replace(".", @".?");
source = source.Replace("-", @"-?");
source = source.Replace("{", @"(?<");
source = source.Replace("}", @">([a-zA-Z0-9_]*))");
return new Regex("^" + source + "$", RegexOptions.IgnoreCase);
}
private string CreateRegexstring(string source)
{
// 替换
source = source.Replace("/", @"/?");
source = source.Replace(".", @".?");
source = source.Replace("-", @"-?");
source = source.Replace("{", @"(?<");
source = source.Replace("}", @">([a-zA-Z0-9_]*))");
return source;
// return new Regex("^" + source + "$", RegexOptions.IgnoreCase);
}
/// <summary>
/// 过滤特殊字符串
/// </summary>
/// <param name="source"></param>
/// <param name="strregex"></param>
/// <returns></returns>
private string CreateRegexspecial(string source, string strregex)
{
// 替换
source = source.Replace("/", @"/?");
source = source.Replace(".", @".?");
source = source.Replace("-", @"-?");
return source;
}
public string CreateRegexReplace(string source)
{
source = source.Replace("{", @"(?<");
source = source.Replace("}", @">([a-zA-Z0-9_]*))");
return source;
}
private string CreateRegexOther(string source,string strregex)
{
// 替换
//source = source.Replace("/", @"/?");
//source = source.Replace(".", @".?");
//source = source.Replace("-", @"-?");
source = source.Replace("{", @"(?<");
source = source.Replace("}", @">(" + strregex + "))");
//return new Regex(source, RegexOptions.IgnoreCase);
return source;
}
private RouteValueDictionary RemoveDomainTokens(RouteValueDictionary values)
{
Regex tokenRegex = new Regex(@"({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?({[a-zA-Z0-9_]*})*-?.?/?");
Match tokenMatch = tokenRegex.Match(Domain);
for (int i = 0; i < tokenMatch.Groups.Count; i++)
{
Group group = tokenMatch.Groups[i];
if (group.Success)
{
string key = group.Value.Replace("{", "").Replace("}", "");
if (values.ContainsKey(key))
values.Remove(key);
}
}
return values;
}
}
public class DomainData
{
/// <summary>
/// 协议头
/// </summary>
public string Protocol { get; set; }
/// <summary>
/// 域名
/// </summary>
public string HostName { get; set; }
/// <summary>
///
/// </summary>
public string Fragment { get; set; }
}
public static void RegisterRoutes(RouteCollection routes)
{
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
routes.Add(
"loginDomainRoute", new newDomainRoute(
"login." + CommConfig.Websitedomain,
"{controller}/{action}/{id}",
new { controller = "Home", action = "login", id = UrlParameter.Optional }
));
}