执行动态添加的社交网络小部件

Executing dynamically added social network widgets

我目前正在 Liferay 6.2 中开发一个 portlet。在 portlet 配置中,我存储社交网络名称及其脚本(由不同的社交网络提供的脚本,例如 Facebook、Twitter 等)。

关于 public portlet,我有不同的选项卡,每个存储的社交网络对应一个选项卡(因此它们的数量是可变的)。当我最初加载 portlet 时,我可以毫无问题地显示 Facebook 页面插件,但是当我开始更改选项卡时,就会出现问题。我带来了社交网络脚本(html + 脚本标签)。

我知道如果你插入那段代码,脚本标签将不会被执行,所以我不会在 portlet 上加载插件,只有 html。如果我 eval() 脚本,Facebook 脚本根本不起作用,并且不显示任何错误。如果我用自己的代码更改 Facebook 的脚本标签,然后对它进行 eval(),它会起作用,但如果我继续使用 Facebook 的代码,则什么也不会发生。

A.io.request(portletURL.toString(),{
            on: {
              success: function() {
                var data = this.get('responseData');
                var cont = document.getElementById('contenedor-script');
                document.getElementById('contenedor-script').innerHTML = data;
                var arr = document.getElementById('contenedor-script').getElementsByTagName('script')
                for (var n = 0; n < arr.length; n++){
                    console.log(arr[n].innerHTML);
                    eval(arr[n].innerHTML) //this executes the script tag
                }
              }
            }
          });

现在插入的脚本是:

<div id="fb-root"></div>
<script>(function(d, s, id) {
  var js, fjs = d.getElementsByTagName(s)[0];
  if (d.getElementById(id)) return;
  js = d.createElement(s); js.id = id;
  js.src = "//connect.facebook.net/es_ES/sdk.js#xfbml=1&version=v2.7";
  fjs.parentNode.insertBefore(js, fjs);
}(document, 'script', 'facebook-jssdk'));</script>


<div class="fb-page" data-href="https://www.facebook.com/facebook" data-tabs="timeline" data-small-header="false" data-adapt-container-width="true" data-hide-cover="false" data-show-facepile="true"><blockquote cite="https://www.facebook.com/www.oviedo.es/" class="fb-xfbml-parse-ignore"><a href="https://www.facebook.com/www.oviedo.es/">Facebook</a></blockquote></div>

当函数未被评估时,html 标记被显示。

我的替代方法是在开始时加载所有选项卡,然后使用 CSS 开始显示和隐藏它们,但这是一个更糟糕的主意。

谢谢。

您需要使用 FB.XFBML.parse() 再次解析插件:https://developers.facebook.com/docs/reference/javascript/FB.XFBML.parse/

元素在浏览器中呈现后立即调用该函数,JavaScript SDK 将 parse/show 它们。

顺便说一句,你当然应该只加载一次 JS SDK。永远不要使用 "eval"...