我正在使用HttpModule重写多语言网站上的网址。在HttpModule中,我为BeginRequest事件添加了一个处理程序,并查找包含文化名称的路径的第一部分。

例如,/ fr-ca / index.aspx将被重写为/index.aspx,并将线程的culture和ui culture设置为3084.这样可以正常工作。

输入表单身份验证。表单身份验证仍然可以正常使用未映射的URL,但如果用户未经授权,它将重定向到web.config的身份验证部分中设置的loginUrl,并包含?ReturnUrl = querystring参数来处理重定向回请求用户通过身份验证后的页面。

如果用户使用非默认语言请求页面,则此处存在两个问题:

  1. loginUrl在重写之前忽略路径
  2. ReturnUrl参数也忽略了原始路径。
  3. 它等同于Request.Url.PathAndQuery而不是Request.RawUrl。

    我不能在AuthorizeRequest事件中跳转到管道,因为那时我必须防止所有可能的文化值,因为我正在使用一个带有多个位置路径的web.config文件。这也无法解决第一个问题。

    我已经浏览了反射器中的FormsAuthenticationModule,我看到我可以在哪里更改它以解决#1和#2,但它当然是密封的。

    我也浏览了很多,但我看不到任何可行的解决方案。

    FormsAuthenticationModule正在检查在UrlAuthorizationModule中生成的401标头。如果您在loginUrl页面上查找referrer(为空),则会确认。

    有什么想法吗?

    编辑#1

    我正在使用IIS 6,而IIS 7不是一个选项。

    编辑#2

    登录页面没有获取默认的culture / ui文化,因为当我生成本地资源(设计视图:工具<!> gt;生成本地资源)时,IDE将以下内容添加到页面指令:

    <!>

    培养= QUOT;汽车QUOT <!>;元:<!>; <!>的ResourceKey = QUOT PageResource1 QUOT; <!>的UICulture = QUOT;汽车QUOT <!>;

    在vs.net 2008中小心这个!至少这解决了默认文化没有被引用的问题之一,但#1和#2仍然是未完成的。

    编辑3

    我希望我可以跳转到其中一个管道事件来进行自己的重定向,但是在Reflecting System.Web.Security.UrlAuthorizationModule OnEnter方法中,我了解到一旦设置了401头,该方法就会调用application。正如您所猜测的那样,CompleteRequest将我们带到了EndRequest事件的正确位置。这就是FA模块跳转到重定向,我恐怕我不能跳到前面做我自己的重定向!令我感到惊讶的是,没有更多的人遇到这个问题,或者他们还没有参与其中。


    示例:

    我在物理文件夹/ members /中有一个成员的部分,受到表单身份验证的保护。

    在web.config中,我有:

    <authentication mode="Forms">
      <forms loginUrl="~/members/login.aspx" timeout="40" />
    </authentication>
    

    和...

      <location path="members">
          <system.web>
              <authorization>
                  <deny users="?" />
                  <allow roles="Members" />
                  <deny users="*" />
              </authorization>
          </system.web>
      </location>
    

    当未经身份验证的用户请求/ members /的索引页时,它们会被FormsAuthenticationModule从上面的身份验证部分重定向到loginUrl。它还会将?ReturnUrl参数附加到请求的页面。

    如果用户使用默认文化浏览网站,这可以正常工作,但是我的HttpModule根据路径第一部分中文化名称的存在来设置文化。

    因此,/ fr-ca/members/index.aspx被重写为/members/index.aspx并将culture / ui文化设置为加拿大法语。不幸的是,FormsAuthenticationModule将用户发送到loginUrl页面,其中包含重写的url,而不是原始的url。因此,文化设置丢失,重定向网址不正确。

    希望如此帮助@Greg

有帮助吗?

解决方案

好的,问题解决了。

原来关键是清除machine.config httpModules,添加我的自定义httpModule,然后添加回所需的默认httpModule。这允许我的自定义httpModule在FormsAuthenticationHttpModule之前跳转到EndRequest事件。

<httpModules>
    <clear/>
    <!-- custom -->
    <add name="LocalizationHttpModule" type="LocalizationHttpModule"/>
    <!-- add back defaults, exlude PassportAuthentication, AnonymousIdentification, Profile -->
    <add name="OutputCache" type="System.Web.Caching.OutputCacheModule" />
    <add name="Session" type="System.Web.SessionState.SessionStateModule" />
    <add name="WindowsAuthentication" type="System.Web.Security.WindowsAuthenticationModule" />
    <add name="FormsAuthentication" type="System.Web.Security.FormsAuthenticationModule" />
    <add name="RoleManager" type="System.Web.Security.RoleManagerModule" />
    <add name="UrlAuthorization" type="System.Web.Security.UrlAuthorizationModule" />
    <add name="FileAuthorization" type="System.Web.Security.FileAuthorizationModule" />

</httpModules> 

然后,在我的自定义httpModule中,我只需点击EndRequest,查找401状态代码,然后按我的意愿重定向。基本上我正在重写FormsAuthenticationHttpModule OnLeave方法中的代码以满足我的需要。

Public Sub Init(ByVal context As System.Web.HttpApplication) Implements System.Web.IHttpModule.Init

    Dim authentication As AuthenticationSection = WebConfigurationManager.GetSection("system.web/authentication")
    If authentication.Mode = AuthenticationMode.Forms Then
        Me._LoginUrl = authentication.Forms.LoginUrl
        AddHandler context.EndRequest, AddressOf Context_EndRequest
    End If

End Sub

Private Sub Context_EndRequest(ByVal sender As Object, ByVal e As EventArgs)
    Dim application As HttpApplication = DirectCast(sender, HttpApplication)
    Dim context As HttpContext = application.Context

    If (context.Response.StatusCode = &H191) Then                
       ' do custom redirect here
    End If

End Sub

其他提示

关于我唯一能想到的是手动重定向到Login表单。

1)允许所有访问会员目录
2)成员资格中的所有页面都直接从Page。的子类继承 3)在Page子类的PreInit(?)中,检查用户是否是成员角色的成员 4)如果没有,请自行构建登录页面的URL,包括ReturnURL参数并将用户重定向到您的登录URL。

你可能也可以通过添加一堆<!> lt;来破解它。位置GT <!>; web.config中的部分。例如:<!> lt; location path = <!> quot; fr-ca / members <!> quot; <!> gt; <!> lt; authenication GT <!>; LT <!>; form loginUrl = <!> quot;〜/ fr-ca / members / login.aspx <!> quot; <!> gt; ...但我真的不知道。

我可能还有其他不熟悉的方法。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top