【问题标题】:How to count the number of times a h:outputLink was clicked?如何计算 h:outputLink 被点击的次数?
【发布时间】:2015-01-07 19:16:13
【问题描述】:

我有一个包含以下代码的 PrimeFaces 页面:

<pm:content id="content">
    <p:dataList value="#{likeditems.likedItems}" var="item" pt:data-inset="true" paginator="true" rows="5">
        <f:facet name="header">
            Products you liked in the past
        </f:facet>
        <h:outputLink value="#{item.url}" target="_new">
            <p:graphicImage name="http://example.com/my-product-mobile/f/op/img/underConstructionImage.jpg" />
            <h2>#{item.title}</h2>
            <p>Approx. #{item.price} (for most up-to-date price, click on this row and view the vendor's page)</p>
        </h:outputLink>
        <f:facet name="footer">
            Products you liked in the past
        </f:facet>
    </p:dataList>
</pm:content>

当用户点击h:outputLink 时,我希望发生两件事:

  1. 在浏览器中打开 URL item.url 的新页面。
  2. 调用方法likeditems.itemLinkClicked(item)(在该方法中,我更新了特定链接的点击次数)。

第一件事已经开始了 (target="_new")。

如何在第一个停止工作的情况下实现第二个(更新链接点击次数的方法调用)?

【问题讨论】:

    标签: jsf primefaces primefaces-mobile


    【解决方案1】:

    第一件事已经开始了 (target="_new")。

    The target should actually be _blank.


    如何在第一个停止工作的情况下实现第二个(更新链接点击次数的方法调用)?

    最简单(幼稚)的 JSF 方式是在点击时触发 &lt;p:remoteCommand&gt;

    <h:outputLink value="#{item.url}" target="_blank" onclick="count_#{item.id}()">
        ...
    </h:outputLink>
    <p:remoteCommand name="count_#{item.id}" action="#{likeditems.itemLinkClicked(item)}" />
    

    但这会产生大量重复的 JS 代码,效果不佳。您可以将其放在数据列表之外并摆弄函数参数。但是,当最终用户右键单击并选择上下文菜单项(在新选项卡、新窗口、新隐身窗口中打开、另存为、复制地址等)时,这仍然不起作用。这在最终用户中间点击时也不起作用(中间点击的默认浏览器行为是“在新窗口中打开”)。

    ZEEF,我们使用脚本将点击、中键或右键单击时的&lt;a href&gt; 更改为一个URL,该URL 调用一个更新计数的servlet,然后在给定的URL 上执行window.open()

    给定一个

    <h:outputLink value="#{item.url}" styleClass="tracked" target="_blank">
    

    相关的脚本基本上应该是这样的:

    // Normal click.
    $(document).on("click", "a.tracked", function(event) {
        var $link = $(this);
        updateTrackedLink($link);
        var trackingURL = $link.attr("href");
        $link.attr("href", $link.data("href"));
        $link.removeData("href");
        window.open(trackingURL);
        event.preventDefault();
    });
    
    // Middle click.
    $(document).on("mouseup", "a.tracked", function(event) {
        if (event.which == 2) {
            updateTrackedLink($(this));
        }
    });
    
    // Right click.
    $(document).on("contextmenu", "a.tracked", function(event) {
        updateTrackedLink($(this));
    });
    
    // Update link href to one of click count servlet, if necessary.
    function updateTrackedLink($link) {
        if ($link.data("href") == null) {
            var url = $link.attr("href");
            $link.data("href", url);
            $link.attr("href", "/click?url=" + encodeURIComponent(url));
        }
    }
    

    click servlet 应该如下所示(为简洁起见,省略了请求参数验证):

    @WebServlet("/click")
    public class ClickServlet extends HttpServlet {
    
        @EJB
        private ClickService clickService;
    
        @Override
        protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            String url = request.getParameter("url");
            clickService.incrementClickCount(url);
            response.sendRedirect(url);
        }
    
    }
    

    请注意,这种方式不需要target="_blank"。它只会被禁用 JavaScript 的用户使用。但是网站上还有很多其他的东西无论如何都不起作用,包括上面的 JS 跟踪。这也是你关心的问题,那你最好把那个click servlet URL直接放在&lt;h:outputLink value&gt;中。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-12-06
      • 2014-08-14
      • 2020-05-16
      • 1970-01-01
      • 2017-11-29
      • 1970-01-01
      • 2020-05-30
      • 2023-04-10
      相关资源
      最近更新 更多