提问者:小点点

如果存在延迟,在onclick处理程序中触发弹出窗口阻止程序


在实现支付网关时,我遇到了这样一种情况:在3D安全过程中使用弹出窗口对用户体验最好。

流程是这样的:

  1. 用户在“支付”页面上,并将信用卡数据输入托管字段。
  2. 在“Buy”onclick事件上,我调用网关的javascript片段来获取卡令牌。
  3. 我将其发布到后端。
  4. 后端检查是否需要3DS.
  5. 如果是,前端打开一个带有3DS表单的新窗口。

onclick的代码如下:

var win;

$("#buy").click(function() {

    gateway.Tokenize(function(token) {

        $.ajax({
            url: 'backend.php',
            type: "POST",
            data: {
                token: token
            }
        }).done(function(data) {

            if (data.threeDRequired) {
                win = window.open(data.url, "_blank");
                win.focus();
            }

        });

    });

});

通常情况下,这没有问题,弹出窗口会打开,但如果tokenize方法或$.ajax调用太长时间无法完成,则会触发弹出窗口阻止程序。 即使在$.ajax调用中添加async:false也无济于事。

我能做些什么让它在所有情况下都起作用吗? 目前我能想到的唯一解决方案是,要么在单击事件开始时打开一个弹出窗口,然后在URL可用时加载它,要么让用户在弹出窗口被阻止时单击一个额外的按钮。 两者似乎都不理想。


共1个答案

匿名用户

事件是同步的,并且马上过期,这意味着你不能在将来的任何时候捕获点击并使用它的特权/权限。

您可以做的是立即打开弹出窗口,然后关闭它,或者在tokenize返回后更新它的位置。

这是一种乐观的做法,但如果你自信成功是最期待的行为,那就不应该太烦人。

var win;
$("#buy").click(function() {
  win = window.open("about:blank", "_blank");
  gateway.Tokenize(function(token) {
    $.ajax({
      url: 'backend.php',
      type: "POST",
      data: {token: token}
    }).done(function(data) {
      if (data.threeDRequired) {
        win.location = data.url;
        win.focus();
      }
      else {
        win.close();
      }
    });
  });
});

这个应该管用。