在花了几天时间阅读了无数博客文章、论坛主题,当然还有 SO 问题之后,我想在这里总结一下我们是如何最终成功地在 Liferay 6.2 集群中配置缓存复制的,使用单播 TCP 以适应 Amazon EC2。
JGroups 配置
在配置 Liferay 进行缓存复制之前,您必须了解 Liferay 依赖于 JGroups 通道。基本上,JGroups 允许发现远程实例并与之通信。默认情况下(至少在 Liferay 中)它利用多播 UDP 来实现这些目标。有关更多信息,请参见JGroups 网站。
要启用单播 TCP,您必须首先从jgroups.jar
Liferay webapp 中获取 JGroups 的 TCP 配置文件(类似于$LIFERAY_HOME/tomcat-7.0.42/webapps/ROOT/WEB-INF/lib/jgroups.jar
)。将此文件解压缩到 Liferay webapp 的类路径可用的位置。说$LIFERAY_HOME/tomcat-7.0.42/webapps/ROOT/WEB-INF/classes/custom_jgroups/tcp.xml
。记下这条路径。
为了让这个配置在 Liferay 集群中工作,你只需要在标签中添加一个singleton_name="liferay"
属性:TCP
<config xmlns="urn:org:jgroups"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="urn:org:jgroups http://www.jgroups.org/schema/JGroups-3.1.xsd">
<TCP singleton_name="liferay"
bind_port="7800"
loopback="false"
...
您可能已经注意到:
A. 这个配置文件没有指定监听的绑定地址,并且
B.集群的初始主机必须通过系统属性进行设置。
实际上,您需要修改$LIFERAY_HOME/tomcat-7.0.42/bin/setenv.sh
以添加以下JVM系统属性:
-Djava.net.preferIPv4Stack=true
-Djgroups.bind_addr=192.168.0.1
-Djgroups.tcpping.initial_hosts=192.168.0.1[7800],80.200.230.2[7800]
绑定地址定义了要监听的网络接口(JGroups 端口在 TCP 配置文件中设置为 7800)。初始 hosts 属性必须包含集群的每个实例(有关更多信息,请参阅JGroups 文档上的 TCPPING 和 MERGE2),以及它们的侦听端口。远程实例可以通过它们的主机名、本地地址或公共地址来引用。
(提示:如果您在 Amazon EC2 上设置 Liferay 集群,每次重启后实例的本地 IP 地址和主机名可能会不同。要解决此问题,您可以将 setenv.sh 中的本地地址替换为主机名命令的结果:`hostname`
——注意这里的反引号)
(提示:如果在 EC2 上使用安全组,还应确保对同一安全组中的所有实例开放 7800 端口)
Liferay 配置
通过将以下属性添加到您的 portal-ext.properties,在 Liferay 上启用 JGroups 复制:
# Tells Liferay to enable Cluster Link. This sets up JGroups control and transport channels (necessary for indexes and cache replication)
cluster.link.enabled=true
# This external address is used to determine which network interface must be used. This typically points to the database shared between the instances.
cluster.link.autodetect.address=shareddatabase.eu-west-1.rds.amazonaws.com:5432
为单播 TCP 配置 JGroups 只需指向正确的文件:
# Configures JGroups control channel for unicast TCP
cluster.link.channel.properties.control=/custom_jgroups/tcp.xml
# Configures JGroups transport channel for unicast TCP
cluster.link.channel.properties.transport.0=/custom_jgroups/tcp.xml
在同一个文件中,Lucene 索引复制需要这个单一属性:
# Enable Lucene indexes replication through Cluster Link
lucene.replicate.write=true
EhCache 缓存复制更加微妙。您必须为 Hibernate 缓存和 Liferay 的内部缓存配置 JGroups。要理解这个配置,你必须知道,从 Liferay 6.2 开始,默认的EhCache 配置文件是“集群的”(不要设置这些属性):
# Default hibernate cache configuration file
net.sf.ehcache.configurationResourceName=/ehcache/hibernate-clustered.xml
# Default internal cache configuration file
ehcache.multi.vm.config.location=/ehcache/liferay-multi-vm-clustered.xml
这些配置文件都依赖于必须设置启用 JGroups 的 EhCache 工厂:
# Enable EhCache caches replication through JGroups
ehcache.bootstrap.cache.loader.factory=com.liferay.portal.cache.ehcache.JGroupsBootstrapCacheLoaderFactory
ehcache.cache.event.listener.factory=net.sf.ehcache.distribution.jgroups.JGroupsCacheReplicatorFactory
ehcache.cache.manager.peer.provider.factory=net.sf.ehcache.distribution.jgroups.JGroupsCacheManagerPeerProviderFactory
JGroups 的缓存管理器对等提供者工厂需要一个file
包含 JGroups 配置的参数。指定单播 TCP 配置文件:
# Configure hibernate cache replication for unicast TCP
net.sf.ehcache.configurationResourceName.peerProviderProperties=file=/custom_jgroups/tcp.xml
# Configure internal caches replication for unicast TCP
ehcache.multi.vm.config.location.peerProviderProperties=file=/custom_jgroups/tcp.xml
(提示:如有疑问,请参阅属性定义和默认值:https ://docs.liferay.com/portal/6.2/propertiesdoc/portal.properties.html )
调试
此外,您可以启用调试跟踪:
cluster.executor.debug.enabled=true
你甚至可以告诉 Liferay 在每个页面上显示处理请求的节点的名称:
web.server.display.node=true
最后,JGroups 通道通过探测工具公开了一个可用的诊断服务。
最后说明
请记住,这仅涵盖索引和缓存复制。在设置 Liferay 集群时,您还应该考虑设置:
- 共享数据库(AWS 上的 RDS),
- 共享文档库(AWS 上的 S3 或 RDS),
- Tomcat 上的会话复制,
- 也许更多取决于你如何使用 Liferay。