subdomínios dinâmicos em asp.net mvc
-
10-07-2019 - |
Pergunta
Eu sou bastante novo para asp.net, e têm pouca experiência com o IIS. Eu gostaria de ter cada usuário do meu aplicativo obter o seu próprio sub-domínio, mas todos usam os mesmos controladores. O subdomínio, então, controlar o conteúdo que é exibido.
Exemplo:
user1subdomain.mydomain.com/Whatever
user2subdomain.mydomain.com/Whatever
Will ambos usam o mesmo controlador. Idealmente um parâmetro poderia dar o nome de usuário para o controlador, o que poderia, em seguida, exibir o conteúdo apropriado. Eu gostaria que fosse o suficiente flexível que novos subdomínios pode ser adicionado ao banco de dados sem reescrever o encaminhamento regras cada vez que um novo subdomínio é adicionado.
Solução
MVC não está vinculado ao domínio, apenas para o caminho (por exemplo http: // domain / path ).
Para fazer isso corretamente é necessário o seguinte ...
-
configuração
- Wildcard DNS para * .Yourdomain.com apontando para o servidor.
- O site na configuração do IIS com nenhum cabeçalho de host. Quaisquer outros sites hospedado nessa instância do IIS na o mesmo IP deve ter cabeçalhos de host especificado.
- A sua aplicação terá de verificar o cabeçalho do host pedido seja no carregamento da página, início da sessão ou algum outro evento.
Outras dicas
Eu encontrei uma resposta mais fácil no blogue desta pessoa. Muito surpreso este obras, assim como ele faz e que esta solução é mais de 4 anos de idade.
http: //blog.maartenballiauw. ser / post / 2009/05/20 / aspnet-mvc-domain-routing.aspx
A implementação rota personalizada:
public class DomainRoute : Route
{
public string Domain { get; set; }
public override RouteData GetRouteData(HttpContextBase httpContext)
{
// Build regex
domainRegex = CreateRegex(Domain);
pathRegex = CreateRegex(Url);
// Request information
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 domain and route
Match domainMatch = domainRegex.Match(requestDomain);
Match pathMatch = pathRegex.Match(requestPath);
// Route data
RouteData data = null;
if (domainMatch.Success && pathMatch.Success)
{
data = new RouteData(this, RouteHandler);
// Add defaults first
if (Defaults != null)
{
foreach (KeyValuePair<string, object> item in Defaults)
{
data.Values[item.Key] = item.Value;
}
}
// Iterate matching domain groups
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;
}
}
}
}
// Iterate matching path groups
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;
}
}
}
}
}
return data;
}
public override VirtualPathData GetVirtualPath(RequestContext requestContext, RouteValueDictionary values)
{
return base.GetVirtualPath(requestContext, RemoveDomainTokens(values));
}
public DomainData GetDomainData(RequestContext requestContext, RouteValueDictionary values)
{
// Build hostname
string hostname = Domain;
foreach (KeyValuePair<string, object> pair in values)
{
hostname = hostname.Replace("{" + pair.Key + "}", pair.Value.ToString());
}
// Return domain data
return new DomainData
{
Protocol = "http",
HostName = hostname,
Fragment = ""
};
}}
E aqui está como ele pode ser usado.
routes.Add("DomainRoute", new DomainRoute(
"{controller}-{action}.example.com", // Domain with parameters
"{id}", // URL with parameters
new { controller = "Home", action = "Index", id = "" } // Parameter defaults
));
Na maior parte não é um problema. Eu acho!
Em termos de aplicação / encaminhamento dos começos de roteamento, onde as extremidades de domínio para mapeamento vários domínios para o mesmo requerimento não é um problema, que vai funcionar.
Em termos de IIS pode mapear os domínios que você quer (bem não é obrigado a ser um limite) a um único local - não tenho certeza se você pode usar um curinga - a versão do IIS que você está usando?
Quando uma solicitação chega existem eventos que você pode ligar para olhar para o domínio e, portanto, configurar parâmetros desejados (usuário, por exemplo), o URL raiz para o pedido está disponível a partir do contexto mais tarde no ciclo também - mas você vai querer pegá-lo cedo.
Se você pode fazer wildcards torna-se bastante trivial - pegar o pedido, validar o subdomínio contra os usuários do banco de dados (se não é válido redirecionamento para o site padrão), definir o usuário e continua através da rota normal <. / p>
Se você não pode fazer wildcards em seguida, o desafio é a adição de cabeçalhos de host para o aplicativo (site) na mosca IIS a partir de sua aplicação como os usuários são adicionados ao banco de dados.