65.9K
CodeProject 正在变化。 阅读更多。
Home

Disqus(可插拔评论系统)在 ASP.NET MVC 3 中的介绍

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.79/5 (10投票s)

2013 年 3 月 10 日

CPOL

11分钟阅读

viewsIcon

52900

downloadIcon

1529

本文讨论了您可以在 Web 应用程序中使用 Disqus 的方法。

Sample Image - maximum width is 600 pixels

引言

您曾多少次发现自己正在设计一个评论系统?很多次,对吧?在我处理多个项目时,情况正是如此!对于我参与过的许多应用程序,我都是自己设计整个评论模块,从表到代码。但对于我最近的项目,我想摆脱这种处理评论的方式。在这篇文章中,我将向大家介绍 Disqus,它是一个可插拔评论系统,只需很少的代码就可以在各种应用程序中使用!本文使用 ASP.NET MVC 3,但这个例子几乎可以在任何地方使用。另外,我与 Disqus 公司没有任何关联。我被它使用的简便性所打动,因此写了这篇文章。更多细节将在后续章节中介绍。本文涵盖两个主题。首先,我将介绍如何在简单的 ASP.NET MVC 3 应用程序中使用 Disqus。然后,我将讨论一种使 Disqus“AJAX 化”的方法。

背景

我之前曾简要说明过我设计评论系统的方式。这不仅仅是一个简单的表和几行插入/删除评论的代码。设计一个评论系统涉及的方面还有很多。设计一个功能齐全的评论系统时需要考虑的一些事项是——是否允许基于线程的评论系统或扁平的评论系统,是否提供阻止垃圾邮件的功能,用户是否必须注册,还是可以作为访客发帖,等等。为了让我们摆脱所有这些麻烦,我们可以使用 Disqus 这样的可插拔评论系统,它内置了所有这些功能。在您的网站上使用 Disqus 就像注册一个 **disqus shortname** 并添加几行 JavaScript 和 HTML 一样简单!让我们直接进入文章!

Disqus 的基本功能 

在本节中,我将讨论如何在应用程序的页面中引入基本的 Disqus 评论功能。第一步是通过访问此地址进行 Disqus 短名称注册 - https://disqus.com/admin/signup/。**Site Shortname** 是您需要记住的最重要的属性,因为您必须使用此短名称才能让 Disqus 识别您的网站。完成此步骤后,您就可以在网站上使用 Disqus 了。

开始使用示例项目

在进入实际有趣的部分之前,让我谈谈示例应用程序。本文附带的示例项目非常简单明了。它包含两个页面——一个用于基本功能,一个用于基于 AJAX 的实现。要开始使用,请下载项目的 zip 文件并解压缩。现在使用 Visual Studio 打开项目,然后打开 _web.config_ 文件。<appSettings /> 部分包含一个名为 **DisqusShortName** 的键,它最初不包含任何内容。如果您按照上一节的步骤操作,此时您应该已经准备好了。输入您应用程序的 Disqus 短名称。现在按 Ctrl + F5。您现在可以使用示例应用程序了!

回到基础!

终于到代码时间了。让我们来看第一种使用 Disqus 的方法!下面是一个实现基本 Disqus 功能的页面的完整列表。

@using DisqusTutorial.Infrastructure
@{
    ViewBag.Title = "Disqus Default Behavior";
}

<h2>Disqus Default Behavior</h2>

<div>
    <input type="hidden" id="rootUrl" value="@string.Format("{0}://{1}{2}", 
            Request.Url.Scheme, Request.Url.Authority, Url.Content("~"))"/>
    <div id="disqus_thread"></div>
    <script type="text/javascript">
        /* * * CONFIGURATION VARIABLES: EDIT BEFORE PASTING INTO YOUR WEBPAGE * * */
        var disqus_shortname = '@ApplicationConfiguration.DisqusShortName';
        // required: replace example with your forum shortname

        var disqus_identifier = 'hello-world';
        var disqus_url = $('#rootUrl').val() + disqus_identifier;
        var disqus_developer = 1;

        /* * * DON'T EDIT BELOW THIS LINE * * */
        (function () {
            var dsq = document.createElement('script'); dsq.type = 'text/javascript'; dsq.async = true;
            dsq.src = 'http://' + disqus_shortname + '.disqus.com/embed.js';
            (document.getElementsByTagName('head')[0] || 
               document.getElementsByTagName('body')[0]).appendChild(dsq);
        })();
    </script>
    <noscript>Please enable JavaScript to view the 
      <a href="http://disqus.com/?ref_noscript">comments powered by Disqus.</a></noscript>
    <a href="http://disqus.com" class="dsq-brlink">comments powered 
      by <span class="logo-disqus">Disqus</span></a>        
</div>

再简单不过了!这时,我认为有必要逐行讨论上面的代码列表!我将忽略第 1 到 8 行,因为其中没有重要内容,只是通常的设置。第 9 行只是一个隐藏字段,用于提供此网站的根 URL。这只是一个基本示例,所以我不想通过使用视图模型来绑定根 URL 和您将在后续代码行中看到的各种其他内容来使此示例复杂化。在您开始喊“这不干净,可以做得更好……”之前,我想说明这一点(Smile | <img src=)。根 URL 对于实现 Disqus 至关重要,因为 Disqus 使用以下三个属性区分两个评论线程,其中使用了根 URL:

  • Disqus 短名称 - 前面已解释。
  • Disqus 标识符 - 顾名思义,这是一串字符,用于唯一标识一个评论线程。重要的是要提出唯一的值,以免在您的应用程序本身内部产生冲突。
  • Disqus URL - 网站根 URL 与 Disqus 标识符的组合,以便您可以随时访问某个线程的讨论。**请注意**,这应该是一个完整的 URL,而不仅仅是一个相对 URL。

回到讨论,第 10 行定义了一个 div,Disqus 将在此 div 中呈现所有评论以及供用户输入新评论的文本框。请注意 ID,它被设置为 disqus_thread,因为 Disqus 需要确切的 ID 才能加载评论。第 13-15 行代表 Disqus 唯一标识线程所需的属性,如前所述。第 16 行非常重要。在开发应用程序时,您的根 URL(例如)将是 _https://:8080_。出于明显的原因,Disqus 无法解析此 URL。为了告知 Disqus 应用程序当前处于开发者模式,我们必须将第 16 行的 disqus_developer 变量设置为 1。否则,Disqus 评论将无法加载。

第 19-21 行完成了加载 Disqus 工作所需的脚本。在第 19 行,创建了一个 script 元素,然后设置了 type 属性。然后设置 async 属性为 true,表示此脚本将异步加载。因此,任何要执行的活动都必须等到脚本完全加载。一旦指定了 src 属性(在下一行),脚本加载就开始了。请注意加载的 JavaScript 文件的格式。当您注册时,Disqus 还会为您创建一个网站(_<shortname>.disqus.com_),其中包含一个 _embed.js_ 脚本。然后在第 21 行,将创建的 script 元素附加到 head 元素。

脚本加载后,Disqus 使用上面列出的三个属性来加载与唯一标识符相对应的讨论。结果类似于此

Sample Image - maximum width is 600 pixels

AJAX 化 Disqus

现在让我们进入本文最激动人心的部分!Disqus 已经提供了足够的信息来开始使用并实现默认行为。但关于如何让 Disqus 在一个完全基于 AJAX 的页面上工作,并没有足够的信息。我正在做一个需要这种功能的项目。在我的项目中,页面的 URL 不会改变,因此页面不会有完整的刷新,除非用户通过单击顶级导航转到其他页面。与服务器的每一次交互都通过 AJAX 完成,因此需要根据服务器返回的标识符以及何时加载新部分来重新加载 Disqus 评论。

Disqus 提供了一种方法,我们可以使用所需的参数(前面已指定)来“重新加载”评论。此功能用于根据服务器信息“加载”评论。为了简单起见,在本节中,我将仅使用三个 Disqus 评论线程来解释此方法。此页面的布局很简单——它包含三个链接,每个链接对应一个可能的评论线程。然后,与之前一样,有一个 ID 为 disqus_threaddiv 元素,Disqus 将在此异步加载评论。

在通常的标题、using 等之后,我声明了四个变量,就像我们在前面的示例中声明的那样。

<script type="text/javascript">
    /* * * CONFIGURATION VARIABLES: EDIT BEFORE PASTING INTO YOUR WEBPAGE * * */
    var disqus_shortname = '@ApplicationConfiguration.DisqusShortName';
    // required: replace example with your forum shortname

    var disqus_identifier = '';
    var disqus_url = '';
    var disqus_developer = 1;
</script>

这是此页面所需的纯 HTML。它包含三个加载不同评论线程的链接、一个用于根 URL 的隐藏字段、一个用于评论本身的元素以及一些通用的 Disqus 链接。

<div id="controls">
    <div style="float: left">
        <a id="btnPrevious" href="javascript:void(0)"><< Previous</a>
    </div>
    <div style="text-align: center">
        <a id="btnInit" href="javascript:void(0)">First</a>
    </div>
    <div style="float: right">
        <a id="btnNext" href="javascript:void(0)">Next >></a>
    </div>
</div>
<br/><br/>
<input type="hidden" id="rootUrl" value="@string.Format("{0}://{1}{2}", 
   Request.Url.Scheme, Request.Url.Authority, Url.Content("~"))"/>
<div id="disqus_thread"></div>
<noscript>Please enable JavaScript to view the 
  <a href="http://disqus.com/?ref_noscript">comments powered by Disqus.</a></noscript>
<a href="http://disqus.com" class="dsq-brlink">comments 
  powered by <span class="logo-disqus">Disqus</span></a>

正如在前一节中所解释的,有一个隐藏字段包含应用程序的根 URL。现在让我们来处理使这一切工作的最重要方面——jQuery/JavaScript。所需的 JavaScript/jQuery 量非常少!在调用第一行的 initializeDisqus 方法之前,让我解释一下其余部分。紧跟在 initialize 调用后面,我为页面上的三个链接声明了“click”事件处理程序。每个事件都指定一个唯一的 Disqus ID,然后通过传递在第一步中指定的 ID 来调用 reset 方法。

$(document).ready(function () {
    initializeDisqus();

    $('#btnNext').click(function () {
        var disqusId = 'another-page';
        reset(disqusId);
    });

    $('#btnPrevious').click(function () {
        var disqusId = 'yet-another-page';
        reset(disqusId);
    });

    $('#btnInit').click(function () {
        var disqusId = 'hello-world';
        reset(disqusId);
    });
});

在介绍 reset 方法之前,让我先介绍一下 initializeDisqus 方法,我之前从未介绍过!这时,我想提醒大家注意我之前说过的一件事——Disqus 所需的脚本是异步加载的!下面是 initializeDisqus 函数的列表。

function initializeDisqus() {
    var dsq = document.createElement('script'); dsq.type = 'text/javascript'; dsq.async = true;
    dsq.src = 'http://' + disqus_shortname + '.disqus.com/embed.js';

    dsq.onload = function () {
        var disqusId = 'hello-world';
        reset(disqusId);
    };

    (document.getElementsByTagName('head')[0] || 
        document.getElementsByTagName('body')[0]).appendChild(dsq);
}

在这种情况下,前两行执行与之前解释的相同的活动。但现在,在尝试加载 _hello-world_ 的评论之前,我需要确保 Disqus 所需的脚本已加载。为此,我使用前面创建的脚本对象的 onload 事件。当脚本完全加载时,将引发此事件。我已验证此方法在 Internet Explorer、Chrome 和 Firefox 中均有效。脚本完全加载后,我调用 reset 函数,并传入所需的 Disqus 标识符。现在让我们来看 reset 方法。

function reset(disqusId) {
    DISQUS.reset({
        reload: true,
        config: function () {
            this.page.identifier = disqusId;
            this.page.url = $('#rootUrl').val() + disqusId;
        }
    });
}

Disqus API 提供了一个 reset 方法,该方法在此函数内调用。最少需要两个属性——第一个属性 reload 指示是否应重新加载评论,在本例中设置为 true。第二个属性是一个函数调用,该函数设置两个属性:Disqus ID(this.page.identifier)和页面的 URL(this.page.url)。请注意,这使用了包含网站根 URL 的隐藏字段。当此方法完成后,div 将使用由 Disqus 标识符标识的线程的评论进行重新加载!

下面是单击每个链接时发生情况的屏幕截图。Disqus 本身包含一个加载指示器。因此,无需添加自己的加载指示器版本!

单击“First”链接后

After First link is clicked

单击“Next”链接后

After Next link is clicked

单击“Previous”链接后

After Previous link is clicked

Disqus Discovery 选项

在测试我应用程序的纯 AJAX 功能时,我遇到了一个问题。问题是,每当加载某个部分的评论时,都会有一个部分显示 Disqus 网站的最新评论。问题在于指定的 URL 是一种伪 URL。因此,不存在单独的页面,但 URL 必须是唯一的,因此它就是这样,如上面的代码片段所示。但是,当用户单击最新评论部分中的某个内容时,它会出于某种原因尝试重定向到登录评论时标识的页面,因此会失败。简单来说,如果 AJAX 评论加载到 URL 为 _https://:8080/home/disqusajax_ 的页面中,并且 Disqus ID 为 hello-world,Disqus URL 为 _https://:8080/hello-world_,那么它不会将最新评论的单击重定向到 _https://:8080/hello-world_,而是将用户重定向到 _https://:8080/home/disqusajax_。为了避免显示最新评论,必须关闭发现选项,如下面的“设置 // Discovery”下所示(如果您不打算使用 AJAX 加载评论线程,则可能不需要这样做,因为关闭此选项意味着流量和/或收入的损失)

Disqus - turning off discovery

关注点

关于 Disqus 还有很多其他可以探索的途径,我正在研究它们。在为 sBlog.Net(文章)博客引擎的评论系统测试 Disqus 时,我注意到 CodeProject 上没有任何关于 Disqus 的内容,这促使我写了这篇文章。还有一些类似 Disqus 的替代方案。其中一些包括 intense debate、Facebook comment box、coComment 等等!

在此更新感兴趣的人:我一直在寻找一种无需使用 API 即可获取 Disqus 最新评论的方法,并且找到了!这很简单!您只需转到您的 Disqus 网站的 RSS Feed。如果您的短名称是“example”,您只需转到 _http://example.disqus.com/latest.rss_ 即可获得最新评论列表,显然按日期/时间排序,最新的排在最前面!

请记住,在部署使用 Disqus 的应用程序时,您必须删除 disqus_developer 变量,以免 Disqus 将您的实时应用程序环境识别为开发环境。

历史

  • 初始版本发布。
  • 更新了“兴趣点”部分。
© . All rights reserved.