7

我正在使用 AngularJS 和 REST Web API 开发一个 SPA 应用程序,它位于一个非常小的 ASP.NET MVC4 层之上。由于这里不重要的原因,我没有使用 MVC4 的默认帐户控制器。

基本上,我想在用户之间共享“任务”。我的目标是能够通过电子邮件将特定“任务”实体的 URL 发送给任何用户。单击该 URL 应启动身份验证。成功验证后,我想显示真实的任务页面信息。

AngularJS 使我的 URL 带有 # 符号,或者显示任务“XYZ123”的页面的 URL 是: http ://hostname.com/#/tasks/XYZ123

ASP.NET 将未经授权的对该 URL 的访问重定向到: http ://hostname.com/Home/Login?ReturnUrl=%2f#/tasks/XYZ123

这没关系,但是相关的控制器方法从 # 中“剪掉”了路径,所以在:

 public ActionResult Login(string returnUrl)

'returnUrl' 的值将只是“/”

所以,我失去了路径:我想建立一个具有原始 URL 的“与 Facebook 连接”链接,例如:

http://hostname.com/Login/ExternalLogin?ReturnUrl=%2F#/tasks/XYZ123

但是我不能。

解决此问题的正确方法是什么?

我可以考虑创建自己的不带 # 标记的重定向服务 URL,但此解决方案意味着额外的工作,并且仅涵盖系统发送带有任务 URL 的消息的情况 - 人类仍会尝试从浏览器。

感谢您的任何提示。

最大限度

4

3 回答 3

3

是的。浏览器会剪切“#/tasks/XYZ123”并请求没有该哈希的页面。尽管哈希本身出现在登录页面上 - 它又是浏览器的工作。哈希没有传送到服务器。

因此,当浏览器使用 ?ReturnUrl=%2f#/tasks/XYZ123 加载登录页面时,我们可以重写表单操作并对哈希进行编码。

如果表格如下所示:

<form action="/Home/Login" method="post" >
    ...
</form>

javascript 代码应如下所示:

<script src="~/js/jquery.js"></script>

<script type="text/javascript">
    $(function() {

        var search = $(location).attr('search') || '';
        var hash = $(location).attr('hash') || '';

        if (hash.length === 0) {                
            if (window.history.pushState) {
                window.history.pushState('login', 'Login', '/Home/Login');
            }
        } else if (search === '?ReturnUrl=%2f') {
            $('form').attr('action', '/Home/Login' + search + encodeURIComponent(hash) );
        }

    });

</script>

以下内容需要具有window.history.pushState的部分:

如果没有哈希,那么对于 SPA,它的 URL(更有可能)将是:

http://hostname.com/Home/Login?ReturnUrl=%2f

所以在这里我们尝试用更准确的方式替换 URL(无需重新加载页面)

http://hostname.com/Home/Login
于 2016-02-02T11:18:48.890 回答
0

可以使用Request(like .Urlor .QueryString) 的属性来获取原始 url(和 url 参数),而不是依赖于 returnUrl 参数的自动绑定。

于 2014-01-09T16:11:49.463 回答
0

将 returnUrl 中的 # 替换为 %23

于 2019-06-17T19:30:49.037 回答