use of org.apache.helix.msdcommon.exception.InvalidRoutingDataException in project helix by apache.
the class GenericZkHelixApiBuilder method validate.
/**
* Validates the given Builder parameters using a generic validation logic.
*
* This validation function checks whether realm mode has been set correctly, and
* resolves them if not set at all.
*
* If realm mode is null, we look at zkAddress field or RealmAwareZkClient's connection config to
* see if we could deduce the Zk address based on the MetadataStoreRoutingData.
*
* Note: If you set the ZK address explicitly, this setting will take priority over the ZK path
* sharding key set in RealmAwareZkConnectionConfig.
* If this field is null, and the realm mode is single-realm, then it will try to look up the
* ZK address based on the ZK path sharding key.
*/
protected void validate() {
initializeConfigsIfNull();
// Resolve RealmMode based on whether ZK address has been set
boolean isZkAddressSet = _zkAddress != null && !_zkAddress.isEmpty();
// If realmMode is multi-realm, make sure it's not tied to a single sharding key
if (!isZkAddressSet && _realmAwareZkConnectionConfig.getZkRealmShardingKey() != null && !_realmAwareZkConnectionConfig.getZkRealmShardingKey().isEmpty()) {
if (_realmMode == RealmAwareZkClient.RealmMode.SINGLE_REALM) {
// Try to resolve the zk address using the zk path sharding key if given
try {
_zkAddress = resolveZkAddressWithShardingKey(_realmAwareZkConnectionConfig);
isZkAddressSet = true;
} catch (InvalidRoutingDataException e) {
LOG.warn("GenericZkHelixApiBuilder: ZkAddress is not set and failed to resolve ZkAddress with ZK path sharding key!", e);
}
} else if (_realmMode == RealmAwareZkClient.RealmMode.MULTI_REALM) {
// Multi-realm and a single sharding key cannot coexist (by definition, multi-realm can access multiple sharding keys)
throw new HelixException("GenericZkHelixApiBuilder: Cannot have a ZK path sharding key in ConnectionConfig on multi-realm mode! Multi-realm accesses multiple sharding keys.");
}
}
if (_realmMode == RealmAwareZkClient.RealmMode.SINGLE_REALM && !isZkAddressSet) {
throw new HelixException("GenericZkHelixApiBuilder: RealmMode cannot be single-realm without a valid ZkAddress set!");
}
if (_realmMode == RealmAwareZkClient.RealmMode.MULTI_REALM && isZkAddressSet) {
throw new HelixException("GenericZkHelixApiBuilder: ZkAddress cannot be set on multi-realm mode!");
}
if (_realmMode == null) {
_realmMode = isZkAddressSet ? RealmAwareZkClient.RealmMode.SINGLE_REALM : RealmAwareZkClient.RealmMode.MULTI_REALM;
}
}
use of org.apache.helix.msdcommon.exception.InvalidRoutingDataException in project helix by apache.
the class ZkBaseDataAccessor method buildRealmAwareZkClientWithDefaultConfigs.
/**
* This method is used for constructors that are not based on the Builder for
* backward-compatibility.
* It checks if there is a System Property config set for Multi-ZK mode and determines if a
* FederatedZkClient should be created.
* @param clientConfig default RealmAwareZkClientConfig with ZK serializer set
* @param zkAddress
* @param zkClientType
* @return
*/
static RealmAwareZkClient buildRealmAwareZkClientWithDefaultConfigs(RealmAwareZkClient.RealmAwareZkClientConfig clientConfig, String zkAddress, ZkClientType zkClientType) {
if (Boolean.getBoolean(SystemPropertyKeys.MULTI_ZK_ENABLED) || zkAddress == null) {
// If the multi ZK config is enabled, use multi-realm mode with FederatedZkClient
try {
return new FederatedZkClient(new RealmAwareZkClient.RealmAwareZkConnectionConfig.Builder().build(), clientConfig);
} catch (IllegalStateException | InvalidRoutingDataException e) {
throw new HelixException("Not able to connect on multi-realm mode.", e);
}
}
RealmAwareZkClient zkClient;
switch(zkClientType) {
case DEDICATED:
zkClient = DedicatedZkClientFactory.getInstance().buildZkClient(new HelixZkClient.ZkConnectionConfig(zkAddress), clientConfig.createHelixZkClientConfig());
break;
case SHARED:
default:
zkClient = SharedZkClientFactory.getInstance().buildZkClient(new HelixZkClient.ZkConnectionConfig(zkAddress), clientConfig.createHelixZkClientConfig());
zkClient.waitUntilConnected(HelixZkClient.DEFAULT_CONNECTION_TIMEOUT, TimeUnit.MILLISECONDS);
break;
}
return zkClient;
}
use of org.apache.helix.msdcommon.exception.InvalidRoutingDataException in project helix by apache.
the class TaskStateModelFactory method createZkClient.
/*
* Create a RealmAwareZkClient to get thread pool sizes
*/
protected static RealmAwareZkClient createZkClient(HelixManager manager) {
if (!(manager instanceof ZKHelixManager)) {
// HelixManager, the initialization should be allowed.
throw new UnsupportedOperationException("Only ZKHelixManager is supported for configurable thread pool.");
}
RealmAwareZkClient.RealmAwareZkClientConfig clientConfig = new RealmAwareZkClient.RealmAwareZkClientConfig().setZkSerializer(new ZNRecordSerializer());
// Set operation retry timeout to prevent hanging infinitely
clientConfig.setOperationRetryTimeout(Duration.ofMinutes(ZKCLIENT_OPERATION_RETRY_TIMEOUT).toMillis());
String zkAddress = manager.getMetadataStoreConnectionString();
if (Boolean.getBoolean(SystemPropertyKeys.MULTI_ZK_ENABLED) || zkAddress == null) {
RealmAwareZkClient.RealmAwareZkConnectionConfig zkConnectionConfig = ((ZKHelixManager) manager).getRealmAwareZkConnectionConfig();
// problem is fixed.
if (zkConnectionConfig == null) {
String clusterName = manager.getClusterName();
String shardingKey = HelixUtil.clusterNameToShardingKey(clusterName);
zkConnectionConfig = new RealmAwareZkClient.RealmAwareZkConnectionConfig.Builder().setRealmMode(RealmAwareZkClient.RealmMode.SINGLE_REALM).setZkRealmShardingKey(shardingKey).build();
}
try {
return new FederatedZkClient(zkConnectionConfig, clientConfig);
} catch (InvalidRoutingDataException | IllegalArgumentException e) {
throw new HelixException("Failed to create FederatedZkClient!", e);
}
}
// Note: operation retry timeout doesn't take effect due to github.com/apache/helix/issues/1682
return SharedZkClientFactory.getInstance().buildZkClient(new HelixZkClient.ZkConnectionConfig(zkAddress), clientConfig.createHelixZkClientConfig());
}
use of org.apache.helix.msdcommon.exception.InvalidRoutingDataException in project helix by apache.
the class TestZkRoutingDataReader method testGetRoutingData.
@Test
public void testGetRoutingData() {
// Create a node that represents a realm address and add 3 sharding keys to it
ZNRecord testZnRecord1 = new ZNRecord("testZnRecord1");
List<String> testShardingKeys1 = Arrays.asList("/sharding/key/1/a", "/sharding/key/1/b", "/sharding/key/1/c");
testZnRecord1.setListField(MetadataStoreRoutingConstants.ZNRECORD_LIST_FIELD_KEY, testShardingKeys1);
// Create another node that represents a realm address and add 3 sharding keys to it
ZNRecord testZnRecord2 = new ZNRecord("testZnRecord2");
List<String> testShardingKeys2 = Arrays.asList("/sharding/key/2/a", "/sharding/key/2/b", "/sharding/key/2/c", "/sharding/key/2/d");
testZnRecord2.setListField(MetadataStoreRoutingConstants.ZNRECORD_LIST_FIELD_KEY, testShardingKeys2);
// Add both nodes as children nodes to ZkRoutingDataReader.ROUTING_DATA_PATH
_gZkClientTestNS.createPersistent(MetadataStoreRoutingConstants.ROUTING_DATA_PATH + "/testRealmAddress1", testZnRecord1);
_gZkClientTestNS.createPersistent(MetadataStoreRoutingConstants.ROUTING_DATA_PATH + "/testRealmAddress2", testZnRecord2);
try {
Map<String, List<String>> routingData = _zkRoutingDataReader.getRoutingData();
Assert.assertEquals(routingData.size(), 2);
Assert.assertEquals(routingData.get("testRealmAddress1"), testShardingKeys1);
Assert.assertEquals(routingData.get("testRealmAddress2"), testShardingKeys2);
} catch (InvalidRoutingDataException e) {
Assert.fail("Not expecting InvalidRoutingDataException");
}
}
use of org.apache.helix.msdcommon.exception.InvalidRoutingDataException in project helix by apache.
the class HelixPropertyFactory method getCloudConfig.
/**
* Retrieve the CloudConfig of the cluster if available.
* Note: the reason we create a dedicated zk client here is because we need an isolated access to
* ZK in order to create a HelixManager instance.
* If shared zk client instance is used, this logic may break if users write tests that shut down
* ZK server and start again at a 0 zxid because the shared client would have a higher zxid.
* @param zkAddress
* @param clusterName
* @return
*/
private CloudConfig getCloudConfig(String zkAddress, String clusterName) {
CloudConfig cloudConfig;
RealmAwareZkClient dedicatedZkClient = null;
try {
if (Boolean.getBoolean(SystemPropertyKeys.MULTI_ZK_ENABLED) || zkAddress == null) {
// DedicatedZkClient
try {
RealmAwareZkClient.RealmAwareZkConnectionConfig connectionConfig = new RealmAwareZkClient.RealmAwareZkConnectionConfig.Builder().setRealmMode(RealmAwareZkClient.RealmMode.SINGLE_REALM).setZkRealmShardingKey("/" + clusterName).build();
dedicatedZkClient = DedicatedZkClientFactory.getInstance().buildZkClient(connectionConfig);
} catch (IOException | InvalidRoutingDataException e) {
throw new HelixException("Not able to connect on multi-ZK mode!", e);
}
} else {
// Use a dedicated ZK client single-ZK mode
HelixZkClient.ZkConnectionConfig connectionConfig = new HelixZkClient.ZkConnectionConfig(zkAddress);
dedicatedZkClient = DedicatedZkClientFactory.getInstance().buildZkClient(connectionConfig);
}
dedicatedZkClient.setZkSerializer(new ZNRecordSerializer());
ConfigAccessor configAccessor = new ConfigAccessor(dedicatedZkClient);
// up yet, constructing a new ZKHelixManager should not throw an exception
try {
cloudConfig = configAccessor.getCloudConfig(clusterName) == null ? buildEmptyCloudConfig() : configAccessor.getCloudConfig(clusterName);
} catch (HelixException e) {
cloudConfig = buildEmptyCloudConfig();
}
} finally {
// Use a try-finally to make sure zkclient connection is closed properly
if (dedicatedZkClient != null && !dedicatedZkClient.isClosed()) {
dedicatedZkClient.close();
}
}
return cloudConfig;
}
Aggregations