本章介绍Hazelcast集群以及集群成员和本机客户端用于构成Hazelcast集群的方法。
5.1。发现机制
Hazelcast集群是运行Hazelcast的集群成员网络。集群成员(也称为节点)自动连接在一起以形成集群。这种自动连接使用集群成员用于查找彼此的各种发现机制进行。
请注意,在群集形成后,群集成员之间的通信始终通过TCP / IP进行,无论使用何种发现机制。
Hazelcast使用以下发现机制。
您可以参考Hazelcast IMDG部署和操作指南,获取有关要使用的最佳发现机制的建议。 |
5.1.1。TCP
您可以将Hazelcast配置为完整的TCP / IP群集。有关配置详细信息,请参阅“ 通过TCP发现成员”部分。
5.1.2。组播
不建议将生成多播机制用于生产,因为UDP通常在生产环境中被阻止,而其他发现机制更明确。
通过这种机制,Hazelcast允许集群成员使用多播通信找到彼此。请参阅“ 按组播发现成员”部分。
5.1.3。AWS Cloud Discovery
Hazelcast支持EC2自动发现。当您不想提供或无法提供可能的IP地址列表时,它非常有用。此发现功能作为Hazelcast插件提供。有关配置和使用它的信息,请参阅其文档。
5.1.4。Apachejclouds®CloudDiscovery
Hazelcast成员和本地客户支持jclouds®进行发现。此机制允许应用程序以与基础架构无关的方式部署在各种云基础架构生态系统中。此发现功能作为Hazelcast插件提供。有关配置和使用它的信息,请参阅其文档。
5.1.5。Azure Cloud Discovery
Hazelcast为在Azure上运行的Hazelcast应用程序提供了一种发现策略。此策略通过返回Azure资源组中标记有指定值的虚拟机来提供所有Hazelcast实例。此发现功能作为Hazelcast插件提供。有关配置和使用它的信息,请参阅其文档。
5.1.6。Zookeeper云发现
此发现机制通过使用Apache Curator与Zookeeper服务器进行通信来提供基于服务的发现策略。您可以在启用Discovery SPI的 Hazelcast 3.6.1及更高版本的应用程序中使用此插件。这是一个Hazelcast插件。有关配置和使用它的信息,请参阅其文档。
5.1.7。领事云发现
Consul是一个高度可用的分布式服务发现和键值存储,旨在支持现代数据中心,使分布式系统和配置变得简单。该机制为启用Hazelcast的应用程序(Hazelcast 3.6及更高版本)提供了基于Consul的发现策略,并使Hazelcast成员能够通过Consul动态发现彼此。此发现功能作为Hazelcast插件提供。有关配置和使用它的信息,请参阅其文档。
5.1.8。etcd Cloud Discovery
此机制为启用Hazelcast的应用程序(Hazelcast 3.6及更高版本)提供基于etcd的发现策略。这是一个易于配置的即插即用Hazelcast发现策略,可以选择使用etcd注册每个Hazelcast成员,并使Hazelcast成员能够通过etcd动态发现彼此。此发现功能作为Hazelcast插件提供。有关配置和使用它的信息,请参阅其文档。
5.1.9。用于PCF的Hazelcast
使用可点击的Hazelcast Tile进行Pivotal Cloud Foundry(PCF),您可以在PCF上部署Hazelcast群集。此功能以Hazelcast插件的形式提供。请参阅其文档,了解如何安装,配置和使用插件Hazelcast for PCF。
5.1.10。Hazelcast OpenShift集成
Hazelcast可以在OpenShift内部运行,受益于其集群管理软件Kubernetes,用于发现成员。使用Hazelcast Docker映像,模板和默认配置文件,您可以将Hazelcast IMDG,Hazelcast IMDG Enterprise和管理中心部署到OpenShift上。请参阅文档:
另请参阅Hazelcast for OpenShift指南,其中介绍了如何设置本地OpenShift环境,启动Hazelcast集群,配置管理中心以及最终运行示例客户端应用程序。
5.1.11。Eureka Cloud Discovery
Eureka是一种基于REST的服务,主要用于AWS云,用于定位服务,以实现中间层服务器的负载平衡和故障转移。Hazelcast支持Eureka V1发现; EC2虚拟私有云中的Hazelcast成员可以使用此机制发现彼此。此发现功能作为Hazelcast插件提供。请参阅其文档。
5.1.12。Heroku Cloud Discovery
Heroku是一种平台即服务(PaaS),您可以使用它完全在云中构建,运行和运行应用程序。它是一个基于托管容器系统的云平台,具有集成的数据服务和强大的生态系统。Hazelcast提供了一个发现插件,通过在Heroku Private Spaces中针对Heroku DNS Discovery解析服务名称来查找其他成员的IP地址。此发现功能作为Hazelcast插件提供。请参阅其文档。
5.1.13。Kubernetes Cloud Discovery
Kubernetes是一个开源系统,用于自动化容器化应用程序的部署,扩展和管理。Hazelcast提供Kubernetes发现机制,通过解析针对Kubernetes Service Discovery系统的请求来查找其他成员的IP地址。它支持两种不同的解析发现注册表的选项:(i)对REST API的请求,(ii)针对给定DNS服务名称的DNS查找。此发现功能作为Hazelcast插件提供。有关配置和使用它的信息,请参阅其文档。
5.2。通过TCP发现会员
如果多播不是您的环境的首选发现方式,则可以将Hazelcast配置为完整的TCP / IP群集。配置Hazelcast以通过TCP / IP发现成员时,必须将成员的主机名和/或IP地址的全部或部分列为集群成员。您不必列出所有这些集群成员,但是当新成员加入时,至少有一个列出的成员必须在集群中处于活动状态。
要将Hazelcast设置为完整的TCP / IP群集,请设置以下配置元素。有关TCP / IP发现配置元素的完整说明,请参阅tcp-ip元素部分。
以下是声明性配置示例。
...
...
...
...
...
如上所示,您可以为member元素提供IP地址或主机名。您还可以提供一系列IP地址,例如192.168.1.0-7。
如上所示,您还可以选择使用该members元素并编写以逗号分隔的IP地址,而不是按行提供成员,如下所示。
如果您不为成员提供端口,Hazelcast会自动尝试端口5701,5702等。
默认情况下,Hazelcast绑定到所有本地网络接口以接受传入流量。您可以使用系统属性更改此行为hazelcast.socket.bind.any。如果将此属性设置为false,Hazelcast将使用interfaces元素中指定的接口(请参阅“ 接口配置”部分)。如果没有提供接口,那么它将尝试解析一个接口以从member元素绑定。
5.3。通过Multicast发现会员
通过多播自动发现机制,Hazelcast允许集群成员使用多播通信找到彼此。集群成员不需要知道其他成员的具体地址,因为他们只是多播到所有其他成员进行监听。是否可以进行多播取决于您的环境。
要将Hazelcast设置为多播自动发现,请设置以下配置元素。有关多播发现配置元素的完整说明,请参阅多播元素部分。
以下是声明性配置示例。
...
...
注意multicast-timeout-seconds元素。multicast-timeout-seconds指定成员在声明自己为领导成员(加入群集的第一个成员)并创建自己的群集之前,应等待来自网络中运行的另一个成员的有效多播响应的时间(以秒为单位)。这仅适用于尚未分配领导者的成员的启动。如果指定一个较高的值multicast-timeout-seconds,例如60秒,则表示在选择一个领导者之前,每个成员将等待60秒再继续前进。提供高价值时要小心。另外,注意不要将值设置得太低,否则成员可能会过早放弃并创建自己的集群。
Hazelcast本机客户端尚不支持多播自动发现。但是,我们为此提供了多播搜索插件。请参阅“ 发现本机客户端”部分。 |
5.4。发现本机客户端
Hazelcast成员和本机Java客户端可以通过多播发现插件找到彼此。该插件使用Hazelcast Discovery SPI实现。您应该在Hazelcast成员和Java客户端配置插件,以便使用多播发现。
要将群集配置为具有多播发现插件,请按照下列步骤操作:
以下是声明性配置示例。
...
....
...
以下是多播发现插件配置属性及其说明。
5.5。创建群集组
您可以创建群集组。为此,请使用group配置元素。
您可以通过指定组名以简单的方式分离群集。示例分组可以是开发,生产,测试,应用程序等。以下是声明性配置示例。
...
您还可以使用编程配置定义群集组。JVM可以托管多个Hazelcast实例。每个Hazelcast实例只能参与一个组。每个Hazelcast实例仅加入其自己的组,不与其他组交互。下面的代码示例创建三个单独Hazelcast instances-- h1属于production群集,而h2与h3属于development集群。
Config configProd = new Config();
configProd.getGroupConfig().setName( "production" );
Config configDev = new Config();
configDev.getGroupConfig().setName( "development" );
HazelcastInstance h1 = Hazelcast.newHazelcastInstance( configProd );
HazelcastInstance h2 = Hazelcast.newHazelcastInstance( configDev );
HazelcastInstance h3 = Hazelcast.newHazelcastInstance( configDev );
5.5.1。Hazelcast之前的群集组3.8.2
如果您的Hazelcast版本低于3.8.2,则还需要提供组密码和组名称。以下是使用密码元素的配置示例:
...
Config configProd = new Config();
configProd.getGroupConfig().setName( "production" ).setPassword( "prod-pass" );
Config configDev = new Config();
configDev.getGroupConfig().setName( "development" ).setPassword( "dev-pass" );
HazelcastInstance h1 = Hazelcast.newHazelcastInstance( configProd );
HazelcastInstance h2 = Hazelcast.newHazelcastInstance( configDev );
HazelcastInstance h3 = Hazelcast.newHazelcastInstance( configDev );
从3.8.2开始,不需要组密码。
5.6。会员用户代码部署 - BETA
Hazelcast可以从远程类库(通常包括lite成员)动态加载自定义类或域类。为此,Hazelcast提供了一个分布式动态类加载器。
使用此动态类加载器,您可以控制从其他成员加载的类的本地缓存,控制要提供给其他成员的类,以及创建类和包的黑名单或白名单。启用此功能后,您不必将类部署到所有集群成员。
以下是用户代码部署功能的简要工作机制:
5.6.1。配置用户代码部署
默认情况下不启用用户代码部署功能。您可以以声明方式或以编程方式配置此功能。以下是示例配置代码段:
声明性配置
程序化配置
Config config = new Config();
UserCodeDeploymentConfig distCLConfig = config.getUserCodeDeploymentConfig();
distCLConfig.setEnabled( true )
.setClassCacheMode( ClassCacheMode.ETERNAL )
.setProviderMode( ProviderMode.LOCAL_CLASSES_ONLY )
.setBlacklistedPrefixes( "com.foo" )
.setWhitelistedPrefixes( "com.bar.MyClass" )
.setProviderFilter( "HAS_ATTRIBUTE:lite" );
用户代码部署具有以下配置元素和属性:
5.6.2。过滤成员的示例
如上所述,配置元素provider-filter用于约束成员仅从所有集群成员的子集加载类。provider-filter必须将值设置为要从中加载类的所需成员中的成员属性。请参阅以下作为编程配置提供的示例用法。
以下示例配置将允许Hazelcast成员仅从具有class-provider属性集的成员加载类。它不会要求任何其他成员提供本地不可用的课程:
Config hazelcastConfig = new Config();
DistributedClassloadingConfig distributedClassloadingConfig = hazelcastConfig.getDistributedClassloadingConfig();
distributedClassloadingConfig.setProviderFilter("HAS_ATTRIBUTE:class-provider");
HazecastInstance instance = Hazelcast.newHazelcastInstance(hazelcastConfig);
以下示例配置设置class-provider成员的属性。因此,上面的成员将从具有以下属性的成员加载类class-provider:
Config hazelcastConfig = new Config();
MemberAttributeConfig memberAttributes = hazelcastConfig.getMemberAttributeConfig();
memberAttributes.setAttribute("class-provider", "true");
HazecastInstance instance = Hazelcast.newHazelcastInstance(hazelcastConfig);
5.7。客户端用户代码部署 - BETA
在以下情况下,您可以在客户端使用用户代码部署:
启用此功能后,客户端将这些类部署到成员。通过这种方式,当客户端添加新类时,成员将不需要重新启动以在类路径中包含新类。
您还可以使用客户端权限策略指定允许哪些客户端使用用户代码部署。请参阅权限。
5.7.1。配置客户端用户代码部署
默认情况下不启用客户端用户代码部署功能。您可以以声明方式或以编程方式配置此功能。以下是示例配置代码段:
声明性配置
在你的hazelcast-client.xml:
程序化配置
ClientConfig clientConfig = new ClientConfig();
ClientUserCodeDeploymentConfig clientUserCodeDeploymentConfig = new ClientUserCodeDeploymentConfig();
clientUserCodeDeploymentConfig.addJar("/User/sample/sample.jar");
clientUserCodeDeploymentConfig.addJar("https://com.sample.com/sample.jar");
clientUserCodeDeploymentConfig.addClass("sample.ClassName");
clientUserCodeDeploymentConfig.addClass("sample.ClassName2");
clientUserCodeDeploymentConfig.setEnabled(true);
clientConfig.setUserCodeDeploymentConfig(clientUserCodeDeploymentConfig);
重要的是要知道
请注意,还应在成员上启用用户代码部署以使用此功能。
Config config = new Config();
UserCodeDeploymentConfig userCodeDeploymentConfig = config.getUserCodeDeploymentConfig();
userCodeDeploymentConfig.setEnabled( true );
有关在成员端启用它及其配置属性的更多信息,请参阅“ 成员用户代码部署”部分。
对于属性class-cache-mode,客户端用户代码部署仅支持ETERNAL模式,无论在成员端设置的配置(可以是ETERNAL和OFF)。
对于属性,provider-mode,客户端用户代码部署仅支持LOCAL_AND_CACHED_CLASSES模式中,无论设定在部件侧(其可以是配置的LOCAL_AND_CACHED_CLASSES,LOCAL_CLASSES_ONLY和OFF)。
剩余的属性,它们是blacklist-prefixes,whitelist-prefixes和provider-filter在所述部件侧配置,将影响客户端用户代码部署的行为也是。例如,假设您com.foo在成员端提供黑名单前缀,该成员将丢弃具有com.foo客户端加载的前缀的类。
5.8。分区组配置
Hazelcast使用一致的散列算法将关键对象分配到分区中。为每个分区创建多个副本,并且这些分区副本在Hazelcast成员之间分发。条目存储在成员中,这些成员拥有分配了条目密钥的分区的副本。默认情况下,总分区数为271; 您可以使用配置属性更改它hazelcast.partition.count。请参阅系统属性附录。
拥有分区主副本的Hazelcast成员称为分区所有者。其他副本称为备份。根据配置,密钥对象可以保存在分区的多个副本中。成员最多只能拥有一个分区的副本(所有权或备份)。
默认情况下,假设群集中的所有成员都相同,Hazelcast会在群集成员之间随机分配分区副本。但是,如果某些成员共享相同的JVM或物理机器或机箱,并且您希望将这些成员的备份分配给另一台机器或机箱中的成员,该怎么办?如果某些成员的处理或内存容量不同并且您不希望将相同数量的分区分配给所有成员,该怎么办?
要处理此类方案,您可以对同一JVM(或物理机)中的成员或位于同一机箱中的成员进行分组。或者您可以将成员分组以创建相同的容量。我们称这些组为分区组。分区将分配给这些分区组而不是单个成员。由分区组拥有的分区的备份副本位于其他分区组中。
5.8.1。分组类型
启用分区分组时,Hazelcast为您配置分区组提供了以下选择。
1. HOST_AWARE:
您可以使用成员的IP地址自动对成员进行分组,因此共享同一网络接口的成员将组合在一起。同一主机上的所有成员(IP地址或域名)将是单个分区组。这有助于避免物理服务器崩溃时数据丢失,因为同一分区的多个副本不存储在同一主机上。但是,如果每个物理机器有多个网络接口或域名,则会使此假设无效。
以下是声明性和编程式配置片段,介绍如何启用HOST_AWARE分组。
Config config = ...;
PartitionGroupConfig partitionGroupConfig = config.getPartitionGroupConfig();
partitionGroupConfig.setEnabled( true )
.setGroupType( MemberGroupType.HOST_AWARE );
2. CUSTOM:
您可以使用Hazelcast的接口匹配配置进行自定义分组。这样,您可以向组添加不同的和多个接口。您还可以在接口地址中使用通配符。例如,用户可以使用自定义分区分组创建机架感知或数据仓库分区组。
以下是声明性和编程式配置示例,说明如何启用和使用CUSTOM分组。
<interface>10.10.0.*interface>
<interface>10.10.3.*interface>
<interface>10.10.5.*interface>
<interface>10.10.10.10-100interface>
<interface>10.10.1.*interface>
<interface>10.10.2.*interface>
Config config = ...;
PartitionGroupConfig partitionGroupConfig = config.getPartitionGroupConfig();
partitionGroupConfig.setEnabled( true )
.setGroupType( MemberGroupType.CUSTOM );
MemberGroupConfig memberGroupConfig = new MemberGroupConfig();
memberGroupConfig.addInterface( "10.10.0.*" )
.addInterface( "10.10.3.*" ).addInterface("10.10.5.*" );
MemberGroupConfig memberGroupConfig2 = new MemberGroupConfig();
memberGroupConfig2.addInterface( "10.10.10.10-100" )
.addInterface( "10.10.1.*").addInterface( "10.10.2.*" );
partitionGroupConfig.addMemberGroupConfig( memberGroupConfig );
partitionGroupConfig.addMemberGroupConfig( memberGroupConfig2 );
当您的群集正在形成时,如果您将成员配置为通过其IP地址发现彼此,则应使用该 |
3. PER_MEMBER:
您可以为每个成员提供自己的组。每个成员都是一个自己的组,主要和备份分区是随机分布的(不在同一个物理成员上)。这提供了最少量的保护,是Hazelcast群集的默认配置。当Hazelcast成员位于不同的主机上时,此分组类型可提供良好的冗余。但是,如果多个实例在同一主机上运行,则此类型不是一个好选择。
以下是声明性和编程式配置片段,说明如何启用PER_MEMBER分组。
Config config = ...;
PartitionGroupConfig partitionGroupConfig = config.getPartitionGroupConfig();
partitionGroupConfig.setEnabled( true )
.setGroupType( MemberGroupType.PER_MEMBER );
4. ZONE_AWARE:
您可以将ZONE_AWARE配置与Hazelcast AWS,Hazelcast jclouds或Hazelcast Azure Discovery Service插件配合使用。
作为发现服务,这些插件在发现过程中将区域信息放入Hazelcast 成员属性映射。当ZONE_AWARE配置为分区组类型时,Hazelcast会根据包含区域信息的成员属性映射条目创建分区组。这意味着在其他区域中创建备份,并且每个区域将被接受为一个分区组。
这是在Hazelcast成员启动期间由Discovery Service插件设置的受支持属性列表:
除了基于云提供商的区域信息之外,hazelcast-jclouds还提供机架或主机信息。在这种情况下,Hazelcast按给定顺序查找区域,机架和主机信息,并创建包含可用信息的分区组。 |
以下是声明性和编程式配置片段,显示如何启用ZONE_AWARE分组。
Config config = ...;
PartitionGroupConfig partitionGroupConfig = config.getPartitionGroupConfig();
partitionGroupConfig.setEnabled( true )
.setGroupType( MemberGroupType.ZONE_AWARE );
5. SPI:
您可以使用SPI配置提供自己的分区组实现。要创建分区组实现,您需要首先扩展DiscoveryStrategy发现服务插件的类,重写该方法public PartitionGroupStrategy getPartitionGroupStrategy(),然后PartitionGroupStrategy在该重写方法中返回配置。
以下是涵盖上段所述实施步骤的示例代码:
public class CustomDiscovery extends AbstractDiscoveryStrategy {
public CustomDiscovery(ILogger logger, Map
super(logger, properties);
}
@Override
public Iterable
Iterable
return iterable;
}
@Override
public PartitionGroupStrategy getPartitionGroupStrategy() {
return new CustomPartitionGroupStrategy();
}
private class CustomPartitionGroupStrategy implements PartitionGroupStrategy {
@Override
public Iterable
Iterable
return iterable;
}
}
}
5.9。记录配置
Hazelcast具有灵活的日志记录配置,并且不依赖于除JDK日志记录之外的任何日志记录框架。它具有用于许多日志记录框架的内置适配器,并且还通过提供日志记录接口来支持自定义记录器。
要使用内置适配器,请将hazelcast.logging.type属性设置为以下预定义类型之一。
您可以hazelcast.logging.type通过声明性配置,编程配置或JVM系统属性进行设置。
如果选择使用log4j,log4j2或slf4j,则应在类路径中包含正确的依赖项。 |
声明性配置
....
....
程序化配置
Config config = new Config() ;
config.setProperty( "hazelcast.logging.type", "log4j" );
系统属性
如果提供的日志记录机制不满意,您可以使用自定义日志记录功能实现自己的日志记录机制 要使用它,请实现com.hazelcast.logging.LoggerFactory和com.hazelcast.logging.ILogger接口并将系统属性设置hazelcast.logging.class为自定义LoggerFactory类名。
-Dhazelcast.logging.class=foo.bar.MyLoggingFactory
您还可以通过注册来收听Hazelcast运行时生成的日志记录事件LogListener`s to `LoggingService。
LogListener listener = new LogListener() {
public void log( LogEvent logEvent ) {
// do something
}
};
HazelcastInstance instance = Hazelcast.newHazelcastInstance();
LoggingService loggingService = instance.getLoggingService();
loggingService.addLogListener( Level.INFO, listener );
通过LoggingService,您可以获得当前使用的ILogger实现并记录您自己的消息。
如果您没有使用命令行来配置日志记录,则应该注意Hazelcast类。jdk在读取新配置的日志记录之前,它们可能默认为日志记录。选择日志记录机制时,它不会更改。 |
5.10。其他网络配置
在使用编程配置时,所有与网络相关的配置都通过networkHazelcast XML配置文件或类中的元素执行NetworkConfig。以下小节介绍了可以在network元素下执行的可用配置。
5.10.1。公开演讲
public-address覆盖成员的公共地址。默认情况下,成员选择其套接字地址作为其公共地址。但是在网络地址转换(NAT)之后,两个端点(成员)可能无法彼此查看/访问。如果两个成员都将其公共地址设置为NAT上定义的地址,那么他们可以相互通信。在这种情况下,它们的公共地址不是本地网络接口的地址,而是NAT定义的虚拟地址。当您拥有私有云时,可以选择设置和使用。请注意,此元素的值应以格式给出host IP address:port number。请参阅以下示例。
声明:
<public-address>11.22.33.44:5555public-address>
程序化:
Config config = new Config();
config.getNetworkConfig()
.setPublicAddress( "11.22.33.44:5555" );
5.10.2。港口
您可以指定Hazelcast将用于在集群成员之间进行通信的端口。它的默认值是5701。以下是示例配置。
声明:
程序化:
Config config = new Config();
config.getNetworkConfig().setPort( 5701 )
.setPortAutoIncrement( true ).setPortCount( 20 );
根据上面的例子,Hazelcast将尝试在5701和5720之间找到空闲端口。
port 具有以下属性。
5.10.3。出站端口
默认情况下,Hazelcast允许系统在套接字绑定操作期间选择一个短暂的端口。但是,安全策略/防火墙可能要求您限制启用Hazelcast的应用程序使用的出站端口。要满足此要求,您可以将Hazelcast配置为仅使用已定义的出站端口。以下是示例配置。
声明:
程序化:
...
NetworkConfig networkConfig = config.getNetworkConfig();
// ports between 35000 and 35100
networkConfig.addOutboundPortDefinition("35000-35100");
// comma separated ports
networkConfig.addOutboundPortDefinition("36001, 36002, 36003");
networkConfig.addOutboundPort(37000);
networkConfig.addOutboundPort(37001);
...
您可以使用端口范围和/或逗号分隔端口。 |
如编程配置中所示,您使用该方法addOutboundPort仅添加一个端口。如果需要添加一组端口,请使用该方法addOutboundPortDefinition。
在声明性配置中,该元素ports可用于单端口和多端口定义。当您将此元素设置为 0或时 *,您的操作系统(而不是Hazelcast)将从短暂范围中选择一个空闲端口。
5.10.4。重用地址
关闭集群成员时,服务器套接字端口将在TIME_WAIT接下来的几分钟内处于该状态。如果在关闭它之后立即启动该成员,则可能无法将其绑定到同一端口,因为它处于该TIME_WAIT状态。如果将reuse-address元素设置为true,TIME_WAIT则忽略状态,并且可以再次将成员绑定到同一端口。
以下是示例配置。
声明:
程序化:
...
NetworkConfig networkConfig = config.getNetworkConfig();
networkConfig.setReuseAddress( true );
...
5.10.5。加入
该join构造元件被用于发现Hazelcast构件,使它们能够形成群集。Hazelcast提供多播,TCP / IP,EC2和jclouds®发现机制。发现机制部分解释了这些机制。本节描述了元素的所有子元素和属性join。以下是示例配置。
声明:
<interface>192.168.1.102interface>
程序化:
Config config = new Config();
NetworkConfig network = config.getNetworkConfig();
JoinConfig join = network.getJoin();
join.getMulticastConfig().setEnabled( false )
.addTrustedInterface( "192.168.1.102" );
join.getTcpIpConfig().addMember( "10.45.67.32" ).addMember( "10.45.67.100" )
.setRequiredMember( "192.168.10.100" ).setEnabled( true );
该join元素具有以下子元素和属性。
多播元素
该multicast元素包括用于微调多播连接机制的参数。
tcp-ip元素
该tcp-ip元素包括微调TCP / IP连接机制的参数。
tcp-ipelement也接受interface参数。请参阅Interfaces元素说明。 |
aws元素
该aws元素包括允许成员在Amazon EC2环境中形成集群的参数。
如果您使用的是AWS以外的云提供程序,则可以使用编程配置来指定TCP / IP群集。需要从该提供者检索成员,例如jclouds。
发现战略要素
该discovery-strategies元素基于Hazelcast Discovery SPI配置内部或外部发现策略。有关详细信息,请参阅Discovery SPI部分和使用的发现策略的供应商文档。
5.10.6。AWSClient配置
要确保正确找到EC2实例,您可以使用AWSClient该类。它确定要连接的EC2实例的私有IP地址。为AWSClient类提供您在aws元素中指定的参数的值,如下所示。您将看到是否找到了您的EC2实例。
public static void main( String[] args )throws Exception{
AwsConfig config = new AwsConfig();
config.setSecretKey( ... ) ;
config.setSecretKey( ... );
config.setRegion( ... );
config.setSecurityGroupName( ... );
config.setTagKey( ... );
config.setTagValue( ... );
config.setEnabled( true );
AWSClient client = new AWSClient( config );
Collection
System.out.println( "addresses found:" + ipAddresses );
for ( String ip: ipAddresses ) {
System.out.println( ip );
}
}
5.10.7。接口
您可以指定Hazelcast应使用的网络接口。服务器通常具有多个网络接口,因此您可能希望列出有效的IP。范围字符('*'和' - ')可用于简化。例如,10.3.10。\ *是指10.3.10.0和10.3.10.255之间的IP。接口10.3.10.4-18是指10.3.10.4和10.3.10.18之间的IP(包括4和18)。如果启用了网络接口配置(默认情况下禁用),并且Hazelcast无法找到匹配的接口,则它将在控制台上打印消息,并且不会在该成员上启动。
以下是示例配置。
声明:
...
...
<interface>10.3.16.*interface>
<interface>10.3.10.4-18interface>
<interface>192.168.1.3interface>
...
程序化:
Config config = new Config();
NetworkConfig network = config.getNetworkConfig();
InterfacesConfig interfaceConfig = network.getInterfaces();
interfaceConfig.setEnabled( true )
.addInterface( "192.168.1.3" );
5.10.8。IPv6支持
Hazelcast无缝支持IPv6地址(默认情况下,此支持已关闭,请参阅本节末尾的注释)。
您所需要的只是在网络配置中定义IPv6地址或接口。唯一的当前限制是您无法在TCP / IP连接配置(tcp-ip元素)中定义通配符IPv6地址。接口配置没有此限制,可以采用与IPv4接口相同的方式配置通配符IPv6接口。
...
<interface>192.168.1.0-7interface>
<interface>192.168.1.*interface>
<interface>fe80:0:0:0:45c5:47ee:fe15:493ainterface>
tcp-ip>
<interface>10.3.16.*interface>
<interface>10.3.10.4-18interface>
<interface>fe80:0:0:0:45c5:47ee:fe15:*interface>
<interface>fe80::223:6cff:fe93:0-5555interface>
interfaces>
...
...
JVM有两个系统属性,用于设置首选协议堆栈(IPv4或IPv6)以及首选地址系列类型(inet4或inet6)。在双栈机器上,默认情况下首选IPv6堆栈,您可以通过java.net.preferIPv4Stack=
另请参阅Java中有关IPv6支持的其他详细信息。
默认情况下,IPv6支持已关闭,因为某些平台在使用IPv6堆栈时存在问题。亚马逊AWS等其他平台根本没有任何支持。要启用IPv6支持,只需将configuration属性设置hazelcast.prefer.ipv4.stack为false。有关详细信息,请参阅系统属性附录。 |
5.10.9。成员地址提供商SPI
此SPI不用于提供Hazelcast实例将与其构成群集的其他群集成员的地址。为此,请参阅上面的其他网络配置部分。 |
默认情况下,Hazelcast选择公共和绑定地址。您可以通过public-address在配置中定义a 或使用上面提到的其他属性来影响选择。但是,在某些情况下,这些属性还不够,默认地址选择策略将选择错误的地址。在使用Docker时在某些云环境(例如AWS)中部署Hazelcast时,或者在NAT后面部署实例且public-address属性不足时,可能会出现这种情况(请参阅公共地址部分)。
在这些情况下,可以以更高级的方式配置绑定和公共地址。您可以提供com.hazelcast.spi.MemberAddressProvider接口的实现,该接口将提供绑定和公共地址。然后,实现可以以任何方式选择这些地址 - 它可以从系统属性或文件读取,甚至可以调用Web服务来检索公共和私有地址。
实施细节在很大程度上取决于部署Hazelcast的环境。因此,我们将演示如何配置Hazelcast以使用简化的自定义成员地址提供程序SPI实现。下面显示了一个实现示例:
public static final class SimpleMemberAddressProvider implements MemberAddressProvider {
@Override
public InetSocketAddress getBindAddress() {
// determine the address using some configuration, calling an API, ...
return new InetSocketAddress(hostname, port);
}
@Override
public InetSocketAddress getPublicAddress() {
// determine the address using some configuration, calling an API, ...
return new InetSocketAddress(hostname, port);
}
}
请注意,如果绑定地址端口是,0那么它将使用Hazelcast网络配置中配置的端口(请参阅端口部分)。如果将公共地址端口设置为,0则它将广播与其绑定的相同端口。如果您希望绑定到任何本地接口,您可以new InetSocketAddress((InetAddress) null, port)从该getBindAddress()地址返回。
以下配置示例包含将提供给提供的类的构造函数的属性。如果您不提供任何属性,则该类可能具有no-arg构造函数或接受单个java.util.Properties实例的构造函数。另一方面,如果确实在配置中提供了属性,则该类必须具有接受单个java.util.Properties实例的构造函数。
声明:
<class-name>SimpleMemberAddressProviderclass-name>
程序化:
Config config = new Config();
MemberAddressProviderConfig memberAddressProviderConfig = config.getNetworkConfig().getMemberAddressProviderConfig();
memberAddressProviderConfig
.setEnabled(true)
.setClassName(MemberAddressProviderWithStaticProperties.class.getName());
Properties properties = memberAddressProviderConfig.getProperties();
properties.setProperty("prop1", "prop1-value");
properties.setProperty("prop2", "prop2-value");
config.getNetworkConfig().getJoin().getMulticastConfig().setEnabled(false);
// perform other configuration
Hazelcast.newHazelcastInstance(config);
5.11。故障检测器配置
故障检测器负责确定群集中的成员是否无法访问或崩溃。故障检测中最重要的问题是区分成员是否仍然活着但是缓慢或已经崩溃。但是根据着名的FLP结果,在异步系统中不可能区分崩溃成员和慢成员。解决此限制的方法是使用不可靠的故障检测器。不可靠的故障检测器允许成员怀疑其他人失败,通常基于活跃标准,但它可能在一定程度上犯错误。
Hazelcast有两个内置故障检测器; 截止故障检测器和Phi应计故障检测器。
从3.9.1开始,Hazelcast提供了另一种故障检测器Ping故障检测器,如果启用,它将与上述并行工作,但识别OSI第3层(网络层)上的故障。默认情况下禁用此检测器。
请注意,Hazelcast还为其Java客户端提供故障检测器。有关更多信息,请参阅客户端故障检测器部分。
5.11.1。截止日期故障检测器
截止日期故障检测器使用绝对超时来丢失/丢失心跳。超时后,会员被视为崩溃/不可用并标记为可疑。
截止日期故障检测器有两个配置属性:
要使用截止日期故障检测器配置属性hazelcast.heartbeat.failuredetector.type应设置为"deadline"。
[...]
[...]
[...]
Config config = ...;
config.setProperty("hazelcast.heartbeat.failuredetector.type", "deadline");
config.setProperty("hazelcast.heartbeat.interval.seconds", "5");
config.setProperty("hazelcast.max.no.heartbeat.seconds", "120");
[...]
Deadline Failure Detector是Hazelcast中的默认故障检测器。 |
5.11.2。Phi应计故障检测器
这是基于Hayashibara等人的Phi Accrual Failure Detector'的故障检测器。
Phi Accrual Failure Detector在滑动时间窗口中跟踪心跳之间的间隔,并测量这些样本的均值和方差,并计算怀疑水平(Phi)的值。当自上一次心跳变长以来的时间段内,phi的值将增加。如果网络变得缓慢或不可靠,则所得的均值和方差将增加,需要更长的时间段,在怀疑成员之前不会收到心跳。
hazelcast.heartbeat.interval.seconds 和hazelcast.max.no.heartbeat.seconds 属性仍将用作心跳消息的期间和心跳消息的截止时间。由于Phi Accrual Failure Detector适用于网络条件,hazelcast.max.no.heartbeat.seconds因此可以比Deadline Failure Detector的超时定义更低。
除上述两个属性外,Phi Accrual Failure Detector还有三个配置属性:
phi = 1意味着我们会犯错误的可能性10%。可能性1%与有phi = 2,0.1%有phi = 3等等有关。默认phi阈值为10。
要使用Phi Accrual Failure Detector,配置属性hazelcast.heartbeat.failuredetector.type应设置为"phi-accrual"。
[...]
[...]
[...]
Config config = ...;
config.setProperty("hazelcast.heartbeat.failuredetector.type", "phi-accrual");
config.setProperty("hazelcast.heartbeat.interval.seconds", "1");
config.setProperty("hazelcast.max.no.heartbeat.seconds", "60");
config.setProperty("hazelcast.heartbeat.phiaccrual.failuredetector.threshold", "10");
config.setProperty("hazelcast.heartbeat.phiaccrual.failuredetector.sample.size", "200");
config.setProperty("hazelcast.heartbeat.phiaccrual.failuredetector.min.std.dev.millis", "100");
[...]
5.11.3。Ping故障检测器
除了Deadline和Phi Accual Failure Detectors之一之外,还可以配置Ping故障检测器。它在OSI协议的第3层运行,并提供更快,更确定的硬件和其他低级事件检测。该检测器可以被配置为在成员被其他检测器之一怀疑之后执行额外检查,或者它可以并行工作,这是默认的。这样可以更快地检测到硬件和网络级问题。
该故障检测器基于InetAddress.isReachable()。当JVM进程具有足够的权限来创建RAW套接字时,实现将选择依赖于ICMP Echo请求。这是优选的。
如果没有足够的权限,则可以将其配置为在端口7上尝试TCP Echo时回退。在后一种情况下,成功连接或显式拒绝都将被视为“主机可访问”。或者,它可以被迫仅使用RAW套接字。这不是优选的,因为每次调用都会创建一个重量级的套接字,而且通常会禁用Echo服务。
要使Ping故障检测器仅依赖于ICMP Echo请求,需要满足一些标准。
要求和Linux / Unix配置
sudo setcap cap_net_raw=+ep
echo 0 > /proc/sys/net/ipv4/icmp_echo_ignore_all
如果不满足上述任何条件,那么isReachable将始终回退端口7上的TCP Echo尝试。
为了能够使用Ping故障检测器,请在Hazelcast声明性配置文件中添加以下属性:
[...]
[...]
[...]
在上面的配置中,Ping检测器将尝试3次ping,每秒一次,每次完成将等待1秒钟。如果3秒后没有成功ping,会员将被怀疑。
要强制执行要求,hazelcast.icmp.echo.fail.fast.on.startup还可以将属性设置为true,在这种情况下,如果未满足任何要求,Hazelcast将无法启动。
以下是ping故障检测器的所有可能配置组合的汇总表。
表2. Ping故障检测器可能的配置组合 |
||||||
ICMP |
平行 |
快速失败 |
描述 |
Linux的 |
视窗 |
苹果系统 |
假 |
假 |
假 |
完全禁用 |
N / A |
N / A |
N / A |
真正 |
假 |
假 |
传统ping模式。这与OSI第7层故障检测器密切配合(参见上文中的.phi或截止日期)。在此模式下Ping只会在收到没有听力的时间段后启动,在这种情况下,远程Hazelcast会员将被ping到最多5次。如果所有5次尝试都失败,则该成员被怀疑。 |
支持的ICMP Echo(如果可用) - 在端口7上回退TCP Echo |
端口7上支持的TCP Echo |
支持的ICMP Echo(如果可用) - 在端口7上回退TCP Echo |
真正 |
真正 |
假 |
并行ping检测器与配置的故障检测器并行工作。定期检查成员是否在线(OSI第3层),并立即怀疑它们,无论其他探测器如何。 |
支持的ICMP Echo(如果可用) - 在端口7上回退TCP Echo |
端口7上支持的TCP Echo |
支持的ICMP Echo(如果可用) - 在端口7上回退TCP Echo |
真正 |
真正 |
真正 |
并行ping检测器与配置的故障检测器并行工作。定期检查成员是否在线(OSI第3层),并立即怀疑它们,无论其他探测器如何。 |
支持 - 需要操作系统配置执行ICMP Echo(如果可用) - 如果不可用则不启动 |
不支持 |
不支持 - 需要root权限 |