转载自http://www.ibm.com/developerworks/cn/websphere/library/techarticles/0508_hepper/0508_hepper.html
从 Web 开发的观点来看,最理想的网站应该允许内容提供者和管理员在向访问者提供内容时无需考虑内容的提供方式。事实上,最理想的内容和应用程序提供方式应该是以最方便最可行的方式自动向站点访问者提供信息。不过,到目前为止,由于考虑到大容量、高性能的网站的性能和可伸缩性,故而有必要将静态内容和动态应用程序区分开来。这两个术语的含义如下:
目前的网站使用不同的技术提供静态内容和动态应用程序。这种异构的方法增加了提供多种类型内容的网站的复杂性。不过,通过使用 IBM WebSphere Portal,可以将这两种类型的内容组合在一个门户中,使得网站管理更为简单。WebSphere Portal V5.1 大幅度提高了静态内容的提供流程,能以最高效的方式提供所有类型的内容。通过将 WebSphere Portal 作为提供动态应用程序和静态内容的公共机制,能通过门户维护的链接将静态页与动态页进行链接,从而实现一致的交叉引用。
将静态内容和动态应用程序结合,还大幅度提高了网站的价值,特别在向访问者呈现无缝集成的用户界面而使用户不会觉察到内容类型的差别时,这一点尤为突出。
让我们来看一个高级示例,以演示此类无缝集成:访问 IBM Internet 网站的访问者可以通过集成的站点搜索引擎查询“WebSphere Portal”,从而得到关于此产品的信息资源列表。访问者可以通过结果集中找到的链接阅读产品文档。访问者也可以找到 WebSphere Portal 目录,然后可以再搜索用于与其后端系统集成的 Portlet 的目录。从这里我们就可以看出动态应用程序(本例中为 IBM 网站搜索和目录)与静态内容(产品文档页)可以如何结合以供站点访问者使用。
WebSphere Portal 中的缓存技术
门户站点集中了多个独立组件(称为 Portlet)提供的内容和应用程序,这些 Portlet 都是独立开发的 Web 应用程序,在门户容器中执行。Portlet 可以维护状态。门户服务器协调多个 Portlet 的执行与标记聚合。WebSphere Portal 能提供灵活的缓存功能,从而提高同时提供静态内容和动态应用程序的网站的性能和可伸缩性。WebSphere Portal 通过组件状态优化缓存使用与利用。门户将组件响应存储在作用域设置为组件状态的缓存中。应用程序响应和静态内容的有效生存期和作用域可能有所不同,与静态内容页相比,通常应用程序的生存期较短,作用域也较小。
WebSphere Portal 在多个级别上使用缓存。通过使用 WebSphere Portal 的组合缓存技术(如自适应页面缓存、Portlet 缓存以及对象缓存),可以提高同时包含静态部分和动态部分的网站的性能和可伸缩性。
在缓存命中的情况下使用这些不同的缓存技术获得的性能提高与出现缓存命中的可能性之间存在一个折衷关系。通过使用自适应页面缓存将门户页标记全部缓存,可以在每次缓存命中的情况下获得最佳性能提高,但只有在请求的页面与缓存的响应完全相同的情况下才会出现缓存命中。页面要完全相同,则需要构成该页的组件生成的所有标记片段都完全相同。
将整个页分解为组件片段可以提高缓存命中的几率。利用 Portlet 缓存,门户会在响应请求前将缓存的 Portlet 片段聚合为完整的页。这种情况下,只需要所请求的 Portlet 片段与已存储的响应完全相同即可,而这提高了缓存命中的可能性,但并不能在每次缓存命中时提供同样的性能提高(仍然需要在门户上进行聚合)。对象缓存可以达到最高的缓存命中率;只要后端没有更改数据,存储在缓存中的此数据就有效。这种情况下,Portlet 根据缓存的数据呈现标记片段,而门户将标记聚合为完整的门户页。
静态内容和动态应用程序的内容生存期和作用域的差别也可以通过使用异构系统基础设施得到缓和,在异构基础设施中,静态内容和应用程序寄宿于独立的环境中;静态内容由 HTTP 服务器或内容管理系统提供,而应用程序则寄宿在应用服务器或门户服务器环境中。用户体验向最终用户隐藏了一个事实,即实际上不同的两个站点在同时运行。应用程序和静态内容交叉链接,使站点访问者能够在两个内容集间无缝地转换。此方法的缺点在于明显地增加了复杂性和维护工作。
本文将介绍一个在 WebSphere Portal 进行缓存的示例使用场景,并提供关于 WebSphere Portal 缓存架构的详细信息以及在 Portlet 和门户站点内利用这些功能的可能方式。
回页首
示例场景
我们的示例场景涉及到一个内部网门户站点,该站点同时提供静态内容和动态应用程序。让我们了解一下此门户站点如何为提高性能和可伸缩性进行了优化,以及它是如何使用 WebSphere Portal V5.1 中的缓存功能的。
该门户站点由两个主要区域组成,这两个区域的内容类型也不同:
以下部分描述为了最高效率地使用缓存机制而应用于这两个区域的设计原则。
News:静态内容
我们的门户站点的 News 区域包含具有 Portlet 的页面,这些 Portlet 提供来自内容管理系统的静态内容。门户的此区域的行为和静态网站的行为相似,但却向员工提供与他们的协作应用程序集成的单一环境。门户的此区域的所有页面均提供给内部网门户的所有用户;用户并不个性化这些页面,而且这些页面上内容对于每个人都是相同的,而这正是静态网站的典型特征。这些站点内容的更改频率也不相同,Tech 页面的新闻文章每分钟都在变,而 Products 页面的内容仅在每天早上更新。
内容 Portlet 提供不同的视图。例如,某些 Portlet 显示带链接的最新文章列表,如果用户单击了这些链接中的某一个,将在同一个 Portlet 中的同一页面上显示相应的文章,或在特殊的文章显示 Portlet 中显示此文章。
这些页面中的每一个都包含导航区域,用于供用户在 Portlet 内导航。此导航区域对于所有用户都是一样的。所有用户都可以共享来自缓存中的这些页面的标记。
MyWork 区域内可用页面集对于每个用户都是不同的,因此这些页的导航不应该包含在可缓存的页面中。在我们的门户站点中,是通过以下方法实现的:为门户的 News 区域内所有页面提供直接导航,而不为 MyWork 区域内的页面提供直接导航。要访问门户的 MyWork 区域中的页面,用户首先导航到 MyWork 主页面(News 区域内的所有页面都可以直接访问此页面),然后在 MyWork 区域内直接一页一页地导航。
WebSphere Portal V5.1 允许将这些页置入缓存代理中。缓存代理位于浏览器和服务器之间。代理接收来自浏览器的请求,并代表这些客户机从服务器请求内容。代理是缓存服务器响应的代理。对于后续的请求,缓存代理会直接从其缓存中将匹配的响应发送回客户机。通过使用缓存代理,每个页面都只需从门户交付一次,然后此页面将驻留在缓存中(直到内容无效时为止)。在内容的生存期内,对同一页面的后续请求都将由缓存代理直接响应,因而不会在门户服务器上生成工作负载。
MyWork:动态应用程序
该门户站点的 MyWork 区域包含供员工在日常事务中进行协作的一些 Portlet。门户的此区域针对动态应用程序进行了优化。始终为特定的用户请求生成门户页面,以确保门户能向当前用户提供最新的应用程序数据。
在示例场景中,一些协作应用程序提供给全体员工,而另一些协作应用程序仅提供给公司内某些选定的组。MyWork 区域内的导航链接应只向用户提供其得到授权可以访问的导航链接;如果用户对某页没有访问权限,该页将不会出现在导航中。门户为每个用户单独生成导航,以反映用户的权限。
WebSphere Portal 用户可通过添加 Portlet、删除 Portlet 或重新排列页面上的现有 Portlet来对 MyWork 区域内的页面进行个性化设计,以使门户适应他们最高效的工作方式。
MyWork 区域中的页面不由多个用户共享。如果将这些页面缓存在多个用户共享的页面响应缓存中,则可能会很快用完缓存内存,却不能提高缓存命中率。将作用域设置为私有的页面存储在浏览器缓存中能达到对缓存的最佳内存利用,同时其位置也尽可能地接近最终用户。
页面结构或页面内容会随每个用户请求而变化,因而不能使用页面缓存来存储页面响应。需要使用更为先进的缓存技术以提高页面性能和降低系统使用率。在动态更改的页面中,通常并非所有的 Portlet 片段都会随每次请求而更改;某些 Portlet 片段在响应多个页面请求期间都不会变化,因此可以为一个用户或多个用户的请求缓存。Portlet 内的标记片段从该 Portlet 维护的数据中生成。其中的部分数据可能每次请求都会更改,因而要为每个请求交付不同的片段;而其他数据部分则可能在一系列始终交付相同标记的请求期间不会更改。根据其更改特征设计数据结构,可以对跨多个请求或多个用户保持为常数的数据元素进行标识。可以使用数据缓存对那些更改频率低于页面请求频率的数据进行缓存。
WebSphere Portal 提供了内置缓存,Portlet 可以使用其提供缓存 Portlet 标记的 Portlet 缓存,从而改善 Portlet 片段请求的响应时间。如 JSR 168 规范中所定义(请参阅参考资料)的,在 Portlet 的描述符提供的缓存过期配置为每个 Portlet 定义 Portlet 缓存行为。WebSphere Portal 中运行的 Portlet 可以使用对象缓存来缓存这样一些数据对象,此类对象为单个用户的多个页面请求所共享,或为不同的用户执行的页面请求所共享。
回页首
WebSphere Portal 中的缓存架构
这里,我们将讨论 WebSphere Portal V5.1 中的扩展缓存架构。图 2 描述了在请求从用户的浏览器传到后端系统期间,WebSphere Portal 不同级别上的缓存功能。此基础设施的定义符合 HTTP 规范中缓存基础设施的定义(请参阅参考资料),此处将以一个简化的模型进行说明。
从浏览器发出请求(从图 2 左边开始):
自适应页面缓存
在传统的观念中,通常对于应用服务器有一种假设,认为不可能在应用服务器外缓存动态生成的页面。另外,传统上还认为永远不能使用可能的代理服务器或浏览器缓存形式的现有缓存基础设施。在此传统的方法中,每个传入请求每次都需要应用服务器资源计算合适的响应。
使用 IBM 的自适应页面缓存专利技术,WebSphere Portal 突破了这些限制,提供了在称为远程缓存的位置中缓存动态生成的页面的机会,前提是组成页面的所有组件都发出信号,指示其为可缓存的内容。此方法的优点很快变得明显起来:对于此类可缓存的页面,第一次生成该页后就无需再往返于门户服务器了。如果能从缓存提供大量访问的页面,则整个门户基础设施的性能将大幅度提高。或多或少包含静态内容的图像页面,或仅显示 Portlet 已知的不同视图的页面,均可通过一个具体的 URL 进行寻址。(后一种情况可以通过提供其不同视图的呈现链接实现;请参阅上文。)
WebSphere Portal 可以通过与页面相关的 URL 引用页面的完整视图;在 WebSphere Portal 中,此功能是通过将导航状态编码到 URL 中实现的。利用此功能,也可以通过 URL 从缓存中访问已缓存的页面。如果曾用于生成特定页面的标记的某个门户资源的服务器端状态发生更改,需要重新生成此页面,因而缓存的视图会变为无效。因此需要告知缓存已呈现的页面视图保留的有效时间。Portlet 需要将这类缓存信息作为 Portlet 呈现的页面的整体缓存信息一部分进行发布。其上具有此类 Portlet 的页面可能是存储并从缓存中提供的好候选对象。
不过,这一优点并非不受到任何限制。由 WebSphere Portal 维护的资源需要得到适当的管理。对于构成页面的某些组件,需要提供额外的信息,以便充分地利用此项技术。
远程缓存
在本文中,远程缓存一词指位于 WebSphere Portal JVM 进程之外的缓存,也有可能位于运行 WebSphere Portal 的计算机之外的位置。远程缓存可以为请求 URL 缓存全部的响应。访问缓存中的这些项的唯一方法就是请求 URL。因此,可能可以在缓存中找到已生成页面的完全呈现标记。
一般而言,WebSphere Portal 允许使用任何符合 HTTP 1.1 缓存功能规范(请参阅参考资料)的任何实现,以更好地利用缓存基础设施。HTTP 1.1 规范仅通过使用特定的 HTTP 请求类型即可使缓存项失效(在本文中,这与远程缓存等效)。由于 WebSphere Portal 无需完全了解其所在的远程缓存基础设施,因而它不能使用此方法使单个缓存项失效。WebSphere Portal 为远程缓存所使用的唯一失效机制是过期超时。
需要区分由 HTTP 1.1 规范最初引入的两种远程缓存概念:
只有在可以计算附加的缓存信息(此信息随 WebSphere Portal 服务器响应一起发送)的情况下,这两种缓存才能成功地缓存页面。HTTP 1.1 规范定义了此类响应标头,并说明了如何处理特定的缓存项。
WebSphere Portal 以能最佳利用远程缓存上可能可用的缓存功能的方式在其生成的响应中提供此信息。自然地,在这些响应标头中需要以下两个项,以通知缓存如何对生成的响应标记进行处理:
WebSphere Portal 将根据远程缓存中进行的缓存而为其响应设置以下相关的 HTTP 1.1 标头:
Cache-Control:public
Cache-Control:private
Cache-Control:no-cache
Cache-Control:max-age delta-seconds
(如果对这些响应标头提供的值没有疑问,则可以使用某个工具使其变为可视,此工具可以作为一个代理,位于 WebSphere Portal 基础设施和浏览器之间,也可以作为浏览器的插件实现。详细信息请参阅参考资料。)
缓存信息的提供者
WebSphere Portal 如何确定呈现的页面是否可以实际缓存在远程缓存中?哪些数据是进行这样计算的必需数据?
为了进行此缓存,WebSphere Portal 将访问完全呈现页面所需的全部必要组件,并对这些组件可以提供的信息进行聚合。这也意味着,如果要最佳地实现此类页面的缓存功能,每个组件都必须提供关于其自身的缓存信息。另外,WebSphere Portal 维护了全局最大值以限制缓存值;例如,最大缓存过期时间,或完全关闭远程缓存中的缓存的时间。
因此,管理员必须在其门户设置中提供此信息,而 Portlet 开发人员也可以向要实现的 Portlet 的部署描述符和代码中添加信息。如果组件不提供任何此类信息,WebSphere Portal 将依赖于每个组件的全局缺省值。全局缺省值的设置与算法将在下文中予以说明。
表 1 提供了关于提供者及其提供的数据(供在远程缓存中进行缓存时使用)的概述。需要使用此数据计算总体缓存信息。
表 1. 缓存信息的提供者
门户资源 | 缓存作用域(共享或非共享) | 缓存过期时间(以秒为单位) | 忽略缓存中的访问控制(True 或 False) |
门户(全局设置) | X | X | |
门户页面 | X | X | X |
Theme | X | X | |
Portlet 定义 | X | X | |
Portlet 窗口 | X | X |
如表中所列出的,缓存信息的提供者为:
引入了忽略缓存中的访问控制设置以确保如果页面上发布的信息为安全敏感信息,则不会在缓存中存储此页面。如果完全呈现的页面存储在共享缓存中,则那些不具有该页面访问权限的用户仍然可能猜测出此类页面的 URL,从而从缓存中加载其内容。远程共享缓存通常不提供任何缺省安全机制。如果真的需要考虑这样的环境,必须将此设置为 False,以保证不会在远程共享缓存中对此类敏感页面进行缓存,从而确保无法通过猜测 URL 访问此类页面包含的信息。
Portlet 窗口可以在呈现时为远程缓存提供信息,因为它们可以根据自身的内部知识执行一些计算,从而可以动态地发布此信息。利用此 WebSphere Portal 功能,可以使用不同选项缓存单个 Portlet 的多个视图。Portlet 窗口本身可以在呈现时确定其输出是否可以缓存,以及应在何种缓存作用域下进行缓存。
如果某个 Portlet 窗口在呈现时不发布任何此类信息,WebSphere Portal 将转向 Portlet 定义或(如果 Portlet 定义没有提供)全局缺省值提供的缓存相关信息。
出于性能方面的原因,在 JSR 168 容器中引入了一个附加(冗余)设置,该设置告知容器在呈现时 Portlet 是否将提供远程缓存信息。WebSphere Portal 可以通过部署描述符使用此信息,因此可以减少计算工作。
对于遗留 Portlet,WebSphere Portal 将使用全局缺省值。遗留 Portlet 既不通过部署描述符提供缓存信息,也在不呈现时提供远程缓存信息。
对于未经身份验证的页面,WebSphere Portal V5.1 将保持与较早版本的兼容性,在早期版本中,这些页面都是可以缓存的,只由全局工作参数进行管理。
缓存信息的计算
构成页面的每个组件为远程缓存提供的所有缓存信息都需要进行聚合,将其合并为呈现页面的两个总体值:缓存作用域和缓存过期时间。WebSphere Portal 会将这些值附加到考虑缓存的门户响应中。请记住,由于 HTTP 1.1 规范的要求,在一次响应中,WebSphere Portal 只能为此目的附加所选 HTTP 标头的一个值集。
计算过程通常就是对缓存作用域和缓存过期时间均使用最小值,以确保以下事项:
很容易确定若干个过期值中的最小值,而两个可能的缓存作用域最小值却不是那么明显。
由于“非共享”的缓存作用域值比“共享”的缓存作用域值限制更多,所以采用与小过期时间比较大过期时间限制更多的类似方法得出结论,确定“非共享”的值要比“共享”的值小一些。
对于 Portlet,有一种特殊的机制应用于提供的每个缓存过期值和缓存作用域值。Portlet 窗口提供的值始终优先于 Portlet 定义提供的值。这意味着不管 Portlet 窗口的值高于或低于 Portlet 定义的值,将始终使用此值(如果提供的话)。如果 Portlet 窗口没有为缓存过期或缓存作用域提供值,则会将 Portlet 定义中的值作为该 Portlet 的提供值。
(下一部分将讨论在组件未提供值的情况下的缺省行为。)
如果将某个门户页面的忽略缓存中的访问控制设置为 False,将不能对完全呈现的页面进行缓存。为了确保不在远程缓存中缓存门户页面,需要将该门户页面的缓存过期值或全局范围内的对应值设置为 0。
全局缺省值与全局最大值 WebSphere Portal V5.1 还引入了缓存的全局缺省值和最大值,这使得 WebSphere Portal 有能力在组成呈现页面的组件没有发布缓存信息的情况下提供可缓存的页面。
全局缺省值和最大值是通过对属性文件中提供的设置(请参阅 How WebSphere Portal contributes global values of cache information)和确定请求是否经过了身份验证的结果进行计算得到的;后者是一个瞬时值,在文件或数据库中没有持久表达形式。
全局最大值提供到呈现的页面的总体缓存信息中。它具有和其他缓存信息提供者(如 Portlet、Portal 页面和 Theme)同样的权限。
只要 Porlet、门户页面或 Theme 未提供任何缓存信息,就将使用全局缺省值。
Portlet 缓存
通过使用自适应页面缓存方法,可以将完整页面缓存在远程缓存中。不过,完整的页面通常由许多 Portlet 的聚合组成。每个 Portlet 都会产生一个标记片段,此标记片段在页面上和其他 Portlet 的片段进行组合,就形成该页面的最终标记。然而,Portlet 所产生的单个标记片段也可能可以缓存。在这一部分中,我们将说明 WebSphere Portal 如何利用片段缓存来缓存单个 Portlet 片段(请参阅Portlet 缓存示例应用程序)。
片段缓存支持两种主要的缓存实例:对象缓存实例和 Servlet 缓存实例。
对象缓存提供 Java™ API 以缓存任意的 Java 对象(请参阅对象缓存与状态处理),而 Servlet 缓存功能则缓存 Servlet 请求发送程序所包含的输出。Portlet 由 Portlet 容器通过请求发送程序调用,因此,由于 Portlet 的标记是 Servlet 的标记,故而适合对其进行缓存。由于 Portlet 具有聚合特征,而 Porlet 标记又依赖于该 Portlet 的导航状态(不属于传递给请求发送程序的 URL),Portlet 容器在缓存此 Portlet 标记时需要执行额外的步骤:
然而,片段缓存方法假定所缓存的标记独立于上下文;否则从前一个上下文中生成的缓存的标记就不能与当前上下文中的标记进行聚合。
WebSphere Portal 将确保专用标记片段将被缓存到包含独立于上下文的 URL 的片段缓存中。这一点是通过对缓存片段而不是非缓存片段应用不同的 URL 生成机制实现的。从缓存检索到的用以聚合到门户页面中的片段需要了解当前的页面上下文。WebSphere Portal 会对缓存的片段应用 URL 重新编写机制,以确保此片段中包含正确的聚合页面导航状态上下文。
通过在其 portlet.xml 描述符(请参阅Portlet 描述符示例),Portlet 可以广告它们能够在片段中缓存。要使用片段缓存功能,需要在 WebSphere Application Server 管理控制台的 Web Container 区域激活 Servlet 缓存(请参阅 Portlet 描述符示例)。WebSphere Application Server 还提供了一个缓存监视器企业应用程序 (CacheMonitor.ear),此应用程序在可视化片段缓存的内容方面非常有用。
对象缓存和状态处理
自适应页面缓存和 Portlet 缓存提供了强大的方法,用以通过避免可能很费时的 Portlet 标记生成过程来缩短呈现时间。高效使用 Portlet 编程模型(有关 JSR 168:Portlet 规范的信息,请参阅参考资料),并有效利用 WebSphere Portal 的状态处理概念,也可以大幅度减少仍然需要呈现标记的情况下生成标记所需的时间。
本部分将介绍这些状态处理概念,并说明如何将 WebSphere Application Server 提供的 DistributedMap 用于使会话保持较小,并同时改进响应时间和可伸缩性。还提供了一个示例应用程序,以演示这些概念的实际应用(请参见附录 E)。
状态处理
WebSphere Portal V5.1 增强了其 JSR 168 编程模式的实现,支持以下可供 Portlet 使用的状态类型:
甚至早在 Portlet 的设计阶段,就需要将 Portlet 管理的各个状态进行区分,并对其进行适当的编码,这一点非常重要。特别地,由于可能在不同导航的组合中访问同一个会话,因此应将导航状态和会话状态设计为彼此正交。如果用户使用“后退”按钮调用包含 Portlet 特定的状态的书签,或打开与原始窗口共享会话的新浏览器窗口,并在两个窗口中独立导航,通常会发生这种情况。
Portlet 所生成的每个链接都属于以下两种类别之一:
有关这些概念的应用程序示例,请参阅附录 E。
对象缓存
在标记生成期间或操作执行期间,经常有必要访问慢速后端或执行一些较为费时的计算。可以将此类操作的结果进行缓存,以使后续请求的执行速度更快。不过,Portlet 会话并非缓存此类信息的位置,因为 Portlet 会话基本上都是由不可重新创建的数据组成的。Portlet 容器(最终为应用服务器)将确保在群集环境中会话状态将跨节点故障保留,甚至能够在群集中复制。此管理需要使用资源。而且,不能在会话的生存期结束前自动丢弃会话中的缓存数据(而在低内存条件下需要释放内存)。
将会话状态与缓存的状态区分开很重要。Portlet 应该使用缓存(而不是会话)保存缓存的数据,以在节约系统资源的同时增强性能。来自导航状态、会话状态或后端状态的可以重新创建的所有数据都适于进行缓存。缓存与会话相比,其优点在于缓存中的数据可以由于低内存事件、超时等等原因而丢弃,而且缓存基础设施不需要像处理会话数据一样使用很多资源保证缓存数据的可用性。
WebSphere Application Server 利用 DistributedMap 提供了一种有效的方法,可供任何 Web 应用程序用于存储任意 Java 对象。DistributedMap 接口是用于动态缓存的简单接口,使用此接口,通过将引用存储到缓存中的对象,J2EE 应用程序和系统组件可以缓存和共享 Java 对象。DistributedMap 是由应用服务器管理的 J2EE 资源,可以通过 Java 命名和目录接口 (JNDI) 查询从 Web 应用程序进行访问。Portlet 应在其初始化阶段进行此查询,并应将缓存实例的引用作为 Portlet 的实例变量保留。可以在一个服务器上配置多个 DistributedMap 实例,其中每个实例都具有不同的 JNDI 名称和缓存特征。最重要的特征包括:缓存大小、缓存项的缺省超时值和共享策略。有关 DistributedMap 的管理和接口的更多信息,请参阅参考资料中的 WebSphere Application Server 信息中心。
必须对 Portlet 进行编码,以使其能够预期缓存未命中;即,不依赖于缓存信息可用这一假设。特别要注意,不能将缓存作为在 Portlet 的请求周期中的操作阶段和呈现阶段共享数据的手段。由于低内存条件和通过管理控制台进行了缓存大小的管理修改,因此可能将缓存配置(暂时)为完全不缓存数据。Portlet 特别需要做好在呈现阶段重新创建信息的准备(例如,通过访问后端)。从性能的观点来看,最好在呈现阶段尽可能多地进行所需的后端交互,因为同一页面上的其他 Portlet 可能会并行呈现。在理想的情况下,呈现页面的延迟为该页上所有 Portlet 延迟的最大值(如果所有 Portlet 顺序呈现的话,就为延迟的总和)。
使用 DistributedMap 时,Portlet 需要确保其在此缓存中使用的键不会与其他 Portlet 在同一个缓存中使用的键冲突。要确保这一点,可采用多种方法:
有关这些概念的应用程序示例,请参阅附录 E。
除了缓存数据外,DistributedMap 还允许显式地使各个键失效。映射的实例可以配置为共享,也可以配置为非共享。共享映射将试图同步保留群集中不同节点的映射实例的内容,而非共享缓存则包含特定于节点的数据。不过,对缓存进行失效操作却始终分布在整个群集中。出于性能考虑,最好将缓存配置为非共享,并显式地对缓存项进行失效操作。由于 Portlet 交互本身的特性,通常在操作阶段对缓存项进行失效操作,而缓存的访问和填充则通常在呈现阶段进行。
回页首
结束语
IBM WebSphere Portal V5.1 允许您从单个门户运行整个网站(包括动态应用程序和静态内容)。可以在您的门户内多个层次上使用缓存。新引入的自适应页面缓存概念支持对完整门户页面进行缓存。门户将自动确定哪些聚合页面可以缓存,并自动设置页面标头以将站点中的静态部分缓存到反向代理或浏览器中。初始访问后,就可以和常规静态网站一样的速度从缓存中提供这些页面了。通过为包括在页面中的组件标记片段指示恰当的生存期和缓存作用域,站点高度动态的部分将自动在页面中呈现。
对于部分动态的页面,WebSphere Portal 支持 Portlet 缓存,以便只对交互 Portlet 或显示实时内容的 Portlet 提供的页面动态部分按请求进行呈现,而 Portlet 所呈现的、具有一定有效时间的静态或半静态部分将从 Portlet 缓存中获取(直到过期为止)。
在实现交互应用程序(必须按请求呈现)的 Portlet 内,可以使用对象缓存优化单个呈现操作的性能。
自适应页面缓存、Portlet 缓存及对象缓存,通过与各种在 WebSphere Portal 代码库中实现的内部性能增强功能配合使用,允许您在 WebSphere Portal 5.1 上运行整个高性能网站。与采用以门户产品为核心并辅以采用不同管理方式的常规 Web 服务器的混合方法相比,此方法可降低总体拥有成本,并同时提供更好的可管理性。
回页首
附录
以下的附录部分提供更为详细的技术细节,描述每种受影响的组件提供与远程缓存相关的信息的方式。也可以使用此信息作为管理员或 Portlet 开发人员需要完成的事项的清单使用,以在 WebSphere Portal 中允许一组页面在远程缓存中进行缓存。
回页首
附录 A:提供远程缓存值的组件
门户页面如何提供缓存信息
缓存作用域和缓存过期时间值以及“忽略缓存中的访问控制”设置均可在 WebSphere Portal 图形用户界面中通过门户页面的编辑页面属性管理功能进行设置。也可以通过 XML 访问脚本设置这些值,如清单 1 所示:
|
参数名称 remote-cache-scope、remote-cache-expiry 和 IgnoreAccessControlInCaches 均为用于提供此信息的保留字。
Theme 如何提供缓存信息
缓存作用域和缓存过期时间值不能在 WebSphere Portal 的 Theme 图形界面中设置。可以通过 XML 访问脚本设置这些值,如清单 2 所示:
|
参数 remote-cache-scope 和 remote-cache-expiry 是用于提供此信息的保留字。
Portlet 定义如何提供缓存信息
Portlet 定义将通过其部署描述符提供缓存信息。仅支持符合 JSR 168 规范的标准 Portlet 发布此信息。对于 IBM 遗留 Portlet,WebSphere Portal 将假设全局缺省值对于未经身份验证的页面仍然有用。
清单 3 显示了一个发布缓存信息的标准 Portlet 的部署描述符 (portlet.xml):
|
在上例中,假设给定了一个
此处仍然缺少缓存作用域值 (
由于在 JSR 168 规范中定义了此部署描述符,所以 WebSphere Portal 使用此部署描述符的一个扩展发布缺少的值 (ibm-portlet-portal-ext.xmi)。例如:
|
Portlet 窗口如何提供缓存信息
Portlet 窗口可以在呈现时发布缓存信息。这意味着 WebSphere Portal 将引入或扩展现有的 Portlet 编程接口,此接口可以在呈现时确定要为缓存作用域和缓存过期时间发布哪个提供值。
JSR 168 规范定义了一个通用缓存过期时间值,Portlet 可以在呈现期间随时自行进行设置。由于没有必要区分内部缓存过期值和远程缓存过期值,WebSphere Portal 也将此值作为该 Portlet 窗口用于远程缓存的提供值使用。
清单 5 显示了在呈现时发布缓存过期时间和缓存作用域的标准 Portlet 的片段:
. . . import com.ibm.wps.util.RemoteCacheInfo; import javax.portlet.RenderResponse; . . . /* Do rendering */ public void doView(RenderRequest renderRequest, RenderResponse renderResponse) throws PortletException, IOException { /* Some code might happen here */ . . . /* Publish an expiration time of 200 seconds during rendering */ renderResponse.setProperty( RenderResponse.EXPIRATION_CACHE, "200" ); /* Publish a cache scope value of "shared" during rendering *) renderResponse.setProperty( RemoteCacheInfo.KEY_SCOPE, RemoteCacheInfo.Scope.SHARED_STRING ); /* Some other code might happen here */ . . . } |
由于 JSR 168 规范中未定义缓存作用域,因此 WebSphere Portal 将提供一个名为 RemoteCacheInfo 的接口,此接口提供键和值的静态字符串,用以设置呈现响应中的缓存作用域信息(如上例所示)。也可以选择直接使用以下字符串:
portlet.remote-cache-scope
SHARED
或 NON_SHARED
WebSphere Portal 如何提供缓存信息的全局值
WebSphere Portal 中有三个影响与远程缓存中的缓存相关的全局值的全局设置:
在属性文件 NavigatorService.properties 中可以找到上述的所有属性,此文件位于以下目录中:
另一个可能提供总体缓存信息的属性就是请求是否为未经身份验证的请求。此信息布保留在文件或数据库中,需要对传入的每个 WebShpere Portal 进行此项检查。
回页首
附录 B:远程缓存信息计算示例
作为一个例子,我们假设以设定了以下的门户页面和设置:
存在一个提供以下值的门户页面:
与此页面关联的 Theme 提供以下值:
在该门户页面上有两个 JSR 168 标准 Portlet。这两个 Portlet 都将 remote-cache-dynamic 的值设置为 True 以告知 Portlet 容器它们也将在呈现时提供远程缓存信息。
第一个 Portlet 的 Portlet 定义提供的值为:
第一个 Portlet 的 Portlet 窗口提供的值为:
第二个 Portlet 的 Portlet 定义提供的值为:
第二个 Portlet 的 Portlet 窗口也提供以下值:
门户通过 NavigatorService.properties 文件中的设置提供以下全局值:
对此页面的请求为:
步骤 1:计算全局值
在第一步中,WebSphere Portal 将计算全局缺省值和全局最大值,如全局默认值和全局最大值中的流程图所示。
此算法得到结果为:
在所给的示例,还得到以下的值:
请注意,全局缺省值和全局最大值并不一定相等。如表中所示,有时候两类值也会不同。
由于我们的所有相关提供者(门户页面、Theme 和 Portlet)都提供了自己的远程缓存信息,因此没有必要使用全局缺省值,也就没有必要进行进一步的计算。
步骤 2:计算远程缓存过期值
在第二步中,WebSphere Portal 将计算所有组件提供的信息的远程缓存过期最小值。
正如前面所提到的,对于 Portlet 有一个特殊的机制处理提供的缓存过期值。Portlet 窗口提供的缓存过期值始终优先于 Portlet 定义提供的值,而不会考虑二者的相对大小。如果 Portlet 窗口没有提供缓存过期值,则将使用 Portlet 定义中的值。在我们的示例中,则这将导致使用一个比第一个 Porlet 中指定的值更大的缓存过期值。
第一个 Portlet 的 Portlet 定义 | 15 秒 |
第一个 Portlet 的 Portlet 窗口 | 20 秒 |
第一个 Portlet 的结果值 | 20 秒 |
第二个 Portlet 的 Portlet 定义 | 100 秒 |
第二个 Portlet 的 Portlet 窗口 | 100 秒 |
第二个 Portlet 的结果值 | 100 秒 |
现在已经计算了所有提供值的最小值,如下所示。
门户页面 | 100 秒 |
Theme | 40 秒 |
全局最大值 | 50 秒 |
第一个 Portlet | 20 秒 |
第二个 Portlet | 100 秒 |
结果值 | 20 秒 |
步骤 3:计算远程缓存作用域
在第三步中,WebSphere Portal 将计算所有组件提供的信息的远程缓存作用域最小值。
对于缓存过期值,也有一个针对 Portlet 缓存作用域提供值的特殊机制。Portlet 窗口提供的缓存作用域始终优先于 Portlet 定义所提供的值,而不考虑二者的相对大小。如果 Portlet 窗口没有提供缓存作用域值,则将使用 Portlet 定义中的值。在我们的示例中,由于 Portlet 窗口的缓存作用域与 Portlet 定义的作用域相同,所有这个机制并没有得到明显体现。
第一个 Portlet 的 Portlet 定义 | SHARED |
第一个 Portlet 的 Portlet 窗口 | SHARED |
第一个 Portlet 的结果值 | SHARED |
第二个 Portlet 的 Portlet 定义 | NON_SHARED |
第二个 Portlet 的 Portlet 窗口 | NON_SHARED |
第二个 Portlet 的结果值 | NON_SHARED |
现在已经计算了所有提供值的最小值,如下所示。
Portal 页面 | SHARED |
Theme | SHARED |
全局最大值 | SHARED |
第一个 Portlet | SHARED |
第二个 Portlet | NON_SHARED |
结果值 | NON_SHARED |
WebSphere Portal 进行了所有的计算后,将把完全呈现的页面的相应的标头写回 HTTP 响应。在我们的示例中,这些标头可能为:
回页首
附录 C:远程缓存中的缓存检查单
当为自适应页面缓存修改了门户设置时,您可能希望开始分析系统,以了解门户产生意外响应的情况。此处给出排除故障时首选需要检查的项目:
如果没有按照预期的方式设置响应标头,则检查以下各项: