ASP.NET 使用 CORS 和 cookie 身份验证的身份/OData 缺少 Auth cookie
ASP.NET Identity / OData using CORS and cookie authentication missing Auth cookie
我有一个 ASP.NET 身份站点和一个 ASP.NET OData 站点。
两个站点都启用了 CORS,并且两个站点都使用 ASP.NET Identity CookieAuthentication。
当我使用 IIS(不是 express)在我的计算机上本地执行这两个站点时,AUTH cookie 会在每个请求到 OData 站点的 header 中传递。
但是当我将站点部署到生产 IIS 服务器时,header 在调用生产 OData 站点时缺少 AUTH cookie。
生产和我的本地 IIS 都具有相同的域名,并且 CORS 设置为允许所有。
WebApiConfig 有
cors = new Http.Cors.EnableCorsAttribute("*", "*", "*");
config.Enable(cors);
在任何人问之前,是的,站点之间的机器密钥是相同的。
更新
这似乎是一个 CORS 问题。
当两个站点都在我的本地计算机上时,它们使用相同的主机名和域名,但是当站点在生产服务器上时,它们具有不同的主机名和相同的域名。
您可能需要在 OAuthAuthorizationServerProvider 中指定 "Access-Control-Allow-Origin"。
我正在使用 OWIN,但您应该也能做类似的事情。
context.OwinContext.Response.Headers.Add("Access-Control-Allow-Origin", new[] { "*" });
尝试在您的 OWIN 启动程序中添加策略 class,如下所示。请记住,Startup class 可能有一些不同的 class 文件,因为它是部分 class。此外,检查 ConfigureAuth 方法以查看是否根据您的需要设置了所有内容。例如,您在 ConfigureAuth 方法中设置身份的外部登录 cookie,如下所示,以允许外部登录 cookie,如 facebook 和 google.
public void Configuration(IAppBuilder app)
{
//
app.UseCors(CorsOptions.AllowAll);
ConfigureAuth(app);
}
app.UseExternalSignInCookie(Microsoft.AspNet.Identity.DefaultAuthenticationTypes.ExternalCookie);
我终于让它工作了。
在 ASP.NET 身份站点中,我有以下内容:
// configure OAuth for login
app.UseCookieAuthentication(new CookieAuthenticationOptions {
AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
Provider = new CookieAuthenticationProvider(),
LoginPath = new PathString("/Account/Login.aspx"),
CookieName = ".TESTAUTH",
CookieDomain = ".test.com",
CookieSecure = CookieSecureOption.Always
});
似乎 ASP.NET 身份站点上的重要部分是 "CookieName, CookieDomain, and the Machine Key" 必须与 OData 站点上的相匹配。
然后在 OData 网站上我有以下内容:
// configure OAuth for login
app.UseCookieAuthentication(new CookieAuthenticationOptions {
AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
Provider = new CookieAuthenticationProvider { OnApplyRedirect = ApplyRedirect },
LoginPath = new PathString("/Account/Login.aspx"),
CookieName = ".TESTAUTH",
CookieDomain = ".test.com",
CookieSecure = CookieSecureOption.Always
});
// build the configuration for web api
HttpConfiguration config = new HttpConfiguration();
// Enable CORS (Cross-Origin Resource Sharing) for JavaScript / AJAX calls
// NOTE: USING ALL "*" IS NOT RECOMMENDED
var cors = new Http.Cors.EnableCorsAttribute("*", "*", "*");
config.EnableCors(cors);
// call the web api startup
WebApiConfig.Register(config);
app.UseWebApi(config);
private void ApplyRedirect(CookieApplyRedirectContext context)
{
Uri absoluteUri = null;
if (Uri.TryCreate(context.RedirectUri, UriKind.Absolute, absoluteUri))
{
var path = PathString.FromUriComponent(absoluteUri);
if (path == context.OwinContext.Request.PathBase + context.Options.LoginPath)
{
QueryString returnURI = new QueryString(context.Options.ReturnUrlParameter, context.Request.Uri.AbsoluteUri);
context.RedirectUri = "https://www.test.com/Account/Login.aspx" + returnURI.ToString;
}
}
context.Response.Redirect(context.RedirectUri);
}
"LoginPath" 是必需的,即使它在 OData 站点上不存在,并且您不能使用完整的 url 到另一个站点作为登录路径。
我使用 "OnApplyRedirect" 重定向到实际的登录页面。
我不确定 "config.EnableCors" 和 "app.UseCors" 之间有什么区别,但 EnableCors 现在似乎可以正常工作。
我有一个 ASP.NET 身份站点和一个 ASP.NET OData 站点。
两个站点都启用了 CORS,并且两个站点都使用 ASP.NET Identity CookieAuthentication。
当我使用 IIS(不是 express)在我的计算机上本地执行这两个站点时,AUTH cookie 会在每个请求到 OData 站点的 header 中传递。
但是当我将站点部署到生产 IIS 服务器时,header 在调用生产 OData 站点时缺少 AUTH cookie。
生产和我的本地 IIS 都具有相同的域名,并且 CORS 设置为允许所有。
WebApiConfig 有
cors = new Http.Cors.EnableCorsAttribute("*", "*", "*");
config.Enable(cors);
在任何人问之前,是的,站点之间的机器密钥是相同的。
更新
这似乎是一个 CORS 问题。
当两个站点都在我的本地计算机上时,它们使用相同的主机名和域名,但是当站点在生产服务器上时,它们具有不同的主机名和相同的域名。
您可能需要在 OAuthAuthorizationServerProvider 中指定 "Access-Control-Allow-Origin"。
我正在使用 OWIN,但您应该也能做类似的事情。
context.OwinContext.Response.Headers.Add("Access-Control-Allow-Origin", new[] { "*" });
尝试在您的 OWIN 启动程序中添加策略 class,如下所示。请记住,Startup class 可能有一些不同的 class 文件,因为它是部分 class。此外,检查 ConfigureAuth 方法以查看是否根据您的需要设置了所有内容。例如,您在 ConfigureAuth 方法中设置身份的外部登录 cookie,如下所示,以允许外部登录 cookie,如 facebook 和 google.
public void Configuration(IAppBuilder app)
{
//
app.UseCors(CorsOptions.AllowAll);
ConfigureAuth(app);
}
app.UseExternalSignInCookie(Microsoft.AspNet.Identity.DefaultAuthenticationTypes.ExternalCookie);
我终于让它工作了。
在 ASP.NET 身份站点中,我有以下内容:
// configure OAuth for login
app.UseCookieAuthentication(new CookieAuthenticationOptions {
AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
Provider = new CookieAuthenticationProvider(),
LoginPath = new PathString("/Account/Login.aspx"),
CookieName = ".TESTAUTH",
CookieDomain = ".test.com",
CookieSecure = CookieSecureOption.Always
});
似乎 ASP.NET 身份站点上的重要部分是 "CookieName, CookieDomain, and the Machine Key" 必须与 OData 站点上的相匹配。
然后在 OData 网站上我有以下内容:
// configure OAuth for login
app.UseCookieAuthentication(new CookieAuthenticationOptions {
AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
Provider = new CookieAuthenticationProvider { OnApplyRedirect = ApplyRedirect },
LoginPath = new PathString("/Account/Login.aspx"),
CookieName = ".TESTAUTH",
CookieDomain = ".test.com",
CookieSecure = CookieSecureOption.Always
});
// build the configuration for web api
HttpConfiguration config = new HttpConfiguration();
// Enable CORS (Cross-Origin Resource Sharing) for JavaScript / AJAX calls
// NOTE: USING ALL "*" IS NOT RECOMMENDED
var cors = new Http.Cors.EnableCorsAttribute("*", "*", "*");
config.EnableCors(cors);
// call the web api startup
WebApiConfig.Register(config);
app.UseWebApi(config);
private void ApplyRedirect(CookieApplyRedirectContext context)
{
Uri absoluteUri = null;
if (Uri.TryCreate(context.RedirectUri, UriKind.Absolute, absoluteUri))
{
var path = PathString.FromUriComponent(absoluteUri);
if (path == context.OwinContext.Request.PathBase + context.Options.LoginPath)
{
QueryString returnURI = new QueryString(context.Options.ReturnUrlParameter, context.Request.Uri.AbsoluteUri);
context.RedirectUri = "https://www.test.com/Account/Login.aspx" + returnURI.ToString;
}
}
context.Response.Redirect(context.RedirectUri);
}
"LoginPath" 是必需的,即使它在 OData 站点上不存在,并且您不能使用完整的 url 到另一个站点作为登录路径。
我使用 "OnApplyRedirect" 重定向到实际的登录页面。
我不确定 "config.EnableCors" 和 "app.UseCors" 之间有什么区别,但 EnableCors 现在似乎可以正常工作。