/** * Updates data on a zookeeper node. * * <p> * The supplied data is used for the last node in the path. The path must * already exist. It is not checked if the data is changed or not. This will * cause the version of the node to be increased. * <p> * This operation is retried until it succeeds. */ public static void update(final ZooKeeperItf zk, final String path, final byte[] data, final int version) throws InterruptedException, KeeperException { zk.retryOperation(new ZooKeeperOperation<Boolean>() { @Override public Boolean execute() throws KeeperException, InterruptedException { zk.setData(path, data, version); return null; } }); }
/** * Updates data on a zookeeper node. * * <p> * The supplied data is used for the last node in the path. The path must * already exist. It is not checked if the data is changed or not. This will * cause the version of the node to be increased. * <p> * This operation is retried until it succeeds. */ public static void update(final ZooKeeperItf zk, final String path, final byte[] data, final int version) throws InterruptedException, KeeperException { zk.retryOperation(new ZooKeeperOperation<Boolean>() { @Override public Boolean execute() throws KeeperException, InterruptedException { zk.setData(path, data, version); return null; } }); }
@Override public void unregisterIndexerProcess(final String indexerProcessId) { try { zk.retryOperation(new ZooKeeperOperation<Integer>() { @Override public Integer execute() throws KeeperException, InterruptedException { zk.delete(indexerProcessId, -1); return 0; } }); } catch (Exception e) { throw new RuntimeException("Error unregistering indexer process " + indexerProcessId, e); } }
@Override public void unregisterIndexerProcess(final String indexerProcessId) { try { zk.retryOperation(new ZooKeeperOperation<Integer>() { @Override public Integer execute() throws KeeperException, InterruptedException { zk.delete(indexerProcessId, -1); return 0; } }); } catch (Exception e) { throw new RuntimeException("Error unregistering indexer process " + indexerProcessId, e); } }
@Override public List<IndexerProcess> getIndexerProcesses(final String indexerName) { try { return zk.retryOperation(new ZooKeeperOperation<List<IndexerProcess>>(){ @Override public List<IndexerProcess> execute() throws KeeperException, InterruptedException { List<IndexerProcess> indexerProcesses = Lists.newArrayList(); for (String childNode : zk.getChildren(zkBaseNode, false)) { List<String> nodeNameParts = Lists.newArrayList(Splitter.on(',').split(childNode)); if (indexerName.equals(nodeNameParts.get(0))) { byte[] errorBytes = zk.getData(zkBaseNode + "/" + childNode, false, null); IndexerProcess indexerProcess = new IndexerProcess(indexerName, nodeNameParts.get(1), errorBytes == null || errorBytes.length == 0? null : Bytes.toString(errorBytes)); indexerProcesses.add(indexerProcess); } } return indexerProcesses; }}); } catch (Exception e) { throw new RuntimeException("Error listing indexer processes for " + indexerName, e); } }
@Override public String registerIndexerProcess(String indexerName, String hostName) { // TODO Each indexer should have its own parent node for all its processes // TODO Make sure that commas in an indexer name won't cause issues final String zkNodePathBase = String.format("%s/%s,%s,", zkBaseNode, indexerName, hostName); try { return zk.retryOperation(new ZooKeeperOperation<String>() { @Override public String execute() throws KeeperException, InterruptedException { return zk.create(zkNodePathBase, new byte[0], ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.EPHEMERAL_SEQUENTIAL); } }); } catch (Exception e) { throw new RuntimeException("Error while registering indexer process", e); } }
@Override public List<IndexerProcess> getIndexerProcesses(final String indexerName) { try { return zk.retryOperation(new ZooKeeperOperation<List<IndexerProcess>>(){ @Override public List<IndexerProcess> execute() throws KeeperException, InterruptedException { List<IndexerProcess> indexerProcesses = Lists.newArrayList(); for (String childNode : zk.getChildren(zkBaseNode, false)) { List<String> nodeNameParts = Lists.newArrayList(Splitter.on(',').split(childNode)); if (indexerName.equals(nodeNameParts.get(0))) { byte[] errorBytes = zk.getData(zkBaseNode + "/" + childNode, false, null); IndexerProcess indexerProcess = new IndexerProcess(indexerName, nodeNameParts.get(1), errorBytes == null || errorBytes.length == 0? null : Bytes.toString(errorBytes)); indexerProcesses.add(indexerProcess); } } return indexerProcesses; }}); } catch (Exception e) { throw new RuntimeException("Error listing indexer processes for " + indexerName, e); } }
@Override public String registerIndexerProcess(String indexerName, String hostName) { // TODO Each indexer should have its own parent node for all its processes // TODO Make sure that commas in an indexer name won't cause issues final String zkNodePathBase = String.format("%s/%s,%s,", zkBaseNode, indexerName, hostName); try { return zk.retryOperation(new ZooKeeperOperation<String>() { @Override public String execute() throws KeeperException, InterruptedException { return zk.create(zkNodePathBase, new byte[0], CreateMode.EPHEMERAL_SEQUENTIAL); } }); } catch (Exception e) { throw new RuntimeException("Error while registering indexer process", e); } }
/** * Gets data from a zookeeper node. * <p> * This operation is retried until it succeeds. */ public static byte[] getData(final ZooKeeperItf zk, final String path, final Watcher watcher, final Stat stat) throws InterruptedException, KeeperException { final List<byte[]> data = new ArrayList<byte[]>(1); zk.retryOperation(new ZooKeeperOperation<Boolean>() { @Override public Boolean execute() throws KeeperException, InterruptedException { data.add(zk.getData(path, watcher, stat)); return null; } }); return data.get(0); } }
/** * Gets data from a zookeeper node. * <p> * This operation is retried until it succeeds. */ public static byte[] getData(final ZooKeeperItf zk, final String path, final Watcher watcher, final Stat stat) throws InterruptedException, KeeperException { final List<byte[]> data = new ArrayList<byte[]>(1); zk.retryOperation(new ZooKeeperOperation<Boolean>() { @Override public Boolean execute() throws KeeperException, InterruptedException { data.add(zk.getData(path, watcher, stat)); return null; } }); return data.get(0); } }
@Override public void setErrorStatus(final String indexerProcessId, Throwable error) { final String stackTrace = ExceptionUtils.getStackTrace(error); try { zk.retryOperation(new ZooKeeperOperation<Integer>() { @Override public Integer execute() throws KeeperException, InterruptedException { zk.setData(indexerProcessId, Bytes.toBytes(stackTrace), -1); return 0; } }); } catch (Exception e) { throw new RuntimeException("Error while setting error status on indexer node " + indexerProcessId, e); } }
@Override public void setErrorStatus(final String indexerProcessId, Throwable error) { final String stackTrace = ExceptionUtils.getStackTrace(error); try { zk.retryOperation(new ZooKeeperOperation<Integer>() { @Override public Integer execute() throws KeeperException, InterruptedException { zk.setData(indexerProcessId, Bytes.toBytes(stackTrace), -1); return 0; } }); } catch (Exception e) { throw new RuntimeException("Error while setting error status on indexer node " + indexerProcessId, e); } }
private void connectWithZooKeeper() throws IOException, KeeperException, InterruptedException { int zkSessionTimeout = HBaseIndexerConfiguration.getSessionTimeout(conf); zk = new StateWatchingZooKeeper(zkConnectionString, zkSessionTimeout); final String zkRoot = conf.get("hbaseindexer.zookeeper.znode.parent"); boolean indexerNodeExists = zk.retryOperation(new ZooKeeperOperation<Boolean>() { @Override public Boolean execute() throws KeeperException, InterruptedException { return zk.exists(zkRoot, false) != null; } }); if (!indexerNodeExists) { System.err.println(); System.err.println("WARNING: No " + zkRoot + " node found in ZooKeeper."); System.err.println(); } }
/** * Verifies that the specified lockId is the owner of the lock. */ public static boolean ownsLock(final ZooKeeperItf zk, final String lockId) throws ZkLockException { if (zk.isCurrentThreadEventThread()) { throw new RuntimeException("ZkLock should not be used from within the ZooKeeper event thread."); } try { int lastSlashPos = lockId.lastIndexOf('/'); final String lockPath = lockId.substring(0, lastSlashPos); String lockName = lockId.substring(lastSlashPos + 1); List<String> children = zk.retryOperation(new ZooKeeperOperation<List<String>>() { @Override public List<String> execute() throws KeeperException, InterruptedException { return zk.getChildren(lockPath, null); } }); if (children.isEmpty()) return false; SortedSet<String> sortedChildren = new TreeSet<String>(children); return sortedChildren.first().equals(lockName); } catch (Throwable t) { throw new ZkLockException("Error checking lock, path: " + lockId, t); } }
private void connectWithZooKeeper() throws IOException, KeeperException, InterruptedException { int zkSessionTimeout = HBaseIndexerConfiguration.getSessionTimeout(conf); zk = new StateWatchingZooKeeper(zkConnectionString, zkSessionTimeout, new DefaultACLProvider()); final String zkRoot = conf.get("hbaseindexer.zookeeper.znode.parent"); boolean indexerNodeExists = zk.retryOperation(new ZooKeeperOperation<Boolean>() { @Override public Boolean execute() throws KeeperException, InterruptedException { return zk.exists(zkRoot, false) != null; } }); if (!indexerNodeExists) { System.err.println(); System.err.println("WARNING: No " + zkRoot + " node found in ZooKeeper."); System.err.println(); } }
private void proposeAsLeader() throws LeaderElectionSetupException, InterruptedException, KeeperException { ZkUtil.createPath(zk, electionPath); try { // In case of connection loss, a node might have been created for us (we do not know it). Therefore, // retrying upon connection loss is important, so that we can continue with watching the leaders. // Later on, we do not look at the name of the node we created here, but at the owner. zk.retryOperation(new ZooKeeperOperation<String>() { @Override public String execute() throws KeeperException, InterruptedException { return zk.create(electionPath + "/n_", null, ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.EPHEMERAL_SEQUENTIAL); } }); } catch (KeeperException e) { throw new LeaderElectionSetupException("Error creating leader election zookeeper node below " + electionPath, e); } watchLeaders(); }
private void proposeAsLeader() throws LeaderElectionSetupException, InterruptedException, KeeperException { ZkUtil.createPath(zk, electionPath); try { // In case of connection loss, a node might have been created for us (we do not know it). Therefore, // retrying upon connection loss is important, so that we can continue with watching the leaders. // Later on, we do not look at the name of the node we created here, but at the owner. zk.retryOperation(new ZooKeeperOperation<String>() { @Override public String execute() throws KeeperException, InterruptedException { return zk.create(electionPath + "/n_", null, CreateMode.EPHEMERAL_SEQUENTIAL); } }); } catch (KeeperException e) { throw new LeaderElectionSetupException("Error creating leader election zookeeper node below " + electionPath, e); } watchLeaders(); }
private IndexerDefinition loadIndexer(String indexerName, boolean forCache) throws InterruptedException, KeeperException, IndexerNotFoundException { final String childPath = indexerCollectionPath + "/" + indexerName; final Stat stat = new Stat(); byte[] data; try { if (forCache) { // do not retry, install watcher data = zk.getData(childPath, watcher, stat); } else { // do retry, do not install watcher data = zk.retryOperation(new ZooKeeperOperation<byte[]>() { @Override public byte[] execute() throws KeeperException, InterruptedException { return zk.getData(childPath, false, stat); } }); } } catch (KeeperException.NoNodeException e) { throw new IndexerNotFoundException(indexerName); } IndexerDefinitionBuilder builder = IndexerDefinitionJsonSerDeser.INSTANCE.fromJsonBytes(data); builder.name(indexerName); builder.occVersion(stat.getVersion()); return builder.build(); }
@Override public void updateIndexerInternal(final IndexerDefinition indexer) throws InterruptedException, KeeperException, IndexerNotFoundException, IndexerConcurrentModificationException, IndexerValidityException { assertValid(indexer); final byte[] newData = IndexerDefinitionJsonSerDeser.INSTANCE.toJsonBytes(indexer); try { zk.retryOperation(new ZooKeeperOperation<Stat>() { @Override public Stat execute() throws KeeperException, InterruptedException { return zk.setData(indexerCollectionPathSlash + indexer.getName(), newData, indexer.getOccVersion()); } }); } catch (KeeperException.NoNodeException e) { throw new IndexerNotFoundException(indexer.getName()); } catch (KeeperException.BadVersionException e) { throw new IndexerConcurrentModificationException(indexer.getName()); } }
@Override public void updateIndexerInternal(final IndexerDefinition indexer) throws InterruptedException, KeeperException, IndexerNotFoundException, IndexerConcurrentModificationException, IndexerValidityException { assertValid(indexer); final byte[] newData = IndexerDefinitionJsonSerDeser.INSTANCE.toJsonBytes(indexer); try { zk.retryOperation(new ZooKeeperOperation<Stat>() { @Override public Stat execute() throws KeeperException, InterruptedException { return zk.setData(indexerCollectionPathSlash + indexer.getName(), newData, indexer.getOccVersion()); } }); } catch (KeeperException.NoNodeException e) { throw new IndexerNotFoundException(indexer.getName()); } catch (KeeperException.BadVersionException e) { throw new IndexerConcurrentModificationException(indexer.getName()); } }