diff --git a/solr/core/build.gradle b/solr/core/build.gradle index 61ecd1713af..12dedcf9e69 100644 --- a/solr/core/build.gradle +++ b/solr/core/build.gradle @@ -121,6 +121,16 @@ dependencies { implementation 'org.eclipse.jetty:jetty-io' implementation 'org.eclipse.jetty.toolchain:jetty-servlet-api' + implementation('org.apache.curator:curator-framework', { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + }) + testImplementation('org.apache.curator:curator-client', { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + }) + testImplementation('org.apache.curator:curator-test', { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + }) + // ZooKeeper implementation('org.apache.zookeeper:zookeeper', { exclude group: "org.apache.yetus", module: "audience-annotations" diff --git a/solr/core/src/java/org/apache/solr/cli/AuthTool.java b/solr/core/src/java/org/apache/solr/cli/AuthTool.java index 2afd71706b6..1f2fc2ac0dd 100644 --- a/solr/core/src/java/org/apache/solr/cli/AuthTool.java +++ b/solr/core/src/java/org/apache/solr/cli/AuthTool.java @@ -217,8 +217,7 @@ private int handleKerberos(CommandLine cli) throws Exception { .withTimeout( SolrZkClientTimeout.DEFAULT_ZK_CLIENT_TIMEOUT, TimeUnit.MILLISECONDS) .build()) { - zkClient.setData( - "/security.json", securityJson.getBytes(StandardCharsets.UTF_8), true); + zkClient.setData("/security.json", securityJson.getBytes(StandardCharsets.UTF_8)); } catch (Exception ex) { CLIO.out( "Unable to access ZooKeeper. Please add the following security.json to ZooKeeper (in case of SolrCloud):\n" @@ -384,7 +383,7 @@ private int handleBasicAuth(CommandLine cli) throws Exception { .withUrl(zkHost) .withTimeout(SolrZkClientTimeout.DEFAULT_ZK_CLIENT_TIMEOUT, TimeUnit.MILLISECONDS) .build()) { - zkClient.setData("/security.json", securityJson.getBytes(StandardCharsets.UTF_8), true); + zkClient.setData("/security.json", securityJson.getBytes(StandardCharsets.UTF_8)); } } @@ -452,8 +451,8 @@ private int handleBasicAuth(CommandLine cli) throws Exception { private void checkSecurityJsonExists(SolrZkClient zkClient) throws KeeperException, InterruptedException { - if (zkClient.exists("/security.json", true)) { - byte[] oldSecurityBytes = zkClient.getData("/security.json", null, null, true); + if (zkClient.exists("/security.json")) { + byte[] oldSecurityBytes = zkClient.getData("/security.json", null, null); if (!"{}".equals(new String(oldSecurityBytes, StandardCharsets.UTF_8).trim())) { CLIO.out( "Security is already enabled. You can disable it with 'bin/solr auth disable'. Existing security.json: \n" @@ -479,7 +478,7 @@ private void clearSecurityJson(CommandLine cli, boolean updateIncludeFileOnly) t .withUrl(zkHost) .withTimeout(SolrZkClientTimeout.DEFAULT_ZK_CLIENT_TIMEOUT, TimeUnit.MILLISECONDS) .build()) { - zkClient.setData("/security.json", "{}".getBytes(StandardCharsets.UTF_8), true); + zkClient.setData("/security.json", "{}".getBytes(StandardCharsets.UTF_8)); } } } diff --git a/solr/core/src/java/org/apache/solr/cli/CreateTool.java b/solr/core/src/java/org/apache/solr/cli/CreateTool.java index e62c42d185a..64f8a9ceaca 100644 --- a/solr/core/src/java/org/apache/solr/cli/CreateTool.java +++ b/solr/core/src/java/org/apache/solr/cli/CreateTool.java @@ -243,9 +243,7 @@ protected void createCollection(CloudSolrClient cloudSolrClient, CommandLine cli boolean configExistsInZk = confName != null && !confName.trim().isEmpty() - && ZkStateReader.from(cloudSolrClient) - .getZkClient() - .exists("/configs/" + confName, true); + && ZkStateReader.from(cloudSolrClient).getZkClient().exists("/configs/" + confName); if (CollectionAdminParams.SYSTEM_COLL.equals(collectionName)) { // do nothing diff --git a/solr/core/src/java/org/apache/solr/cli/ZkRmTool.java b/solr/core/src/java/org/apache/solr/cli/ZkRmTool.java index dad5bdbbe94..4b106a540b5 100644 --- a/solr/core/src/java/org/apache/solr/cli/ZkRmTool.java +++ b/solr/core/src/java/org/apache/solr/cli/ZkRmTool.java @@ -87,7 +87,7 @@ public void runImpl(CommandLine cli) throws Exception { .withUrl(zkHost) .withTimeout(SolrZkClientTimeout.DEFAULT_ZK_CLIENT_TIMEOUT, TimeUnit.MILLISECONDS) .build()) { - if (!recurse && zkClient.getChildren(znode, null, true).size() != 0) { + if (!recurse && zkClient.getChildren(znode, null).size() != 0) { throw new SolrServerException( "ZooKeeper node " + znode + " has children and recurse has NOT been specified."); } diff --git a/solr/core/src/java/org/apache/solr/cloud/CloudUtil.java b/solr/core/src/java/org/apache/solr/cloud/CloudUtil.java index de9181e505c..fc3d7239202 100644 --- a/solr/core/src/java/org/apache/solr/cloud/CloudUtil.java +++ b/solr/core/src/java/org/apache/solr/cloud/CloudUtil.java @@ -140,10 +140,10 @@ public static String unifiedResourcePath(SolrResourceLoader loader) { public static Map getTrustedKeys(SolrZkClient zk, String dir) { Map result = new HashMap<>(); try { - List children = zk.getChildren("/keys/" + dir, null, true); + List children = zk.getChildren("/keys/" + dir, null); for (String key : children) { if (key.endsWith(".der")) - result.put(key, zk.getData("/keys/" + dir + "/" + key, null, null, true)); + result.put(key, zk.getData("/keys/" + dir + "/" + key, null, null)); } } catch (KeeperException.NoNodeException e) { log.info("Error fetching key names"); diff --git a/solr/core/src/java/org/apache/solr/cloud/DistributedApiAsyncTracker.java b/solr/core/src/java/org/apache/solr/cloud/DistributedApiAsyncTracker.java index 8ebdb2ae287..6120d8ad6b2 100644 --- a/solr/core/src/java/org/apache/solr/cloud/DistributedApiAsyncTracker.java +++ b/solr/core/src/java/org/apache/solr/cloud/DistributedApiAsyncTracker.java @@ -311,8 +311,8 @@ enum State { this.rootNodePath = rootNodePath; try { - if (!zkClient.exists(rootNodePath, true)) { - zkClient.makePath(rootNodePath, new byte[0], CreateMode.PERSISTENT, true); + if (!zkClient.exists(rootNodePath)) { + zkClient.makePath(rootNodePath, new byte[0], CreateMode.PERSISTENT); } } catch (KeeperException.NodeExistsException nee) { // Some other thread (on this or another JVM) beat us to create the node, that's ok, the @@ -329,27 +329,25 @@ void createNewInFlightTask(String asyncId) throws KeeperException, InterruptedEx zkClient.create( getPath(asyncId), State.SUBMITTED.shorthand.getBytes(StandardCharsets.UTF_8), - CreateMode.EPHEMERAL, - true); + CreateMode.EPHEMERAL); } void setTaskRunning(String asyncId) throws KeeperException, InterruptedException { - zkClient.setData( - getPath(asyncId), State.RUNNING.shorthand.getBytes(StandardCharsets.UTF_8), true); + zkClient.setData(getPath(asyncId), State.RUNNING.shorthand.getBytes(StandardCharsets.UTF_8)); } void deleteInFlightTask(String asyncId) throws KeeperException, InterruptedException { - zkClient.delete(getPath(asyncId), -1, true); + zkClient.delete(getPath(asyncId), -1); } State getInFlightState(String asyncId) throws KeeperException, InterruptedException { - if (!zkClient.exists(getPath(asyncId), true)) { + if (!zkClient.exists(getPath(asyncId))) { return State.NOT_FOUND; } final byte[] bytes; try { - bytes = zkClient.getData(getPath(asyncId), null, null, true); + bytes = zkClient.getData(getPath(asyncId), null, null); } catch (KeeperException.NoNodeException nne) { // Unlikely race, but not impossible... if (log.isInfoEnabled()) { diff --git a/solr/core/src/java/org/apache/solr/cloud/DistributedClusterStateUpdater.java b/solr/core/src/java/org/apache/solr/cloud/DistributedClusterStateUpdater.java index bc565ad97e8..02543e51e40 100644 --- a/solr/core/src/java/org/apache/solr/cloud/DistributedClusterStateUpdater.java +++ b/solr/core/src/java/org/apache/solr/cloud/DistributedClusterStateUpdater.java @@ -598,7 +598,7 @@ private void doStateDotJsonCasUpdate(ClusterState updatedState) if (updater.isCollectionCreation()) { // The state.json file does not exist yet (more precisely it is assumed not to exist) log.debug("going to create collection {}", jsonPath); - zkStateReader.getZkClient().create(jsonPath, stateJson, CreateMode.PERSISTENT, true); + zkStateReader.getZkClient().create(jsonPath, stateJson, CreateMode.PERSISTENT); } else { // We're updating an existing state.json if (log.isDebugEnabled()) { @@ -607,9 +607,7 @@ private void doStateDotJsonCasUpdate(ClusterState updatedState) jsonPath, collection.getZNodeVersion()); } - zkStateReader - .getZkClient() - .setData(jsonPath, stateJson, collection.getZNodeVersion(), true); + zkStateReader.getZkClient().setData(jsonPath, stateJson, collection.getZNodeVersion()); } } } @@ -623,7 +621,7 @@ private void doStateDotJsonCasUpdate(ClusterState updatedState) private ClusterState fetchStateForCollection() throws KeeperException, InterruptedException { String collectionStatePath = DocCollection.getCollectionPath(updater.getCollectionName()); Stat stat = new Stat(); - byte[] data = zkStateReader.getZkClient().getData(collectionStatePath, null, stat, true); + byte[] data = zkStateReader.getZkClient().getData(collectionStatePath, null, stat); // This factory method can detect a missing configName and supply it by reading it from the // old ZK location. @@ -933,7 +931,7 @@ public static void executeNodeDownStateUpdate(String nodeName, ZkStateReader zkS try { final List collectionNames = - zkStateReader.getZkClient().getChildren(COLLECTIONS_ZKNODE, null, true); + zkStateReader.getZkClient().getChildren(COLLECTIONS_ZKNODE, null); // Collections are totally independent of each other. Multiple threads could share the load // here (need a ZK connection for each though). diff --git a/solr/core/src/java/org/apache/solr/cloud/DistributedMap.java b/solr/core/src/java/org/apache/solr/cloud/DistributedMap.java index fb2347c3e82..532a782825b 100644 --- a/solr/core/src/java/org/apache/solr/cloud/DistributedMap.java +++ b/solr/core/src/java/org/apache/solr/cloud/DistributedMap.java @@ -68,8 +68,7 @@ private void assertKeyFormat(String trackingId) { public void put(String trackingId, byte[] data) throws KeeperException, InterruptedException { assertKeyFormat(trackingId); - zookeeper.makePath( - dir + "/" + PREFIX + trackingId, data, CreateMode.PERSISTENT, null, false, true); + zookeeper.makePath(dir + "/" + PREFIX + trackingId, data, CreateMode.PERSISTENT, null, false); } /** @@ -81,8 +80,7 @@ public boolean putIfAbsent(String trackingId, byte[] data) throws KeeperException, InterruptedException { assertKeyFormat(trackingId); try { - zookeeper.makePath( - dir + "/" + PREFIX + trackingId, data, CreateMode.PERSISTENT, null, true, true); + zookeeper.makePath(dir + "/" + PREFIX + trackingId, data, CreateMode.PERSISTENT, null, true); return true; } catch (NodeExistsException e) { return false; @@ -90,16 +88,16 @@ public boolean putIfAbsent(String trackingId, byte[] data) } public byte[] get(String trackingId) throws KeeperException, InterruptedException { - return zookeeper.getData(dir + "/" + PREFIX + trackingId, null, null, true); + return zookeeper.getData(dir + "/" + PREFIX + trackingId, null, null); } public boolean contains(String trackingId) throws KeeperException, InterruptedException { - return zookeeper.exists(dir + "/" + PREFIX + trackingId, true); + return zookeeper.exists(dir + "/" + PREFIX + trackingId); } public int size() throws KeeperException, InterruptedException { Stat stat = new Stat(); - zookeeper.getData(dir, null, stat, true); + zookeeper.getData(dir, null, stat); return stat.getNumChildren(); } @@ -110,7 +108,7 @@ public int size() throws KeeperException, InterruptedException { public boolean remove(String trackingId) throws KeeperException, InterruptedException { final var path = dir + "/" + PREFIX + trackingId; try { - zookeeper.delete(path, -1, true); + zookeeper.delete(path, -1); } catch (KeeperException.NoNodeException e) { return false; } catch (KeeperException.NotEmptyException hack) { @@ -123,15 +121,15 @@ public boolean remove(String trackingId) throws KeeperException, InterruptedExce /** Helper method to clear all child nodes for a parent node. */ public void clear() throws KeeperException, InterruptedException { - List childNames = zookeeper.getChildren(dir, null, true); + List childNames = zookeeper.getChildren(dir, null); for (String childName : childNames) { - zookeeper.delete(dir + "/" + childName, -1, true); + zookeeper.delete(dir + "/" + childName, -1); } } /** Returns the keys of all the elements in the map */ public Collection keys() throws KeeperException, InterruptedException { - List childs = zookeeper.getChildren(dir, null, true); + List childs = zookeeper.getChildren(dir, null); final List ids = new ArrayList<>(childs.size()); childs.stream().forEach((child) -> ids.add(child.substring(PREFIX.length()))); return ids; diff --git a/solr/core/src/java/org/apache/solr/cloud/ElectionContext.java b/solr/core/src/java/org/apache/solr/cloud/ElectionContext.java index 1ace066447c..e41546f24da 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ElectionContext.java +++ b/solr/core/src/java/org/apache/solr/cloud/ElectionContext.java @@ -55,7 +55,7 @@ public void cancelElection() throws InterruptedException, KeeperException { if (leaderSeqPath != null) { try { log.debug("Canceling election {}", leaderSeqPath); - zkClient.delete(leaderSeqPath, -1, true); + zkClient.delete(leaderSeqPath, -1); } catch (NoNodeException e) { // fine log.debug("cancelElection did not find election node to remove {}", leaderSeqPath); diff --git a/solr/core/src/java/org/apache/solr/cloud/LeaderElector.java b/solr/core/src/java/org/apache/solr/cloud/LeaderElector.java index 6a003b19955..760d6ae04ab 100644 --- a/solr/core/src/java/org/apache/solr/cloud/LeaderElector.java +++ b/solr/core/src/java/org/apache/solr/cloud/LeaderElector.java @@ -25,7 +25,6 @@ import java.util.regex.Matcher; import java.util.regex.Pattern; import org.apache.solr.cloud.ZkController.ContextKey; -import org.apache.solr.common.AlreadyClosedException; import org.apache.solr.common.SolrException; import org.apache.solr.common.cloud.SolrZkClient; import org.apache.solr.common.cloud.ZkMaintenanceUtils; @@ -95,7 +94,7 @@ private void checkIfIamLeader(final ElectionContext context, boolean replacement context.checkIfIamLeaderFired(); // get all other numbers... final String holdElectionPath = context.electionPath + ELECTION_NODE; - List seqs = zkClient.getChildren(holdElectionPath, null, true); + List seqs = zkClient.getChildren(holdElectionPath, null); sortSeqs(seqs); String leaderSeqNodeName = @@ -107,7 +106,7 @@ private void checkIfIamLeader(final ElectionContext context, boolean replacement // If any double-registrations exist for me, remove all but this latest one! // TODO: can we even get into this state? - String prefix = zkClient.getZooKeeper().getSessionId() + "-" + context.id + "-"; + String prefix = zkClient.getZkSessionId() + "-" + context.id + "-"; Iterator it = seqs.iterator(); while (it.hasNext()) { String elec = it.next(); @@ -115,7 +114,7 @@ private void checkIfIamLeader(final ElectionContext context, boolean replacement try { String toDelete = holdElectionPath + "/" + elec; log.warn("Deleting duplicate registration: {}", toDelete); - zkClient.delete(toDelete, -1, true); + zkClient.delete(toDelete, -1); } catch (KeeperException.NoNodeException e) { // ignore } @@ -149,8 +148,7 @@ private void checkIfIamLeader(final ElectionContext context, boolean replacement watcher = new ElectionWatcher( context.leaderSeqPath, watchedNode, getSeq(context.leaderSeqPath), context), - null, - true); + null); log.debug("Watching path {} to know if I could be the leader", watchedNode); } catch (KeeperException.SessionExpiredException e) { throw e; @@ -227,7 +225,7 @@ public int joinElection(ElectionContext context, boolean replacement, boolean jo final String shardsElectZkPath = context.electionPath + LeaderElector.ELECTION_NODE; - long sessionId = zkClient.getZooKeeper().getSessionId(); + long sessionId = zkClient.getZkSessionId(); String id = sessionId + "-" + context.id; String leaderSeqPath = null; boolean cont = true; @@ -241,10 +239,7 @@ public int joinElection(ElectionContext context, boolean replacement, boolean jo if (nodes.size() < 2) { leaderSeqPath = zkClient.create( - shardsElectZkPath + "/" + id + "-n_", - null, - CreateMode.EPHEMERAL_SEQUENTIAL, - false); + shardsElectZkPath + "/" + id + "-n_", null, CreateMode.EPHEMERAL_SEQUENTIAL); } else { String firstInLine = nodes.get(1); log.debug("The current head: {}", firstInLine); @@ -253,15 +248,12 @@ public int joinElection(ElectionContext context, boolean replacement, boolean jo throw new IllegalStateException("Could not find regex match in:" + firstInLine); } leaderSeqPath = shardsElectZkPath + "/" + id + "-n_" + m.group(1); - zkClient.create(leaderSeqPath, null, CreateMode.EPHEMERAL, false); + zkClient.create(leaderSeqPath, null, CreateMode.EPHEMERAL); } } else { leaderSeqPath = zkClient.create( - shardsElectZkPath + "/" + id + "-n_", - null, - CreateMode.EPHEMERAL_SEQUENTIAL, - false); + shardsElectZkPath + "/" + id + "-n_", null, CreateMode.EPHEMERAL_SEQUENTIAL); } log.debug("Joined leadership election with path: {}", leaderSeqPath); @@ -269,7 +261,7 @@ public int joinElection(ElectionContext context, boolean replacement, boolean jo cont = false; } catch (ConnectionLossException e) { // we don't know if we made our node or not... - List entries = zkClient.getChildren(shardsElectZkPath, null, true); + List entries = zkClient.getChildren(shardsElectZkPath, null); boolean foundId = false; for (String entry : entries) { @@ -337,7 +329,7 @@ public void process(WatchedEvent event) { if (canceled) { log.debug("This watcher is not active anymore {}", myNode); try { - zkClient.delete(myNode, -1, true); + zkClient.delete(myNode, -1); } catch (KeeperException.NoNodeException nne) { // expected . don't do anything } catch (Exception e) { @@ -348,7 +340,7 @@ public void process(WatchedEvent event) { try { // am I the next leader? checkIfIamLeader(context, true); - } catch (AlreadyClosedException e) { + } catch (IllegalStateException e) { } catch (Exception e) { if (!zkClient.isClosed()) { @@ -365,8 +357,7 @@ public void setup(final ElectionContext context) throws InterruptedException, Ke ZkMaintenanceUtils.ensureExists(electZKPath, zkClient); } else { // we use 2 param so that replica won't create /collection/{collection} if it doesn't exist - ZkMaintenanceUtils.ensureExists( - electZKPath, (byte[]) null, CreateMode.PERSISTENT, zkClient, 2); + ZkMaintenanceUtils.ensureExists(electZKPath, null, CreateMode.PERSISTENT, zkClient, 2); } this.context = context; diff --git a/solr/core/src/java/org/apache/solr/cloud/Overseer.java b/solr/core/src/java/org/apache/solr/cloud/Overseer.java index a57270c23db..b37453948d5 100644 --- a/solr/core/src/java/org/apache/solr/cloud/Overseer.java +++ b/solr/core/src/java/org/apache/solr/cloud/Overseer.java @@ -316,7 +316,7 @@ public void run() { // the workQueue is empty now, use stateUpdateQueue as fallback queue fallbackQueue = stateUpdateQueue; fallbackQueueSize = 0; - } catch (AlreadyClosedException e) { + } catch (IllegalStateException e) { return; } catch (KeeperException.SessionExpiredException e) { log.warn("Solr cannot talk to ZK, exiting Overseer work queue loop", e); @@ -342,7 +342,7 @@ public void run() { } catch (InterruptedException e) { Thread.currentThread().interrupt(); return; - } catch (AlreadyClosedException e) { + } catch (IllegalStateException e) { } catch (Exception e) { log.error("Exception in Overseer main queue loop", e); @@ -402,7 +402,7 @@ public void run() { } catch (InterruptedException e) { Thread.currentThread().interrupt(); return; - } catch (AlreadyClosedException e) { + } catch (IllegalStateException e) { } catch (Exception e) { log.error("Exception in Overseer main queue loop", e); @@ -479,8 +479,8 @@ private void checkIfIamStillLeader() { final String path = OVERSEER_ELECT + "/leader"; byte[] data; try { - data = zkClient.getData(path, null, stat, true); - } catch (AlreadyClosedException e) { + data = zkClient.getData(path, null, stat); + } catch (IllegalStateException e) { return; } catch (Exception e) { log.warn("Error communicating with ZooKeeper", e); @@ -494,7 +494,7 @@ private void checkIfIamStillLeader() { log.warn( "I (id={}) am exiting, but I'm still the leader", overseerCollectionConfigSetProcessor.getId()); - zkClient.delete(path, stat.getVersion(), true); + zkClient.delete(path, stat.getVersion()); } catch (KeeperException.BadVersionException e) { // no problem ignore it some other Overseer has already taken over } catch (Exception e) { @@ -616,7 +616,7 @@ private LeaderStatus amILeader() { String propsId = null; try { ZkNodeProps props = - ZkNodeProps.load(zkClient.getData(OVERSEER_ELECT + "/leader", null, null, true)); + ZkNodeProps.load(zkClient.getData(OVERSEER_ELECT + "/leader", null, null)); propsId = props.getStr(ID); if (myId.equals(propsId)) { return LeaderStatus.YES; @@ -634,7 +634,7 @@ private LeaderStatus amILeader() { } catch (InterruptedException e) { success = false; Thread.currentThread().interrupt(); - } catch (AlreadyClosedException e) { + } catch (IllegalStateException e) { success = false; } catch (Exception e) { success = false; @@ -1184,7 +1184,7 @@ OverseerTaskQueue getConfigSetQueue(final SolrZkClient zkClient, Stats zkStats) private void createOverseerNode(final SolrZkClient zkClient) { try { - zkClient.create("/overseer", new byte[0], CreateMode.PERSISTENT, true); + zkClient.create("/overseer", new byte[0], CreateMode.PERSISTENT); } catch (KeeperException.NodeExistsException e) { // ok } catch (InterruptedException e) { diff --git a/solr/core/src/java/org/apache/solr/cloud/OverseerElectionContext.java b/solr/core/src/java/org/apache/solr/cloud/OverseerElectionContext.java index 8eb8a6d1386..270d746bc4e 100644 --- a/solr/core/src/java/org/apache/solr/cloud/OverseerElectionContext.java +++ b/solr/core/src/java/org/apache/solr/cloud/OverseerElectionContext.java @@ -62,7 +62,7 @@ void runLeaderProcess(boolean weAreReplacement, int pauseBeforeStartMs) final String id = leaderSeqPath.substring(leaderSeqPath.lastIndexOf('/') + 1); ZkNodeProps myProps = new ZkNodeProps(ID, id); - zkClient.makePath(leaderPath, Utils.toJSON(myProps), CreateMode.EPHEMERAL, true); + zkClient.makePath(leaderPath, Utils.toJSON(myProps), CreateMode.EPHEMERAL); if (pauseBeforeStartMs > 0) { try { Thread.sleep(pauseBeforeStartMs); diff --git a/solr/core/src/java/org/apache/solr/cloud/OverseerNodePrioritizer.java b/solr/core/src/java/org/apache/solr/cloud/OverseerNodePrioritizer.java index 63dca3f1c61..0e1a0acd58e 100644 --- a/solr/core/src/java/org/apache/solr/cloud/OverseerNodePrioritizer.java +++ b/solr/core/src/java/org/apache/solr/cloud/OverseerNodePrioritizer.java @@ -67,9 +67,8 @@ public OverseerNodePrioritizer( public synchronized void prioritizeOverseerNodes(String overseerId) throws Exception { SolrZkClient zk = zkStateReader.getZkClient(); List overseerDesignates = new ArrayList<>(); - if (zk.exists(ZkStateReader.ROLES, true)) { - Map m = - (Map) Utils.fromJSON(zk.getData(ZkStateReader.ROLES, null, new Stat(), true)); + if (zk.exists(ZkStateReader.ROLES)) { + Map m = (Map) Utils.fromJSON(zk.getData(ZkStateReader.ROLES, null, new Stat())); @SuppressWarnings("unchecked") List l = (List) m.get("overseer"); if (l != null) { diff --git a/solr/core/src/java/org/apache/solr/cloud/OverseerTaskProcessor.java b/solr/core/src/java/org/apache/solr/cloud/OverseerTaskProcessor.java index eb5661885c4..9ebe8644626 100644 --- a/solr/core/src/java/org/apache/solr/cloud/OverseerTaskProcessor.java +++ b/solr/core/src/java/org/apache/solr/cloud/OverseerTaskProcessor.java @@ -36,7 +36,6 @@ import java.util.function.Predicate; import org.apache.solr.cloud.Overseer.LeaderStatus; import org.apache.solr.cloud.OverseerTaskQueue.QueueEvent; -import org.apache.solr.common.AlreadyClosedException; import org.apache.solr.common.cloud.SolrZkClient; import org.apache.solr.common.cloud.ZkNodeProps; import org.apache.solr.common.cloud.ZkStateReader; @@ -188,7 +187,7 @@ public void run() { // We don't need to handle this. This is just a fail-safe which comes in handy in skipping // already processed async calls. log.error("KeeperException", e); - } catch (AlreadyClosedException e) { + } catch (IllegalStateException ignore) { return; } catch (InterruptedException e) { Thread.currentThread().interrupt(); @@ -202,7 +201,7 @@ public void run() { try { prioritizer.prioritizeOverseerNodes(myId); - } catch (AlreadyClosedException e) { + } catch (IllegalStateException ignore) { return; } catch (Exception e) { if (!zkStateReader.getZkClient().isClosed()) { @@ -395,7 +394,7 @@ public void run() { } catch (InterruptedException e) { Thread.currentThread().interrupt(); return; - } catch (AlreadyClosedException ignore) { + } catch (IllegalStateException ignore) { } catch (Exception e) { log.error("Exception processing", e); @@ -432,7 +431,7 @@ public static List getSortedOverseerNodeNames(SolrZkClient zk) throws KeeperException, InterruptedException { List children = null; try { - children = zk.getChildren(Overseer.OVERSEER_ELECT + LeaderElector.ELECTION_NODE, null, true); + children = zk.getChildren(Overseer.OVERSEER_ELECT + LeaderElector.ELECTION_NODE, null); } catch (Exception e) { log.warn("error ", e); return new ArrayList<>(); @@ -447,7 +446,7 @@ public static List getSortedElectionNodes(SolrZkClient zk, String path) throws KeeperException, InterruptedException { List children = null; try { - children = zk.getChildren(path, null, true); + children = zk.getChildren(path, null); LeaderElector.sortSeqs(children); return children; } catch (Exception e) { @@ -465,7 +464,7 @@ public static String getLeaderId(SolrZkClient zkClient) throws KeeperException, InterruptedException { byte[] data = null; try { - data = zkClient.getData(Overseer.OVERSEER_ELECT + "/leader", null, new Stat(), true); + data = zkClient.getData(Overseer.OVERSEER_ELECT + "/leader", null, new Stat()); } catch (KeeperException.NoNodeException e) { return null; } @@ -481,9 +480,7 @@ protected LeaderStatus amILeader() { try { ZkNodeProps props = ZkNodeProps.load( - zkStateReader - .getZkClient() - .getData(Overseer.OVERSEER_ELECT + "/leader", null, null, true)); + zkStateReader.getZkClient().getData(Overseer.OVERSEER_ELECT + "/leader", null, null)); propsId = props.getStr(ID); if (myId.equals(propsId)) { return LeaderStatus.YES; @@ -602,7 +599,7 @@ public void run() { response.getResponse()); } success = true; - } catch (AlreadyClosedException ignore) { + } catch (IllegalStateException ignore) { } catch (KeeperException e) { log.error("KeeperException", e); @@ -617,7 +614,7 @@ public void run() { // Reset task from tracking data structures so that it can be retried. try { resetTaskWithException(messageHandler, head.getId(), asyncId, taskKey, message); - } catch (AlreadyClosedException ignore) { + } catch (IllegalStateException ignore) { } } diff --git a/solr/core/src/java/org/apache/solr/cloud/OverseerTaskQueue.java b/solr/core/src/java/org/apache/solr/cloud/OverseerTaskQueue.java index 3092dce185e..a7b81e2889e 100644 --- a/solr/core/src/java/org/apache/solr/cloud/OverseerTaskQueue.java +++ b/solr/core/src/java/org/apache/solr/cloud/OverseerTaskQueue.java @@ -77,12 +77,12 @@ public void allowOverseerPendingTasksToComplete() { public boolean containsTaskWithRequestId(String requestIdKey, String requestId) throws KeeperException, InterruptedException { - List childNames = zookeeper.getChildren(dir, null, true); + List childNames = zookeeper.getChildren(dir, null); stats.setQueueLength(childNames.size()); for (String childName : childNames) { if (childName != null && childName.startsWith(PREFIX)) { try { - byte[] data = zookeeper.getData(dir + "/" + childName, null, null, true); + byte[] data = zookeeper.getData(dir + "/" + childName, null, null); if (data != null) { ZkNodeProps message = ZkNodeProps.load(data); if (message.containsKey(requestIdKey)) { @@ -109,7 +109,7 @@ public void remove(QueueEvent event) throws KeeperException, InterruptedExceptio String responsePath = dir + "/" + RESPONSE_PREFIX + path.substring(path.lastIndexOf('-') + 1); try { - zookeeper.setData(responsePath, event.getBytes(), true); + zookeeper.setData(responsePath, event.getBytes()); } catch (KeeperException.NoNodeException ignored) { // we must handle the race case where the node no longer exists log.info( @@ -117,7 +117,7 @@ public void remove(QueueEvent event) throws KeeperException, InterruptedExceptio responsePath); } try { - zookeeper.delete(path, -1, true); + zookeeper.delete(path, -1); } catch (KeeperException.NoNodeException ignored) { } } finally { @@ -196,10 +196,10 @@ private String createData(String path, byte[] data, CreateMode mode) throws KeeperException, InterruptedException { for (; ; ) { try { - return zookeeper.create(path, data, mode, true); + return zookeeper.create(path, data, mode); } catch (KeeperException.NoNodeException e) { try { - zookeeper.create(dir, new byte[0], CreateMode.PERSISTENT, true); + zookeeper.create(dir, new byte[0], CreateMode.PERSISTENT); } catch (KeeperException.NodeExistsException ne) { // someone created it } @@ -221,7 +221,7 @@ public QueueEvent offer(byte[] data, long timeout) throws KeeperException, Inter String watchID = createResponseNode(); LatchWatcher watcher = new LatchWatcher(); - Stat stat = zookeeper.exists(watchID, watcher, true); + Stat stat = zookeeper.exists(watchID, watcher); // create the request node createRequestNode(data, watchID); @@ -230,11 +230,11 @@ public QueueEvent offer(byte[] data, long timeout) throws KeeperException, Inter pendingResponses.incrementAndGet(); watcher.await(timeout); } - byte[] bytes = zookeeper.getData(watchID, null, null, true); + byte[] bytes = zookeeper.getData(watchID, null, null); // create the event before deleting the node, otherwise we can get the deleted // event from the watcher. QueueEvent event = new QueueEvent(watchID, bytes, watcher.getWatchedEvent()); - zookeeper.delete(watchID, -1, true); + zookeeper.delete(watchID, -1); return event; } finally { time.stop(); @@ -295,9 +295,7 @@ public String getTailId() throws KeeperException, InterruptedException { try { QueueEvent queueEvent = new QueueEvent( - dir + "/" + headNode, - zookeeper.getData(dir + "/" + headNode, null, null, true), - null); + dir + "/" + headNode, zookeeper.getData(dir + "/" + headNode, null, null), null); return queueEvent.getId(); } catch (KeeperException.NoNodeException e) { // Another client removed the node first, try next diff --git a/solr/core/src/java/org/apache/solr/cloud/RefreshCollectionMessage.java b/solr/core/src/java/org/apache/solr/cloud/RefreshCollectionMessage.java index fee0d32bf50..c09a38d418c 100644 --- a/solr/core/src/java/org/apache/solr/cloud/RefreshCollectionMessage.java +++ b/solr/core/src/java/org/apache/solr/cloud/RefreshCollectionMessage.java @@ -40,7 +40,7 @@ public ClusterState run(ClusterState clusterState, Overseer overseer, ZkStateWri overseer .getZkStateReader() .getZkClient() - .exists(DocCollection.getCollectionPath(collection), null, true); + .exists(DocCollection.getCollectionPath(collection), null); if (stat == null) { // collection does not exist return clusterState.copyWith(collection, null); diff --git a/solr/core/src/java/org/apache/solr/cloud/ShardLeaderElectionContext.java b/solr/core/src/java/org/apache/solr/cloud/ShardLeaderElectionContext.java index c57a43980b1..743f10a4524 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ShardLeaderElectionContext.java +++ b/solr/core/src/java/org/apache/solr/cloud/ShardLeaderElectionContext.java @@ -443,7 +443,7 @@ private boolean waitForReplicasToComeUp(int timeoutms) throws InterruptedExcepti if (slices != null) { int found = 0; try { - found = zkClient.getChildren(shardsElectZkPath, null, true).size(); + found = zkClient.getChildren(shardsElectZkPath, null).size(); } catch (KeeperException e) { if (e instanceof KeeperException.SessionExpiredException) { // if the session has expired, then another election will be launched, so diff --git a/solr/core/src/java/org/apache/solr/cloud/ShardLeaderElectionContextBase.java b/solr/core/src/java/org/apache/solr/cloud/ShardLeaderElectionContextBase.java index 32706698d8b..f7544f094ec 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ShardLeaderElectionContextBase.java +++ b/solr/core/src/java/org/apache/solr/cloud/ShardLeaderElectionContextBase.java @@ -19,6 +19,8 @@ import java.lang.invoke.MethodHandles; import java.util.List; +import org.apache.curator.framework.api.transaction.CuratorTransactionResult; +import org.apache.curator.framework.api.transaction.OperationType; import org.apache.solr.cloud.overseer.OverseerAction; import org.apache.solr.common.SolrException; import org.apache.solr.common.SolrException.ErrorCode; @@ -36,11 +38,6 @@ import org.apache.zookeeper.KeeperException; import org.apache.zookeeper.KeeperException.NoNodeException; import org.apache.zookeeper.KeeperException.NodeExistsException; -import org.apache.zookeeper.Op; -import org.apache.zookeeper.OpResult; -import org.apache.zookeeper.OpResult.SetDataResult; -import org.apache.zookeeper.ZooDefs; -import org.apache.zookeeper.data.Stat; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -106,10 +103,11 @@ public void cancelElection() throws InterruptedException, KeeperException { leaderPath, leaderZkNodeParentVersion); String parent = ZkMaintenanceUtils.getZkParent(leaderPath); - List ops = - List.of(Op.check(parent, leaderZkNodeParentVersion), Op.delete(leaderPath, -1)); - zkClient.multi(ops, true); + zkClient.multi( + op -> op.check().withVersion(leaderZkNodeParentVersion).forPath(parent), + op -> op.delete().withVersion(-1).forPath(leaderPath)); } catch (InterruptedException e) { + Thread.currentThread().interrupt(); throw e; } catch (IllegalArgumentException e) { log.error("Illegal argument", e); @@ -144,27 +142,25 @@ void runLeaderProcess(boolean weAreReplacement, int pauseBeforeStartMs) // be used to make sure we only remove our own leader registration node. // The setData call used to get the parent version is also the trigger to // increment the version. We also do a sanity check that our leaderSeqPath exists. - List ops = - List.of( - Op.check(leaderSeqPath, -1), - Op.create( - leaderPath, - Utils.toJSON(leaderProps), - zkClient.getZkACLProvider().getACLsToAdd(leaderPath), - CreateMode.EPHEMERAL), - Op.setData(parent, null, -1)); - List results; - - results = zkClient.multi(ops, true); - for (OpResult result : results) { - if (result.getType() == ZooDefs.OpCode.setData) { - SetDataResult dresult = (SetDataResult) result; - Stat stat = dresult.getStat(); - leaderZkNodeParentVersion = stat.getVersion(); - return; - } - } - assert leaderZkNodeParentVersion != null; + List results = + zkClient.multi( + op -> op.check().withVersion(-1).forPath(leaderSeqPath), + op -> + op.create() + .withMode(CreateMode.EPHEMERAL) + .forPath(leaderPath, Utils.toJSON(leaderProps)), + op -> op.setData().withVersion(-1).forPath(parent, null)); + leaderZkNodeParentVersion = + results.stream() + .filter( + CuratorTransactionResult.ofTypeAndPath(OperationType.SET_DATA, parent)) + .findFirst() + .orElseThrow( + () -> + new RuntimeException( + "Could not set data for parent path in ZK: " + parent)) + .getResultStat() + .getVersion(); } }); } catch (NoNodeException e) { diff --git a/solr/core/src/java/org/apache/solr/cloud/SizeLimitedDistributedMap.java b/solr/core/src/java/org/apache/solr/cloud/SizeLimitedDistributedMap.java index c4c8923b218..510c0f1c1f5 100644 --- a/solr/core/src/java/org/apache/solr/cloud/SizeLimitedDistributedMap.java +++ b/solr/core/src/java/org/apache/solr/cloud/SizeLimitedDistributedMap.java @@ -65,7 +65,7 @@ public boolean putIfAbsent(String trackingId, byte[] data) private void shrinkIfNeeded() throws KeeperException, InterruptedException { if (this.size() >= maxSize) { // Bring down the size - List children = zookeeper.getChildren(dir, null, true); + List children = zookeeper.getChildren(dir, null); int cleanupSize = maxSize / 10; @@ -79,7 +79,7 @@ protected boolean lessThan(Long a, Long b) { Map childToModificationZxid = CollectionUtil.newHashMap(children.size()); for (String child : children) { - Stat stat = zookeeper.exists(dir + "/" + child, null, true); + Stat stat = zookeeper.exists(dir + "/" + child, null); if (stat != null) { priorityQueue.insertWithOverflow(stat.getMzxid()); childToModificationZxid.put(child, stat.getMzxid()); diff --git a/solr/core/src/java/org/apache/solr/cloud/ZkCLI.java b/solr/core/src/java/org/apache/solr/cloud/ZkCLI.java index 8e058a32a9a..45e7895cc63 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ZkCLI.java +++ b/solr/core/src/java/org/apache/solr/cloud/ZkCLI.java @@ -398,7 +398,7 @@ public static void main(String[] args) stdout.println("-" + MAKEPATH + " requires one arg - the path to make"); System.exit(1); } - zkClient.makePath(arglist.get(0), true); + zkClient.makePath(arglist.get(0)); } else if (line.getOptionValue(CMD).equalsIgnoreCase(PUT)) { List arglist = line.getArgList(); if (arglist.size() != 2) { @@ -406,16 +406,17 @@ public static void main(String[] args) "-" + PUT + " requires two args - the path to create and the data string"); System.exit(1); } + String path = arglist.get(0); byte[] data = arglist.get(1).getBytes(StandardCharsets.UTF_8); if (shouldCompressData(data, path, minStateByteLenForCompression)) { // state.json should be compressed before being put to ZK data = compressor.compressBytes(data, data.length / 10); } - if (zkClient.exists(path, true)) { - zkClient.setData(path, data, true); + if (zkClient.exists(path)) { + zkClient.setData(path, data); } else { - zkClient.makePath(path, data, CreateMode.PERSISTENT, true); + zkClient.makePath(path, data, CreateMode.PERSISTENT); } } else if (line.getOptionValue(CMD).equalsIgnoreCase(PUT_FILE)) { List arglist = line.getArgList(); @@ -433,10 +434,10 @@ public static void main(String[] args) // state.json should be compressed before being put to ZK data = compressor.compressBytes(data, data.length / 10); } - if (zkClient.exists(path, true)) { - zkClient.setData(path, data, true); + if (zkClient.exists(path)) { + zkClient.setData(path, data); } else { - zkClient.makePath(path, data, CreateMode.PERSISTENT, true); + zkClient.makePath(path, data, CreateMode.PERSISTENT); } } else if (line.getOptionValue(CMD).equalsIgnoreCase(GET)) { List arglist = line.getArgList(); @@ -444,7 +445,7 @@ public static void main(String[] args) stdout.println("-" + GET + " requires one arg - the path to get"); System.exit(1); } - byte[] data = zkClient.getData(arglist.get(0), null, null, true); + byte[] data = zkClient.getData(arglist.get(0), null, null); stdout.println(new String(data, StandardCharsets.UTF_8)); } else if (line.getOptionValue(CMD).equalsIgnoreCase(GET_FILE)) { List arglist = line.getArgList(); @@ -453,7 +454,7 @@ public static void main(String[] args) "-" + GET_FILE + "requires two args - the path to get and the file to save it to"); System.exit(1); } - byte[] data = zkClient.getData(arglist.get(0), null, null, true); + byte[] data = zkClient.getData(arglist.get(0), null, null); Files.write(Path.of(arglist.get(1)), data); } else if (line.getOptionValue(CMD).equals(UPDATEACLS)) { List arglist = line.getArgList(); diff --git a/solr/core/src/java/org/apache/solr/cloud/ZkConfigSetService.java b/solr/core/src/java/org/apache/solr/cloud/ZkConfigSetService.java index 1718edbf56a..fa3f1b4037b 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ZkConfigSetService.java +++ b/solr/core/src/java/org/apache/solr/cloud/ZkConfigSetService.java @@ -72,7 +72,7 @@ public SolrResourceLoader createCoreResourceLoader(CoreDescriptor cd) { // For back compat with cores that can create collections without the collections API try { - if (!zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + colName, true)) { + if (!zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + colName)) { // TODO remove this functionality or maybe move to a CLI mechanism log.warn( "Auto-creating collection (in ZK) from core descriptor (on disk). This feature may go away!"); @@ -117,7 +117,7 @@ protected Long getCurrentSchemaModificationVersion( String zkPath = CONFIGS_ZKNODE + "/" + configSet + "/" + schemaFile; Stat stat; try { - stat = zkClient.exists(zkPath, null, true); + stat = zkClient.exists(zkPath, null); } catch (KeeperException e) { log.warn("Unexpected exception when getting modification time of {}", zkPath, e); return null; // debatable; we'll see an error soon if there's a real problem @@ -139,7 +139,7 @@ public String configSetName(CoreDescriptor cd) { @Override public boolean checkConfigExists(String configName) throws IOException { try { - return zkClient.exists(CONFIGS_ZKNODE + "/" + configName, true); + return zkClient.exists(CONFIGS_ZKNODE + "/" + configName); } catch (KeeperException | InterruptedException e) { throw new IOException( "Error checking whether config exists", SolrZkClient.checkInterrupted(e)); @@ -200,7 +200,7 @@ public void uploadFileToConfig( log.warn("Not including uploading file to config, as it is a forbidden type: {}", fileName); } else { // if overwriteOnExists is true then zkClient#makePath failOnExists is set to false - zkClient.makePath(filePath, data, CreateMode.PERSISTENT, null, !overwriteOnExists, true); + zkClient.makePath(filePath, data, CreateMode.PERSISTENT, null, !overwriteOnExists); } } catch (KeeperException.NodeExistsException nodeExistsException) { throw new SolrException( @@ -224,8 +224,7 @@ public void setConfigMetadata(String configName, Map data) throw Utils.toJSON(data), CreateMode.PERSISTENT, null, - false, - true); + false); } catch (KeeperException | InterruptedException e) { throw new IOException("Error setting config metadata", SolrZkClient.checkInterrupted(e)); } @@ -237,7 +236,7 @@ public Map getConfigMetadata(String configName) throws IOExcepti @SuppressWarnings("unchecked") Map data = (Map) - Utils.fromJSON(zkClient.getData(CONFIGS_ZKNODE + "/" + configName, null, null, true)); + Utils.fromJSON(zkClient.getData(CONFIGS_ZKNODE + "/" + configName, null, null)); return data; } catch (KeeperException | InterruptedException e) { throw new IOException("Error getting config metadata", SolrZkClient.checkInterrupted(e)); @@ -252,7 +251,7 @@ public void downloadConfig(String configName, Path dir) throws IOException { @Override public byte[] downloadFileFromConfig(String configName, String filePath) throws IOException { try { - return zkClient.getData(CONFIGS_ZKNODE + "/" + configName + "/" + filePath, null, null, true); + return zkClient.getData(CONFIGS_ZKNODE + "/" + configName + "/" + filePath, null, null); } catch (KeeperException.NoNodeException e) { return null; } catch (KeeperException | InterruptedException e) { @@ -263,7 +262,7 @@ public byte[] downloadFileFromConfig(String configName, String filePath) throws @Override public List listConfigs() throws IOException { try { - return zkClient.getChildren(CONFIGS_ZKNODE, null, true); + return zkClient.getChildren(CONFIGS_ZKNODE, null); } catch (KeeperException.NoNodeException e) { return Collections.emptyList(); } catch (KeeperException | InterruptedException e) { @@ -310,9 +309,9 @@ public List getAllConfigFiles(String configName) throws IOException { private void copyConfigDirFromZk(String fromZkPath, String toZkPath) throws IOException { try { - List files = zkClient.getChildren(fromZkPath, null, true); + List files = zkClient.getChildren(fromZkPath, null); for (String file : files) { - List children = zkClient.getChildren(fromZkPath + "/" + file, null, true); + List children = zkClient.getChildren(fromZkPath + "/" + file, null); if (children.size() == 0) { copyData(fromZkPath + "/" + file, toZkPath + "/" + file); } else { @@ -338,8 +337,8 @@ private void copyData(String fromZkFilePath, String toZkFilePath) toZkFilePath); } else { log.debug("Copying zk node {} to {}", fromZkFilePath, toZkFilePath); - byte[] data = zkClient.getData(fromZkFilePath, null, null, true); - zkClient.makePath(toZkFilePath, data, true); + byte[] data = zkClient.getData(fromZkFilePath, null, null); + zkClient.makePath(toZkFilePath, data); } } diff --git a/solr/core/src/java/org/apache/solr/cloud/ZkController.java b/solr/core/src/java/org/apache/solr/cloud/ZkController.java index c27e79c8274..44e72a76d84 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ZkController.java +++ b/solr/core/src/java/org/apache/solr/cloud/ZkController.java @@ -53,6 +53,7 @@ import java.util.concurrent.TimeoutException; import java.util.concurrent.atomic.AtomicReference; import java.util.function.Supplier; +import org.apache.curator.framework.api.ACLProvider; import org.apache.solr.client.solrj.SolrClient; import org.apache.solr.client.solrj.cloud.SolrCloudManager; import org.apache.solr.client.solrj.impl.CloudLegacySolrClient; @@ -69,7 +70,6 @@ import org.apache.solr.common.SolrException; import org.apache.solr.common.SolrException.ErrorCode; import org.apache.solr.common.cloud.ClusterState; -import org.apache.solr.common.cloud.DefaultConnectionStrategy; import org.apache.solr.common.cloud.DefaultZkACLProvider; import org.apache.solr.common.cloud.DefaultZkCredentialsInjector; import org.apache.solr.common.cloud.DefaultZkCredentialsProvider; @@ -86,7 +86,6 @@ import org.apache.solr.common.cloud.Slice; import org.apache.solr.common.cloud.SolrZkClient; import org.apache.solr.common.cloud.ZkACLProvider; -import org.apache.solr.common.cloud.ZkClientConnectionStrategy; import org.apache.solr.common.cloud.ZkCoreNodeProps; import org.apache.solr.common.cloud.ZkCredentialsInjector; import org.apache.solr.common.cloud.ZkCredentialsProvider; @@ -124,7 +123,6 @@ import org.apache.zookeeper.KeeperException; import org.apache.zookeeper.KeeperException.NoNodeException; import org.apache.zookeeper.KeeperException.SessionExpiredException; -import org.apache.zookeeper.Op; import org.apache.zookeeper.WatchedEvent; import org.apache.zookeeper.Watcher; import org.apache.zookeeper.data.ACL; @@ -231,6 +229,8 @@ public String toString() { private boolean genericCoreNodeNames; + private int clientTimeout; + private volatile boolean isClosed; private final ConcurrentHashMap replicasMetTragicEvent = @@ -327,12 +327,6 @@ public ZkController( this.leaderVoteWait = cloudConfig.getLeaderVoteWait(); this.leaderConflictResolveWait = cloudConfig.getLeaderConflictResolveWait(); - int clientTimeout = cloudConfig.getZkClientTimeout(); - - String connectionStrategy = System.getProperty("solr.zookeeper.connectionStrategy"); - ZkClientConnectionStrategy strat = - ZkClientConnectionStrategy.forName(connectionStrategy, new DefaultConnectionStrategy()); - String zkCredentialsInjectorClass = cloudConfig.getZkCredentialsInjectorClass(); ZkCredentialsInjector zkCredentialsInjector = StrUtils.isNullOrEmpty(zkCredentialsInjectorClass) @@ -340,6 +334,8 @@ public ZkController( : cc.getResourceLoader() .newInstance(zkCredentialsInjectorClass, ZkCredentialsInjector.class); + this.clientTimeout = cloudConfig.getZkClientTimeout(); + String zkACLProviderClass = cloudConfig.getZkACLProviderClass(); ZkACLProvider zkACLProvider = StrUtils.isNullOrEmpty(zkACLProviderClass) @@ -355,7 +351,6 @@ public ZkController( .newInstance(zkCredentialsProviderClass, ZkCredentialsProvider.class); zkCredentialsProvider.setZkCredentialsInjector(zkCredentialsInjector); - strat.setZkCredentialsToAddAutomatically(zkCredentialsProvider); addOnReconnectListener(getConfigDirListener()); String stateCompressionProviderClass = cloudConfig.getStateCompressorClass(); @@ -369,7 +364,6 @@ public ZkController( .withUrl(zkServerAddress) .withTimeout(clientTimeout, TimeUnit.MILLISECONDS) .withConnTimeOut(zkClientConnectTimeout, TimeUnit.MILLISECONDS) - .withConnStrategy(strat) .withReconnectListener(() -> onReconnect(descriptorsSupplier)) .withBeforeConnect(() -> beforeReconnect(descriptorsSupplier)) .withAclProvider(zkACLProvider) @@ -417,8 +411,7 @@ private void beforeReconnect(Supplier> descriptorsSupplier) markAllAsNotLeader(descriptorsSupplier); } - private void onReconnect(Supplier> descriptorsSupplier) - throws SessionExpiredException { + private void onReconnect(Supplier> descriptorsSupplier) { // on reconnect, reload cloud info log.info("ZooKeeper session re-connected ... refreshing core states after session expiration."); clearZkCollectionTerms(); @@ -519,8 +512,6 @@ private void onReconnect(Supplier> descriptorsSupplier) // Restore the interrupted status Thread.currentThread().interrupt(); throw new ZooKeeperException(ErrorCode.SERVER_ERROR, "", e); - } catch (SessionExpiredException e) { - throw e; } catch (Exception e) { log.error("Exception during reconnect", e); throw new ZooKeeperException(ErrorCode.SERVER_ERROR, "", e); @@ -535,18 +526,17 @@ private void onReconnect(Supplier> descriptorsSupplier) */ private void checkNoOldClusterstate(final SolrZkClient zkClient) throws InterruptedException { try { - if (!zkClient.exists(ZkStateReader.UNSUPPORTED_CLUSTER_STATE, true)) { + if (!zkClient.exists(ZkStateReader.UNSUPPORTED_CLUSTER_STATE)) { return; } - final byte[] data = - zkClient.getData(ZkStateReader.UNSUPPORTED_CLUSTER_STATE, null, null, true); + final byte[] data = zkClient.getData(ZkStateReader.UNSUPPORTED_CLUSTER_STATE, null, null); if (Arrays.equals("{}".getBytes(StandardCharsets.UTF_8), data)) { // Empty json. This log will only occur once. log.warn( "{} no longer supported starting with Solr 9. Found empty file on Zookeeper, deleting it.", ZkStateReader.UNSUPPORTED_CLUSTER_STATE); - zkClient.delete(ZkStateReader.UNSUPPORTED_CLUSTER_STATE, -1, true); + zkClient.delete(ZkStateReader.UNSUPPORTED_CLUSTER_STATE, -1); } else { // /clusterstate.json not empty: refuse to start but do not automatically delete. A bit of a // pain but user shouldn't have older collections at this stage anyway. @@ -610,8 +600,7 @@ private void registerAllCoresAsDown( + "/leader_elect/" + slice + "/election", - null, - true) + null) .size(); if (children == 0) { log.debug( @@ -701,7 +690,7 @@ public void preClose() { try { this.removeEphemeralLiveNode(); - } catch (AlreadyClosedException + } catch (IllegalStateException | SessionExpiredException | KeeperException.ConnectionLossException e) { @@ -710,7 +699,7 @@ public void preClose() { } try { - if (getZkClient().getConnectionManager().isConnected()) { + if (getZkClient().isConnected()) { log.info("Publish this node as DOWN..."); publishNodeAsDown(getNodeName()); } @@ -933,13 +922,13 @@ public static void createClusterZkNodes(SolrZkClient zkClient) private static void repairSecurityJson(SolrZkClient zkClient) throws KeeperException, InterruptedException { - List securityConfAcl = zkClient.getACL(ZkStateReader.SOLR_SECURITY_CONF_PATH, null, true); - ZkACLProvider aclProvider = zkClient.getZkACLProvider(); + List securityConfAcl = zkClient.getACL(ZkStateReader.SOLR_SECURITY_CONF_PATH, null); + ACLProvider aclProvider = zkClient.getZkACLProvider(); boolean tryUpdate = false; if (OPEN_ACL_UNSAFE.equals(securityConfAcl)) { - List aclToAdd = aclProvider.getACLsToAdd(ZkStateReader.SOLR_SECURITY_CONF_PATH); + List aclToAdd = aclProvider.getAclForPath(ZkStateReader.SOLR_SECURITY_CONF_PATH); if (OPEN_ACL_UNSAFE.equals(aclToAdd)) { log.warn( "Contents of zookeeper /security.json are world-readable;" @@ -949,7 +938,7 @@ private static void repairSecurityJson(SolrZkClient zkClient) } } else if (aclProvider instanceof SecurityAwareZkACLProvider) { // Use Set to explicitly ignore order - Set nonSecureACL = new HashSet<>(aclProvider.getACLsToAdd(null)); + Set nonSecureACL = new HashSet<>(aclProvider.getDefaultAcl()); // case where security.json was not treated as a secure path if (nonSecureACL.equals(new HashSet<>(securityConfAcl))) { tryUpdate = true; @@ -1000,7 +989,7 @@ private void init() { } } - Stat stat = zkClient.exists(ZkStateReader.LIVE_NODES_ZKNODE, null, true); + Stat stat = zkClient.exists(ZkStateReader.LIVE_NODES_ZKNODE, null); if (stat != null && stat.getNumChildren() > 0) { publishAndWaitForDownStates(); } @@ -1029,7 +1018,7 @@ private void checkForExistingEphemeralNode() throws KeeperException, Interrupted String nodeName = getNodeName(); String nodePath = ZkStateReader.LIVE_NODES_ZKNODE + "/" + nodeName; - if (!zkClient.exists(nodePath, true)) { + if (!zkClient.exists(nodePath)) { return; } @@ -1044,8 +1033,7 @@ private void checkForExistingEphemeralNode() throws KeeperException, Interrupted if (Watcher.Event.EventType.NodeDeleted.equals(event.getType())) { deletedLatch.countDown(); } - }, - true); + }); if (stat == null) { // znode suddenly disappeared but that's okay @@ -1053,7 +1041,7 @@ private void checkForExistingEphemeralNode() throws KeeperException, Interrupted } boolean deleted = - deletedLatch.await(zkClient.getZooKeeper().getSessionTimeout() * 2L, TimeUnit.MILLISECONDS); + deletedLatch.await(zkClient.getZkSessionTimeout() * 2L, TimeUnit.MILLISECONDS); if (!deleted) { throw new SolrException( ErrorCode.SERVER_ERROR, @@ -1159,10 +1147,10 @@ public static boolean checkChrootPath(String zkHost, boolean create) .withTimeout(SolrZkClientTimeout.DEFAULT_ZK_CLIENT_TIMEOUT, TimeUnit.MILLISECONDS) .withConnTimeOut(SolrZkClientTimeout.DEFAULT_ZK_CONNECT_TIMEOUT, TimeUnit.MILLISECONDS) .build(); - boolean exists = tmpClient.exists(chrootPath, true); + boolean exists = tmpClient.exists(chrootPath); if (!exists && create) { log.info("creating chroot {}", chrootPath); - tmpClient.makePath(chrootPath, false, true); + tmpClient.makePath(chrootPath, false); exists = true; } tmpClient.close(); @@ -1182,25 +1170,19 @@ private void createEphemeralLiveNode() throws KeeperException, InterruptedExcept String nodePath = ZkStateReader.LIVE_NODES_ZKNODE + "/" + nodeName; log.info("Register node as live in ZooKeeper:{}", nodePath); Map roles = cc.nodeRoles.getRoles(); - List ops = new ArrayList<>(roles.size() + 1); - ops.add( - Op.create( - nodePath, - null, - zkClient.getZkACLProvider().getACLsToAdd(nodePath), - CreateMode.EPHEMERAL)); + List ops = new ArrayList<>(2); + ops.add(op -> op.create().withMode(CreateMode.EPHEMERAL).forPath(nodePath)); // Create the roles node as well roles.forEach( (role, mode) -> ops.add( - Op.create( - NodeRoles.getZNodeForRoleMode(role, mode) + "/" + nodeName, - null, - zkClient.getZkACLProvider().getACLsToAdd(nodePath), - CreateMode.EPHEMERAL))); + op -> + op.create() + .withMode(CreateMode.EPHEMERAL) + .forPath(NodeRoles.getZNodeForRoleMode(role, mode) + "/" + nodeName))); - zkClient.multi(ops, true); + zkClient.multi(ops); } public void removeEphemeralLiveNode() throws KeeperException, InterruptedException { @@ -1210,10 +1192,8 @@ public void removeEphemeralLiveNode() throws KeeperException, InterruptedExcepti String nodeName = getNodeName(); String nodePath = ZkStateReader.LIVE_NODES_ZKNODE + "/" + nodeName; log.info("Remove node as live in ZooKeeper:{}", nodePath); - List ops = List.of(Op.delete(nodePath, -1)); - try { - zkClient.multi(ops, true); + zkClient.delete(nodePath, -1); } catch (NoNodeException e) { } @@ -1225,7 +1205,7 @@ public String getNodeName() { /** Returns true if the path exists */ public boolean pathExists(String path) throws KeeperException, InterruptedException { - return zkClient.exists(path, true); + return zkClient.exists(path); } /** @@ -1501,7 +1481,7 @@ private String getLeader(final CloudDescriptor cloudDesc, int timeoutms) { leaderUrl = getLeaderProps(collection, cloudDesc.getShardId(), timeoutms).getCoreUrl(); } - } catch (AlreadyClosedException e) { + } catch (IllegalStateException e) { throw e; } catch (Exception e) { log.error("Error getting leader from zk", e); @@ -1540,8 +1520,7 @@ public ZkCoreNodeProps getLeaderProps( while (iterCount-- > 0) { try { byte[] data = - zkClient.getData( - ZkStateReader.getShardLeadersPath(collection, slice), null, null, true); + zkClient.getData(ZkStateReader.getShardLeadersPath(collection, slice), null, null); ZkCoreNodeProps leaderProps = new ZkCoreNodeProps(ZkNodeProps.load(data)); return leaderProps; } catch (InterruptedException e) { @@ -2207,14 +2186,14 @@ public static void linkConfSet(SolrZkClient zkClient, String collection, String log.debug("Load collection config from:{}", path); byte[] data; try { - data = zkClient.getData(path, null, null, true); + data = zkClient.getData(path, null, null); } catch (NoNodeException e) { // if there is no node, we will try and create it // first try to make in case we are pre configuring ZkNodeProps props = new ZkNodeProps(CONFIGNAME_PROP, confSetName); try { - zkClient.makePath(path, Utils.toJSON(props), CreateMode.PERSISTENT, null, true); + zkClient.makePath(path, Utils.toJSON(props), CreateMode.PERSISTENT); } catch (KeeperException e2) { // it's okay if the node already exists if (e2.code() != KeeperException.Code.NODEEXISTS) { @@ -2222,7 +2201,7 @@ public static void linkConfSet(SolrZkClient zkClient, String collection, String } // if we fail creating, setdata // TODO: we should consider using version - zkClient.setData(path, Utils.toJSON(props), true); + zkClient.setData(path, Utils.toJSON(props)); } return; } @@ -2238,7 +2217,7 @@ public static void linkConfSet(SolrZkClient zkClient, String collection, String } // TODO: we should consider using version - zkClient.setData(path, Utils.toJSON(props), true); + zkClient.setData(path, Utils.toJSON(props)); } public ZkDistributedQueue getOverseerJobQueue() { @@ -2344,9 +2323,7 @@ public void rejoinOverseerElection(String electionNode, boolean joinAtHead) { if (electionNode.startsWith(getNodeName())) { try { zkClient.delete( - Overseer.OVERSEER_ELECT + LeaderElector.ELECTION_NODE + "/" + electionNode, - -1, - true); + Overseer.OVERSEER_ELECT + LeaderElector.ELECTION_NODE + "/" + electionNode, -1); } catch (NoNodeException e) { // no problem } catch (InterruptedException e) { @@ -2434,7 +2411,7 @@ public void rejoinShardLeaderElection(SolrParams params) { public void checkOverseerDesignate() { try { - byte[] data = zkClient.getData(ZkStateReader.ROLES, null, new Stat(), true); + byte[] data = zkClient.getData(ZkStateReader.ROLES, null, new Stat()); if (data == null) return; Map roles = (Map) Utils.fromJSON(data); if (roles == null) return; @@ -2540,7 +2517,7 @@ public static int persistConfigResourceToZooKeeper( String errMsg = "Failed to persist resource at {0} - old {1}"; try { try { - Stat stat = zkClient.setData(resourceLocation, content, znodeVersion, true); + Stat stat = zkClient.setData(resourceLocation, content, znodeVersion); // if the set succeeded, it should have incremented the version by one always latestVersion = stat.getVersion(); log.info("Persisted config data to node {} ", resourceLocation); @@ -2548,12 +2525,12 @@ public static int persistConfigResourceToZooKeeper( } catch (NoNodeException e) { if (createIfNotExists) { try { - zkClient.create(resourceLocation, content, CreateMode.PERSISTENT, true); + zkClient.create(resourceLocation, content, CreateMode.PERSISTENT); latestVersion = 0; // just created so version must be zero touchConfDir(zkLoader); } catch (KeeperException.NodeExistsException nee) { try { - Stat stat = zkClient.exists(resourceLocation, null, true); + Stat stat = zkClient.exists(resourceLocation, null); if (log.isDebugEnabled()) { log.debug( "failed to set data version in zk is {} and expected version is {} ", @@ -2576,7 +2553,7 @@ public static int persistConfigResourceToZooKeeper( } catch (KeeperException.BadVersionException bve) { try { - zkClient.exists(resourceLocation, null, true); + zkClient.exists(resourceLocation, null); } catch (Exception e) { log.error("Exception during ZooKeeper node checking ", e); } @@ -2700,7 +2677,7 @@ public void process(WatchedEvent event) { Stat stat = null; try { - stat = zkClient.exists(zkDir, null, true); + stat = zkClient.exists(zkDir, null); } catch (KeeperException e) { // ignore , it is not a big deal } catch (InterruptedException e) { @@ -2754,7 +2731,7 @@ private boolean fireEventListeners(String zkDir) { private void setConfWatcher(String zkDir, Watcher watcher, Stat stat) { try { - Stat newStat = zkClient.exists(zkDir, watcher, true); + Stat newStat = zkClient.exists(zkDir, watcher); if (stat != null && newStat.getVersion() > stat.getVersion()) { // a race condition where a we missed an event fired // so fire the event listeners @@ -2904,7 +2881,7 @@ public void publishNodeAsDown(String nodeName) { m -> m.put(Overseer.QUEUE_OPERATION, OverseerAction.DOWNNODE.toLower()) .put(ZkStateReader.NODE_NAME_PROP, nodeName)); - } catch (AlreadyClosedException e) { + } catch (IllegalStateException e) { log.info( "Not publishing node as DOWN because a resource required to do so is already closed."); } catch (InterruptedException e) { diff --git a/solr/core/src/java/org/apache/solr/cloud/ZkDistributedLock.java b/solr/core/src/java/org/apache/solr/cloud/ZkDistributedLock.java index ca29d53e9d7..469986960d6 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ZkDistributedLock.java +++ b/solr/core/src/java/org/apache/solr/cloud/ZkDistributedLock.java @@ -92,8 +92,7 @@ protected ZkDistributedLock(SolrZkClient zkClient, String lockDir, String lockNo + DistributedCollectionConfigSetCommandRunner.ZK_PATH_SEPARATOR + lockNodePrefix, null, - CreateMode.EPHEMERAL_SEQUENTIAL, - false); + CreateMode.EPHEMERAL_SEQUENTIAL); sequence = getSequenceFromNodename(lockNode); } @@ -141,7 +140,7 @@ public void waitUntilAcquired() { String nodeToWatch = nodeToWatch(); while (nodeToWatch != null) { final DeletedNodeWatcher watcher = new DeletedNodeWatcher(nodeToWatch); - if (zkClient.exists(nodeToWatch, watcher, true) != null) { + if (zkClient.exists(nodeToWatch, watcher) != null) { watcher.await(); } nodeToWatch = nodeToWatch(); @@ -157,7 +156,7 @@ public void waitUntilAcquired() { @Override public void release() { try { - zkClient.delete(lockNode, -1, true); + zkClient.delete(lockNode, -1); released = true; } catch (KeeperException e) { throw new SolrException(SolrException.ErrorCode.SERVER_ERROR, e); @@ -188,7 +187,7 @@ public boolean isAcquired() { * {@code null} if the lock is ours. */ String nodeToWatch() throws KeeperException, InterruptedException { - List locks = zkClient.getChildren(lockDir, null, true); + List locks = zkClient.getChildren(lockDir, null); boolean foundSelf = false; // For finding bugs or ZK bad behavior // We deviate from the ZK recipe here: we do not sort the list of nodes, and we stop waiting on // the first one we find that blocks us. This is done in O(n), whereas sorting is more diff --git a/solr/core/src/java/org/apache/solr/cloud/ZkDistributedLockFactory.java b/solr/core/src/java/org/apache/solr/cloud/ZkDistributedLockFactory.java index 54434c8e6bc..76696dc3942 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ZkDistributedLockFactory.java +++ b/solr/core/src/java/org/apache/solr/cloud/ZkDistributedLockFactory.java @@ -59,8 +59,8 @@ protected StringBuilder getPathPrefix() { private void makeLockPath(String lockNodePath) throws KeeperException, InterruptedException { try { - if (!zkClient.exists(lockNodePath, true)) { - zkClient.makePath(lockNodePath, new byte[0], CreateMode.PERSISTENT, true); + if (!zkClient.exists(lockNodePath)) { + zkClient.makePath(lockNodePath, new byte[0], CreateMode.PERSISTENT); } } catch (KeeperException.NodeExistsException nee) { // Some other thread (on this or another JVM) beat us to create the node, that's ok. diff --git a/solr/core/src/java/org/apache/solr/cloud/ZkDistributedQueue.java b/solr/core/src/java/org/apache/solr/cloud/ZkDistributedQueue.java index 57db14740c5..c8bc80615f0 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ZkDistributedQueue.java +++ b/solr/core/src/java/org/apache/solr/cloud/ZkDistributedQueue.java @@ -32,16 +32,16 @@ import java.util.concurrent.locks.Condition; import java.util.concurrent.locks.ReentrantLock; import java.util.function.Predicate; +import org.apache.curator.framework.api.transaction.CuratorTransactionResult; import org.apache.solr.client.solrj.cloud.DistributedQueue; import org.apache.solr.common.SolrException; import org.apache.solr.common.SolrException.ErrorCode; -import org.apache.solr.common.cloud.ConnectionManager.IsClosed; import org.apache.solr.common.cloud.SolrZkClient; +import org.apache.solr.common.cloud.SolrZkClient.IsClosed; import org.apache.solr.common.cloud.ZkMaintenanceUtils; import org.apache.solr.common.util.Pair; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.Op; import org.apache.zookeeper.WatchedEvent; import org.apache.zookeeper.Watcher; import org.apache.zookeeper.data.Stat; @@ -246,24 +246,19 @@ public byte[] remove() throws NoSuchElementException, KeeperException, Interrupt public void remove(Collection paths) throws KeeperException, InterruptedException { if (paths.isEmpty()) return; - List ops = new ArrayList<>(); + List ops = new ArrayList<>(); for (String path : paths) { - ops.add(Op.delete(dir + "/" + path, -1)); + ops.add(op -> op.delete().withVersion(-1).forPath(dir + "/" + path)); } for (int from = 0; from < ops.size(); from += 1000) { int to = Math.min(from + 1000, ops.size()); if (from < to) { - try { - zookeeper.multi(ops.subList(from, to), true); - } catch (KeeperException.NoNodeException e) { - // don't know which nodes are not exist, so try to delete one by one node - for (int j = from; j < to; j++) { + Collection results = zookeeper.multi(ops.subList(from, to)); + for (CuratorTransactionResult result : results) { + if (result.getError() != 0) { try { - zookeeper.delete(ops.get(j).getPath(), -1, true); - } catch (KeeperException.NoNodeException e2) { - if (log.isDebugEnabled()) { - log.debug("Can not remove node which is not exist : {}", ops.get(j).getPath()); - } + zookeeper.delete(result.getForPath(), -1); + } catch (KeeperException.NoNodeException ignored) { } } } @@ -319,7 +314,7 @@ public void offer(byte[] data) throws KeeperException, InterruptedException { if (maxQueueSize > 0) { if (offerPermits.get() <= 0 || offerPermits.getAndDecrement() <= 0) { // If a max queue size is set, check it before creating a new queue item. - Stat stat = zookeeper.exists(dir, null, true); + Stat stat = zookeeper.exists(dir, null); if (stat == null) { // jump to the code below, which tries to create dir if it doesn't exist throw new KeeperException.NoNodeException(); @@ -337,12 +332,12 @@ public void offer(byte[] data) throws KeeperException, InterruptedException { // Explicitly set isDirty here so that synchronous same-thread calls behave as expected. // This will get set again when the watcher actually fires, but that's ok. - zookeeper.create(dir + "/" + PREFIX, data, CreateMode.PERSISTENT_SEQUENTIAL, true); + zookeeper.create(dir + "/" + PREFIX, data, CreateMode.PERSISTENT_SEQUENTIAL); isDirty = true; return; } catch (KeeperException.NoNodeException e) { try { - zookeeper.create(dir, new byte[0], CreateMode.PERSISTENT, true); + zookeeper.create(dir, new byte[0], CreateMode.PERSISTENT); } catch (KeeperException.NodeExistsException ne) { // someone created it } @@ -429,7 +424,7 @@ TreeSet fetchZkChildren(Watcher watcher) throws InterruptedException, Ke try { TreeSet orderedChildren = new TreeSet<>(); - List childNames = zookeeper.getChildren(dir, watcher, true); + List childNames = zookeeper.getChildren(dir, watcher); stats.setQueueLength(childNames.size()); for (String childName : childNames) { // Check format @@ -441,7 +436,7 @@ TreeSet fetchZkChildren(Watcher watcher) throws InterruptedException, Ke } return orderedChildren; } catch (KeeperException.NoNodeException e) { - zookeeper.makePath(dir, false, true); + zookeeper.makePath(dir, false); // go back to the loop and try again } } @@ -504,7 +499,7 @@ public Collection> peekElements( break; } try { - byte[] data = zookeeper.getData(dir + "/" + child, null, null, true); + byte[] data = zookeeper.getData(dir + "/" + child, null, null); result.add(new Pair<>(child, data)); } catch (KeeperException.NoNodeException e) { // Another client deleted the node first, remove the in-memory and continue. @@ -531,7 +526,7 @@ private byte[] firstElement() throws KeeperException, InterruptedException { return null; } try { - return zookeeper.getData(dir + "/" + firstChild, null, null, true); + return zookeeper.getData(dir + "/" + firstChild, null, null); } catch (KeeperException.NoNodeException e) { // Another client deleted the node first, remove the in-memory and retry. updateLock.lockInterruptibly(); @@ -554,8 +549,8 @@ private byte[] removeFirst() throws KeeperException, InterruptedException { } try { String path = dir + "/" + firstChild; - byte[] result = zookeeper.getData(path, null, null, true); - zookeeper.delete(path, -1, true); + byte[] result = zookeeper.getData(path, null, null); + zookeeper.delete(path, -1); stats.setQueueLength(knownChildren.size()); return result; } catch (KeeperException.NoNodeException e) { diff --git a/solr/core/src/java/org/apache/solr/cloud/ZkShardTerms.java b/solr/core/src/java/org/apache/solr/cloud/ZkShardTerms.java index 796e7961a93..1c856b1a5d2 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ZkShardTerms.java +++ b/solr/core/src/java/org/apache/solr/cloud/ZkShardTerms.java @@ -22,7 +22,6 @@ import java.util.HashSet; import java.util.Map; import java.util.Set; -import java.util.concurrent.TimeoutException; import java.util.concurrent.atomic.AtomicBoolean; import java.util.concurrent.atomic.AtomicReference; import java.util.function.Function; @@ -322,7 +321,7 @@ private boolean saveTerms(ShardTerms newTerms, String action) throws KeeperException.NoNodeException { byte[] znodeData = Utils.toJSON(newTerms); try { - Stat stat = zkClient.setData(znodePath, znodeData, newTerms.getVersion(), true); + Stat stat = zkClient.setData(znodePath, znodeData, newTerms.getVersion()); setNewTerms(new ShardTerms(newTerms, stat.getVersion())); log.info("Successful update of terms at {} to {} for {}", znodePath, newTerms, action); return true; @@ -349,7 +348,7 @@ private void ensureTermNodeExist() { try { Map initialTerms = new HashMap<>(); - zkClient.makePath(path, Utils.toJSON(initialTerms), CreateMode.PERSISTENT, true); + zkClient.makePath(path, Utils.toJSON(initialTerms), CreateMode.PERSISTENT); } catch (KeeperException.NodeExistsException e) { // it's okay if another beats us creating the node } @@ -369,7 +368,7 @@ public void refreshTerms() { ShardTerms newTerms; try { Stat stat = new Stat(); - byte[] data = zkClient.getData(znodePath, null, stat, true); + byte[] data = zkClient.getData(znodePath, null, stat); newTerms = new ShardTerms((Map) Utils.fromJSON(data), stat.getVersion()); } catch (KeeperException | InterruptedException e) { Throwable cause = SolrZkClient.checkInterrupted(e); @@ -397,16 +396,6 @@ private void retryRegisterWatcher() { return; } catch (KeeperException e) { log.warn("Failed watching shard term for collection: {}, retrying!", collection, e); - try { - zkClient.getConnectionManager().waitForConnected(zkClient.getZkClientTimeout()); - } catch (TimeoutException te) { - if (Thread.interrupted()) { - throw new SolrException( - SolrException.ErrorCode.SERVER_ERROR, - "Error watching shard term for collection: " + collection, - te); - } - } } } } @@ -426,7 +415,7 @@ private void registerWatcher() throws KeeperException { }; try { // exists operation is faster than getData operation - zkClient.exists(znodePath, watcher, true); + zkClient.exists(znodePath, watcher); } catch (InterruptedException e) { Thread.currentThread().interrupt(); throw new SolrException( diff --git a/solr/core/src/java/org/apache/solr/cloud/ZkSolrResourceLoader.java b/solr/core/src/java/org/apache/solr/cloud/ZkSolrResourceLoader.java index 4aa5990e0ea..0d9ef1c8338 100644 --- a/solr/core/src/java/org/apache/solr/cloud/ZkSolrResourceLoader.java +++ b/solr/core/src/java/org/apache/solr/cloud/ZkSolrResourceLoader.java @@ -58,7 +58,7 @@ public ZkSolrResourceLoader( public Pair getZkResourceInfo(String resource) { String file = (".".equals(resource)) ? configSetZkPath : configSetZkPath + "/" + resource; try { - Stat stat = zkController.getZkClient().exists(file, null, true); + Stat stat = zkController.getZkClient().exists(file, null); if (stat != null) { return new Pair<>(file, stat.getVersion()); } else { @@ -87,7 +87,7 @@ public InputStream openResource(String resource) throws IOException { try { if (zkController.pathExists(file)) { Stat stat = new Stat(); - byte[] bytes = zkController.getZkClient().getData(file, null, stat, true); + byte[] bytes = zkController.getZkClient().getData(file, null, stat); return new ZkByteArrayInputStream(bytes, file, stat); } else { // Path does not exists. We only retry for session expired exceptions. diff --git a/solr/core/src/java/org/apache/solr/cloud/api/collections/CreateCollectionCmd.java b/solr/core/src/java/org/apache/solr/cloud/api/collections/CreateCollectionCmd.java index 9accbf4dc69..59db03a4c73 100644 --- a/solr/core/src/java/org/apache/solr/cloud/api/collections/CreateCollectionCmd.java +++ b/solr/core/src/java/org/apache/solr/cloud/api/collections/CreateCollectionCmd.java @@ -190,9 +190,7 @@ public void call(ClusterState clusterState, ZkNodeProps message, NamedList resu if (zkStateReader.getClusterState().getCollectionOrNull(collection) == null) { if (zkStateReader .getZkClient() - .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collection, true)) { + .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collection)) { // if the collection is not in the clusterstate, but is listed in zk, do nothing, it will // just be removed in the finally - we cannot continue, because the below code will error // if the collection is not in the clusterstate @@ -209,7 +209,7 @@ public void call(ClusterState state, ZkNodeProps message, NamedList resu try { String collectionPath = DocCollection.getCollectionPathRoot(collection); - if (zkStateReader.getZkClient().exists(collectionPath, true)) { + if (zkStateReader.getZkClient().exists(collectionPath)) { if (removeCounterNode) { zkStateReader.getZkClient().clean(collectionPath); } else { diff --git a/solr/core/src/java/org/apache/solr/cloud/api/collections/OverseerRoleCmd.java b/solr/core/src/java/org/apache/solr/cloud/api/collections/OverseerRoleCmd.java index d8e7a3dea64..fc400ffb26a 100644 --- a/solr/core/src/java/org/apache/solr/cloud/api/collections/OverseerRoleCmd.java +++ b/solr/core/src/java/org/apache/solr/cloud/api/collections/OverseerRoleCmd.java @@ -75,12 +75,12 @@ public void call(ClusterState state, ZkNodeProps message, NamedList resu } String roleName = message.getStr("role"); - boolean nodeExists = zkClient.exists(ZkStateReader.ROLES, true); + boolean nodeExists = zkClient.exists(ZkStateReader.ROLES); if (nodeExists) { @SuppressWarnings("unchecked") Map> tmp = (Map>) - Utils.fromJSON(zkClient.getData(ZkStateReader.ROLES, null, new Stat(), true)); + Utils.fromJSON(zkClient.getData(ZkStateReader.ROLES, null, new Stat())); roles = tmp; } else { roles = CollectionUtil.newLinkedHashMap(1); @@ -96,9 +96,9 @@ public void call(ClusterState state, ZkNodeProps message, NamedList resu } if (nodeExists) { - zkClient.setData(ZkStateReader.ROLES, Utils.toJSON(roles), true); + zkClient.setData(ZkStateReader.ROLES, Utils.toJSON(roles)); } else { - zkClient.create(ZkStateReader.ROLES, Utils.toJSON(roles), CreateMode.PERSISTENT, true); + zkClient.create(ZkStateReader.ROLES, Utils.toJSON(roles), CreateMode.PERSISTENT); } runPrioritizer(); } diff --git a/solr/core/src/java/org/apache/solr/cloud/api/collections/OverseerStatusCmd.java b/solr/core/src/java/org/apache/solr/cloud/api/collections/OverseerStatusCmd.java index 0b841fe8790..d7fad3f776f 100644 --- a/solr/core/src/java/org/apache/solr/cloud/api/collections/OverseerStatusCmd.java +++ b/solr/core/src/java/org/apache/solr/cloud/api/collections/OverseerStatusCmd.java @@ -175,13 +175,13 @@ public void call(ClusterState state, ZkNodeProps message, NamedList resu String leaderNode = OverseerTaskProcessor.getLeaderNode(zkStateReader.getZkClient()); results.add("leader", leaderNode); Stat stat = new Stat(); - zkStateReader.getZkClient().getData("/overseer/queue", null, stat, true); + zkStateReader.getZkClient().getData("/overseer/queue", null, stat); results.add("overseer_queue_size", stat.getNumChildren()); stat = new Stat(); - zkStateReader.getZkClient().getData("/overseer/queue-work", null, stat, true); + zkStateReader.getZkClient().getData("/overseer/queue-work", null, stat); results.add("overseer_work_queue_size", stat.getNumChildren()); stat = new Stat(); - zkStateReader.getZkClient().getData("/overseer/collection-queue-work", null, stat, true); + zkStateReader.getZkClient().getData("/overseer/collection-queue-work", null, stat); results.add("overseer_collection_queue_size", stat.getNumChildren()); NamedList overseerStats = new NamedList<>(); diff --git a/solr/core/src/java/org/apache/solr/cloud/api/collections/SplitShardCmd.java b/solr/core/src/java/org/apache/solr/cloud/api/collections/SplitShardCmd.java index 0060eb676af..f849ab24d92 100644 --- a/solr/core/src/java/org/apache/solr/cloud/api/collections/SplitShardCmd.java +++ b/solr/core/src/java/org/apache/solr/cloud/api/collections/SplitShardCmd.java @@ -212,10 +212,7 @@ public boolean split(ClusterState clusterState, ZkNodeProps message, NamedList -1) return true; return false; diff --git a/solr/core/src/java/org/apache/solr/core/ZkContainer.java b/solr/core/src/java/org/apache/solr/core/ZkContainer.java index f7ea012b249..0fb8cb30d52 100644 --- a/solr/core/src/java/org/apache/solr/core/ZkContainer.java +++ b/solr/core/src/java/org/apache/solr/core/ZkContainer.java @@ -32,7 +32,6 @@ import org.apache.solr.client.solrj.impl.SolrZkClientTimeout; import org.apache.solr.cloud.SolrZkServer; import org.apache.solr.cloud.ZkController; -import org.apache.solr.common.AlreadyClosedException; import org.apache.solr.common.SolrException; import org.apache.solr.common.cloud.ClusterProperties; import org.apache.solr.common.cloud.Replica; @@ -223,7 +222,7 @@ public void registerInZk(final SolrCore core, boolean background, boolean skipRe log.error("Interrupted", e); } catch (KeeperException e) { log.error("KeeperException registering core {}", core.getName(), e); - } catch (AlreadyClosedException ignore) { + } catch (IllegalStateException ignore) { } catch (Exception e) { log.error("Exception registering core {}", core.getName(), e); diff --git a/solr/core/src/java/org/apache/solr/core/backup/BackupManager.java b/solr/core/src/java/org/apache/solr/core/backup/BackupManager.java index be6a1a83c2f..968b2186a93 100644 --- a/solr/core/src/java/org/apache/solr/core/backup/BackupManager.java +++ b/solr/core/src/java/org/apache/solr/core/backup/BackupManager.java @@ -294,7 +294,7 @@ public void uploadCollectionProperties(String collectionName) throws IOException repository.openInput(sourceDir, ZkStateReader.COLLECTION_PROPS_ZKNODE, IOContext.DEFAULT)) { byte[] arr = new byte[(int) is.length()]; is.readBytes(arr, 0, (int) is.length()); - zkStateReader.getZkClient().create(zkPath, arr, CreateMode.PERSISTENT, true); + zkStateReader.getZkClient().create(zkPath, arr, CreateMode.PERSISTENT); } catch (KeeperException | InterruptedException e) { throw new IOException( "Error uploading file to zookeeper path " + source.toString() + " to " + zkPath, @@ -312,13 +312,13 @@ public void downloadCollectionProperties(String collectionName) throws IOExcepti + ZkStateReader.COLLECTION_PROPS_ZKNODE; try { - if (!zkStateReader.getZkClient().exists(zkPath, true)) { + if (!zkStateReader.getZkClient().exists(zkPath)) { // Nothing to back up return; } try (OutputStream os = repository.createOutput(dest)) { - byte[] data = zkStateReader.getZkClient().getData(zkPath, null, null, true); + byte[] data = zkStateReader.getZkClient().getData(zkPath, null, null); os.write(data); } } catch (KeeperException | InterruptedException e) { diff --git a/solr/core/src/java/org/apache/solr/core/snapshots/SolrSnapshotManager.java b/solr/core/src/java/org/apache/solr/core/snapshots/SolrSnapshotManager.java index acdbd722717..db83b2e6d11 100644 --- a/solr/core/src/java/org/apache/solr/core/snapshots/SolrSnapshotManager.java +++ b/solr/core/src/java/org/apache/solr/core/snapshots/SolrSnapshotManager.java @@ -74,7 +74,7 @@ public static boolean snapshotExists( SolrZkClient zkClient, String collectionName, String commitName) throws KeeperException, InterruptedException { String zkPath = getSnapshotMetaDataZkPath(collectionName, Optional.ofNullable(commitName)); - return zkClient.exists(zkPath, true); + return zkClient.exists(zkPath); } /** @@ -90,7 +90,7 @@ public static void createCollectionLevelSnapshot( SolrZkClient zkClient, String collectionName, CollectionSnapshotMetaData meta) throws KeeperException, InterruptedException { String zkPath = getSnapshotMetaDataZkPath(collectionName, Optional.of(meta.getName())); - zkClient.makePath(zkPath, Utils.toJSON(meta), CreateMode.PERSISTENT, true); + zkClient.makePath(zkPath, Utils.toJSON(meta), CreateMode.PERSISTENT); } /** @@ -106,7 +106,7 @@ public static void updateCollectionLevelSnapshot( SolrZkClient zkClient, String collectionName, CollectionSnapshotMetaData meta) throws KeeperException, InterruptedException { String zkPath = getSnapshotMetaDataZkPath(collectionName, Optional.of(meta.getName())); - zkClient.setData(zkPath, Utils.toJSON(meta), -1, true); + zkClient.setData(zkPath, Utils.toJSON(meta), -1); } /** @@ -122,7 +122,7 @@ public static void deleteCollectionLevelSnapshot( SolrZkClient zkClient, String collectionName, String commitName) throws InterruptedException, KeeperException { String zkPath = getSnapshotMetaDataZkPath(collectionName, Optional.of(commitName)); - zkClient.delete(zkPath, -1, true); + zkClient.delete(zkPath, -1); } /** @@ -138,11 +138,11 @@ public static void cleanupCollectionLevelSnapshots(SolrZkClient zkClient, String String zkPath = getSnapshotMetaDataZkPath(collectionName, Optional.empty()); try { // Delete the meta-data for each snapshot. - Collection snapshots = zkClient.getChildren(zkPath, null, true); + Collection snapshots = zkClient.getChildren(zkPath, null); for (String snapshot : snapshots) { String path = getSnapshotMetaDataZkPath(collectionName, Optional.of(snapshot)); try { - zkClient.delete(path, -1, true); + zkClient.delete(path, -1); } catch (KeeperException ex) { // Gracefully handle the case when the zk node doesn't exist if (ex.code() != KeeperException.Code.NONODE) { @@ -152,7 +152,7 @@ public static void cleanupCollectionLevelSnapshots(SolrZkClient zkClient, String } // Delete the parent node. - zkClient.delete(zkPath, -1, true); + zkClient.delete(zkPath, -1); } catch (KeeperException ex) { // Gracefully handle the case when the zk node doesn't exist (e.g. if no snapshots were // created for this collection). @@ -180,7 +180,7 @@ public static Optional getCollectionLevelSnapshot( try { @SuppressWarnings({"unchecked"}) Map data = - (Map) Utils.fromJSON(zkClient.getData(zkPath, null, null, true)); + (Map) Utils.fromJSON(zkClient.getData(zkPath, null, null)); return Optional.of(new CollectionSnapshotMetaData(data)); } catch (KeeperException ex) { // Gracefully handle the case when the zk node for a specific @@ -208,7 +208,7 @@ public static Collection listSnapshots( String zkPath = getSnapshotMetaDataZkPath(collectionName, Optional.empty()); try { - Collection snapshots = zkClient.getChildren(zkPath, null, true); + Collection snapshots = zkClient.getChildren(zkPath, null); for (String snapshot : snapshots) { Optional s = getCollectionLevelSnapshot(zkClient, collectionName, snapshot); diff --git a/solr/core/src/java/org/apache/solr/filestore/DistribPackageStore.java b/solr/core/src/java/org/apache/solr/filestore/DistribPackageStore.java index 8bd0f2c71ea..c301f0d297b 100644 --- a/solr/core/src/java/org/apache/solr/filestore/DistribPackageStore.java +++ b/solr/core/src/java/org/apache/solr/filestore/DistribPackageStore.java @@ -337,18 +337,14 @@ public void put(FileEntry entry) throws IOException { private void distribute(FileInfo info) { try { String dirName = info.path.substring(0, info.path.lastIndexOf('/')); - coreContainer - .getZkController() - .getZkClient() - .makePath(ZK_PACKAGESTORE + dirName, false, true); + coreContainer.getZkController().getZkClient().makePath(ZK_PACKAGESTORE + dirName, false); coreContainer .getZkController() .getZkClient() .create( ZK_PACKAGESTORE + info.path, info.getDetails().getMetaData().sha512.getBytes(UTF_8), - CreateMode.PERSISTENT, - true); + CreateMode.PERSISTENT); } catch (Exception e) { throw new SolrException(SERVER_ERROR, "Unable to create an entry in ZK", e); } @@ -512,7 +508,7 @@ public void delete(String path) { private void checkInZk(String path) { try { // fail if file exists - if (coreContainer.getZkController().getZkClient().exists(ZK_PACKAGESTORE + path, true)) { + if (coreContainer.getZkController().getZkClient().exists(ZK_PACKAGESTORE + path)) { throw new SolrException(BAD_REQUEST, "The path exist ZK, delete and retry"); } @@ -536,11 +532,7 @@ public void refresh(String path) { @SuppressWarnings({"rawtypes"}) List l = null; try { - l = - coreContainer - .getZkController() - .getZkClient() - .getChildren(ZK_PACKAGESTORE + path, null, true); + l = coreContainer.getZkController().getZkClient().getChildren(ZK_PACKAGESTORE + path, null); } catch (KeeperException.NoNodeException e) { // does not matter } @@ -647,7 +639,7 @@ private static Map _getKeys(Path solrHome) throws IOException { public static void deleteZKFileEntry(SolrZkClient client, String path) { try { - client.delete(ZK_PACKAGESTORE + path, -1, true); + client.delete(ZK_PACKAGESTORE + path, -1); } catch (KeeperException | InterruptedException e) { log.error("", e); } diff --git a/solr/core/src/java/org/apache/solr/filestore/PackageStoreAPI.java b/solr/core/src/java/org/apache/solr/filestore/PackageStoreAPI.java index eb87c1a8e29..ffa7f7dced4 100644 --- a/solr/core/src/java/org/apache/solr/filestore/PackageStoreAPI.java +++ b/solr/core/src/java/org/apache/solr/filestore/PackageStoreAPI.java @@ -140,7 +140,7 @@ public void delete(SolrQueryRequest req, SolrQueryResponse rsp) { coreContainer .getZkController() .getZkClient() - .create(TMP_ZK_NODE, "true".getBytes(UTF_8), CreateMode.EPHEMERAL, true); + .create(TMP_ZK_NODE, "true".getBytes(UTF_8), CreateMode.EPHEMERAL); String path = req.getPathTemplateValues().get("*"); validateName(path, true); if (coreContainer.getPackageLoader().getPackageAPI().isJarInuse(path)) { @@ -159,7 +159,7 @@ public void delete(SolrQueryRequest req, SolrQueryResponse rsp) { throw new SolrException(SolrException.ErrorCode.SERVER_ERROR, e); } finally { try { - coreContainer.getZkController().getZkClient().delete(TMP_ZK_NODE, -1, true); + coreContainer.getZkController().getZkClient().delete(TMP_ZK_NODE, -1); } catch (Exception e) { log.error("Unexpected error ", e); } @@ -188,7 +188,7 @@ public void upload(SolrQueryRequest req, SolrQueryResponse rsp) { coreContainer .getZkController() .getZkClient() - .create(TMP_ZK_NODE, "true".getBytes(UTF_8), CreateMode.EPHEMERAL, true); + .create(TMP_ZK_NODE, "true".getBytes(UTF_8), CreateMode.EPHEMERAL); Iterable streams = req.getContentStreams(); if (streams == null) @@ -239,7 +239,7 @@ public void upload(SolrQueryRequest req, SolrQueryResponse rsp) { log.error("Unexpected error", e); } finally { try { - coreContainer.getZkController().getZkClient().delete(TMP_ZK_NODE, -1, true); + coreContainer.getZkController().getZkClient().delete(TMP_ZK_NODE, -1); } catch (Exception e) { log.error("Unexpected error ", e); } diff --git a/solr/core/src/java/org/apache/solr/handler/admin/ClusterStatus.java b/solr/core/src/java/org/apache/solr/handler/admin/ClusterStatus.java index 9130fcc317a..b3aea417df9 100644 --- a/solr/core/src/java/org/apache/solr/handler/admin/ClusterStatus.java +++ b/solr/core/src/java/org/apache/solr/handler/admin/ClusterStatus.java @@ -113,11 +113,10 @@ public void getClusterStatus(NamedList results) } Map roles = null; - if (zkStateReader.getZkClient().exists(ZkStateReader.ROLES, true)) { + if (zkStateReader.getZkClient().exists(ZkStateReader.ROLES)) { roles = (Map) - Utils.fromJSON( - zkStateReader.getZkClient().getData(ZkStateReader.ROLES, null, null, true)); + Utils.fromJSON(zkStateReader.getZkClient().getData(ZkStateReader.ROLES, null, null)); } ClusterState clusterState = zkStateReader.getClusterState(); @@ -197,7 +196,7 @@ public void getClusterStatus(NamedList results) } List liveNodes = - zkStateReader.getZkClient().getChildren(ZkStateReader.LIVE_NODES_ZKNODE, null, true); + zkStateReader.getZkClient().getChildren(ZkStateReader.LIVE_NODES_ZKNODE, null); // now we need to walk the collectionProps tree to cross-check replica state with live nodes crossCheckReplicaStateWithLiveNodes(liveNodes, collectionProps); diff --git a/solr/core/src/java/org/apache/solr/handler/admin/ContainerPluginsApi.java b/solr/core/src/java/org/apache/solr/handler/admin/ContainerPluginsApi.java index 117334b6d4b..290185c7b07 100644 --- a/solr/core/src/java/org/apache/solr/handler/admin/ContainerPluginsApi.java +++ b/solr/core/src/java/org/apache/solr/handler/admin/ContainerPluginsApi.java @@ -174,7 +174,7 @@ public static Map plugins(Supplier zkClientSupplie try { Map clusterPropsJson = (Map) - Utils.fromJSON(zkClient.getData(ZkStateReader.CLUSTER_PROPS, null, new Stat(), true)); + Utils.fromJSON(zkClient.getData(ZkStateReader.CLUSTER_PROPS, null, new Stat())); return (Map) clusterPropsJson.computeIfAbsent(PLUGIN, o -> new LinkedHashMap<>()); } catch (KeeperException.NoNodeException e) { diff --git a/solr/core/src/java/org/apache/solr/handler/admin/SecurityConfHandlerZk.java b/solr/core/src/java/org/apache/solr/handler/admin/SecurityConfHandlerZk.java index a0978c02759..09d8cbcddf6 100644 --- a/solr/core/src/java/org/apache/solr/handler/admin/SecurityConfHandlerZk.java +++ b/solr/core/src/java/org/apache/solr/handler/admin/SecurityConfHandlerZk.java @@ -79,8 +79,7 @@ protected boolean persistConf(SecurityConfig securityConfig) throws IOException .setData( SOLR_SECURITY_CONF_PATH, Utils.toJSON(securityConfig.getData()), - securityConfig.getVersion(), - true); + securityConfig.getVersion()); log.debug("Persisted security.json to {}", SOLR_SECURITY_CONF_PATH); return true; } catch (KeeperException.BadVersionException bdve) { diff --git a/solr/core/src/java/org/apache/solr/handler/admin/ShowFileRequestHandler.java b/solr/core/src/java/org/apache/solr/handler/admin/ShowFileRequestHandler.java index e2d8b7715b8..71b2127f790 100644 --- a/solr/core/src/java/org/apache/solr/handler/admin/ShowFileRequestHandler.java +++ b/solr/core/src/java/org/apache/solr/handler/admin/ShowFileRequestHandler.java @@ -156,7 +156,7 @@ private void showFromZooKeeper( } // Show a directory listing - List children = zkClient.getChildren(adminFile, null, true); + List children = zkClient.getChildren(adminFile, null); if (children.size() > 0) { NamedList> files = new SimpleOrderedMap<>(); @@ -167,7 +167,7 @@ private void showFromZooKeeper( SimpleOrderedMap fileInfo = new SimpleOrderedMap<>(); files.add(f, fileInfo); - List fchildren = zkClient.getChildren(adminFile + "/" + f, null, true); + List fchildren = zkClient.getChildren(adminFile + "/" + f, null); if (fchildren.size() > 0) { fileInfo.add("directory", true); } else { @@ -185,8 +185,7 @@ private void showFromZooKeeper( params.set(CommonParams.WT, "raw"); req.setParams(params); ContentStreamBase content = - new ContentStreamBase.ByteArrayStream( - zkClient.getData(adminFile, null, null, true), adminFile); + new ContentStreamBase.ByteArrayStream(zkClient.getData(adminFile, null, null), adminFile); content.setContentType(getSafeContentType(req.getParams().get(USE_CONTENT_TYPE))); rsp.add(RawResponseWriter.CONTENT, content); @@ -342,7 +341,7 @@ public static String getAdminFileFromZooKeeper( } // Make sure the file exists, is readable and is not a hidden file - if (!zkClient.exists(adminFile, true)) { + if (!zkClient.exists(adminFile)) { log.error("Can not find: {}", adminFile); rsp.setException( new SolrException(SolrException.ErrorCode.NOT_FOUND, "Can not find: " + adminFile)); diff --git a/solr/core/src/java/org/apache/solr/handler/admin/ZookeeperInfoHandler.java b/solr/core/src/java/org/apache/solr/handler/admin/ZookeeperInfoHandler.java index b5a8234a321..ce1616ff901 100644 --- a/solr/core/src/java/org/apache/solr/handler/admin/ZookeeperInfoHandler.java +++ b/solr/core/src/java/org/apache/solr/handler/admin/ZookeeperInfoHandler.java @@ -282,7 +282,7 @@ private synchronized List getCollections(SolrZkClient zkClient) // cache is stale, rebuild the full list ... cachedCollections = new ArrayList(); - List fromZk = zkClient.getChildren("/collections", this, true); + List fromZk = zkClient.getChildren("/collections", this); if (fromZk != null) cachedCollections.addAll(fromZk); // sort the final merged set of collections @@ -623,7 +623,7 @@ boolean printTree(JSONWriter json, String path) throws IOException { Stat stat = new Stat(); try { // Trickily, the call to zkClient.getData fills in the stat variable - byte[] data = zkClient.getData(path, null, stat, true); + byte[] data = zkClient.getData(path, null, stat); if (stat.getEphemeralOwner() != 0) { writeKeyValue(json, "ephemeral", true, false); @@ -656,7 +656,7 @@ boolean printTree(JSONWriter json, String path) throws IOException { json.startArray(); try { - List children = zkClient.getChildren(path, null, true); + List children = zkClient.getChildren(path, null); java.util.Collections.sort(children); boolean first = true; @@ -711,7 +711,7 @@ boolean printZnode(JSONWriter json, String path) throws IOException { String dataStrErr = null; Stat stat = new Stat(); // Trickily, the call to zkClient.getData fills in the stat variable - byte[] data = zkClient.getData(path, null, stat, true); + byte[] data = zkClient.getData(path, null, stat); if (null != data) { try { dataStr = (new BytesRef(data)).utf8ToString(); diff --git a/solr/core/src/java/org/apache/solr/handler/admin/ZookeeperReadAPI.java b/solr/core/src/java/org/apache/solr/handler/admin/ZookeeperReadAPI.java index c2f244e93d8..4e958192c7a 100644 --- a/solr/core/src/java/org/apache/solr/handler/admin/ZookeeperReadAPI.java +++ b/solr/core/src/java/org/apache/solr/handler/admin/ZookeeperReadAPI.java @@ -121,20 +121,18 @@ public ListZkChildrenResponse listNodes( zkPath = sanitizeZkPath(zkPath); try { - Stat stat = coreContainer.getZkController().getZkClient().exists(zkPath, null, true); + Stat stat = coreContainer.getZkController().getZkClient().exists(zkPath, null); listResponse.stat = new AnnotatedStat(stat); if (includeChildren != null && !includeChildren.booleanValue()) { return listResponse; } - List l = - coreContainer.getZkController().getZkClient().getChildren(zkPath, null, false); + List l = coreContainer.getZkController().getZkClient().getChildren(zkPath, null); String prefix = zkPath.endsWith("/") ? zkPath : zkPath + "/"; Map stats = new LinkedHashMap<>(); for (String s : l) { try { - stats.put( - s, coreContainer.getZkController().getZkClient().exists(prefix + s, null, false)); + stats.put(s, coreContainer.getZkController().getZkClient().exists(prefix + s, null)); } catch (Exception e) { throw new RuntimeException(e); } @@ -184,7 +182,7 @@ private ZooKeeperFileResponse readNodeAndAddToResponse(String zkPath) { private byte[] readPathFromZookeeper(String path) { byte[] d; try { - d = coreContainer.getZkController().getZkClient().getData(path, null, null, false); + d = coreContainer.getZkController().getZkClient().getData(path, null, null); } catch (KeeperException.NoNodeException e) { throw new SolrException(SolrException.ErrorCode.NOT_FOUND, "No such node: " + path); } catch (Exception e) { diff --git a/solr/core/src/java/org/apache/solr/handler/component/SearchHandler.java b/solr/core/src/java/org/apache/solr/handler/component/SearchHandler.java index 744d6093222..3e5c2086b16 100644 --- a/solr/core/src/java/org/apache/solr/handler/component/SearchHandler.java +++ b/solr/core/src/java/org/apache/solr/handler/component/SearchHandler.java @@ -324,9 +324,7 @@ public ShardHandler getAndPrepShardHandler(SolrQueryRequest req, ResponseBuilder boolean requireZkConnected = shardsTolerant != null && shardsTolerant.equals(ShardParams.REQUIRE_ZK_CONNECTED); ZkController zkController = cc.getZkController(); - boolean zkConnected = - zkController != null - && !zkController.getZkClient().getConnectionManager().isLikelyExpired(); + boolean zkConnected = zkController != null && zkController.getZkClient().isConnected(); if (requireZkConnected && false == zkConnected) { throw new SolrException(SolrException.ErrorCode.SERVER_ERROR, "ZooKeeper is not connected"); } else { diff --git a/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerAPI.java b/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerAPI.java index a8a4b5091d4..644a48eae12 100644 --- a/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerAPI.java +++ b/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerAPI.java @@ -218,7 +218,7 @@ public void getFileContents(SolrQueryRequest req, SolrQueryResponse rsp) throws String filePath = getConfigSetZkPath(getMutableId(configSet), file); byte[] data; try { - data = zkStateReader().getZkClient().getData(filePath, null, null, true); + data = zkStateReader().getZkClient().getData(filePath, null, null); } catch (KeeperException | InterruptedException e) { throw new IOException("Error reading file: " + filePath, SolrZkClient.checkInterrupted(e)); } @@ -273,7 +273,7 @@ public void updateFileContents(SolrQueryRequest req, SolrQueryResponse rsp) // apply the update and reload the temp collection / re-index sample docs SolrZkClient zkClient = zkStateReader().getZkClient(); try { - zkClient.setData(zkPath, data, true); + zkClient.setData(zkPath, data); } catch (KeeperException | InterruptedException e) { throw new IOException( "Failed to save data in ZK at path: " + zkPath, SolrZkClient.checkInterrupted(e)); @@ -402,8 +402,8 @@ public void downloadConfig(SolrQueryRequest req, SolrQueryResponse rsp) throws I SolrZkClient zkClient = zkStateReader().getZkClient(); String configId = mutableId; try { - if (!zkClient.exists(getConfigSetZkPath(mutableId, null), true)) { - if (zkClient.exists(getConfigSetZkPath(configSet, null), true)) { + if (!zkClient.exists(getConfigSetZkPath(mutableId, null))) { + if (zkClient.exists(getConfigSetZkPath(configSet, null))) { configId = configSet; } else { throw new SolrException( @@ -1363,7 +1363,7 @@ private void validateNewConfigSetName(String configSet) { private boolean pathExistsInZk(final String zkPath) throws IOException { SolrZkClient zkClient = zkStateReader().getZkClient(); try { - return zkClient.exists(zkPath, true); + return zkClient.exists(zkPath); } catch (KeeperException | InterruptedException e) { throw new IOException( "Failed to check if path exists: " + zkPath, SolrZkClient.checkInterrupted(e)); diff --git a/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerConfigSetHelper.java b/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerConfigSetHelper.java index db35a805c51..8c726f288ca 100644 --- a/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerConfigSetHelper.java +++ b/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerConfigSetHelper.java @@ -705,7 +705,7 @@ int getCurrentSchemaVersion(final String configSet) throws IOException { int currentVersion = -1; final String path = getManagedSchemaZkPath(configSet); try { - Stat stat = cc.getZkController().getZkClient().exists(path, null, true); + Stat stat = cc.getZkController().getZkClient().exists(path, null); if (stat != null) { currentVersion = stat.getVersion(); } @@ -927,7 +927,7 @@ protected ManagedIndexSchema removeLanguageSpecificObjectsAndFiles( for (String path : toRemoveFiles) { try { - zkClient.delete(path, -1, false); + zkClient.delete(path, -1); } catch (KeeperException.NoNodeException nne) { // no-op } catch (KeeperException | InterruptedException e) { @@ -993,9 +993,9 @@ protected ManagedIndexSchema restoreLanguageSpecificObjectsAndFiles( for (String path : langFilesToRestore) { String copyToPath = path.replace(origPathDir, replacePathDir); try { - if (!zkClient.exists(copyToPath, true)) { - zkClient.makePath(copyToPath, false, true); - zkClient.setData(copyToPath, zkClient.getData(path, null, null, true), true); + if (!zkClient.exists(copyToPath)) { + zkClient.makePath(copyToPath, false); + zkClient.setData(copyToPath, zkClient.getData(path, null, null)); } } catch (KeeperException | InterruptedException e) { throw new IOException( diff --git a/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerSettingsDAO.java b/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerSettingsDAO.java index bf8e3d26e93..a824e70381d 100644 --- a/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerSettingsDAO.java +++ b/solr/core/src/java/org/apache/solr/handler/designer/SchemaDesignerSettingsDAO.java @@ -130,7 +130,7 @@ private ConfigOverlay getConfigOverlay(String config) throws IOException { byte[] data = null; Stat stat = new Stat(); try { - data = cc.getZkController().getZkStateReader().getZkClient().getData(path, null, stat, true); + data = cc.getZkController().getZkStateReader().getZkClient().getData(path, null, stat); } catch (KeeperException.NoNodeException nne) { // ignore } catch (KeeperException | InterruptedException e) { diff --git a/solr/core/src/java/org/apache/solr/packagemanager/PackageManager.java b/solr/core/src/java/org/apache/solr/packagemanager/PackageManager.java index 79b9fa1c9c3..f518499c934 100644 --- a/solr/core/src/java/org/apache/solr/packagemanager/PackageManager.java +++ b/solr/core/src/java/org/apache/solr/packagemanager/PackageManager.java @@ -182,14 +182,14 @@ public List fetchInstalledPackageInstances() throws SolrExc List ret = new ArrayList<>(); packages = new HashMap<>(); try { - if (zkClient.exists(ZkStateReader.SOLR_PKGS_PATH, true)) { + if (zkClient.exists(ZkStateReader.SOLR_PKGS_PATH)) { @SuppressWarnings("unchecked") Map>> packagesZnodeMap = (Map>>) getMapper() .readValue( new String( - zkClient.getData(ZkStateReader.SOLR_PKGS_PATH, null, null, true), + zkClient.getData(ZkStateReader.SOLR_PKGS_PATH, null, null), StandardCharsets.UTF_8), Map.class) .get("packages"); @@ -322,7 +322,7 @@ public Map getPackagesDeployedAsClusterLevelPlugins private void ensureCollectionsExist(List collections) { try { - List existingCollections = zkClient.getChildren("/collections", null, true); + List existingCollections = zkClient.getChildren("/collections", null); Set nonExistent = new HashSet<>(collections); nonExistent.removeAll(existingCollections); if (!nonExistent.isEmpty()) { @@ -1080,7 +1080,7 @@ public void undeploy( public Map getDeployedCollections(String packageName) { List allCollections; try { - allCollections = zkClient.getChildren(ZkStateReader.COLLECTIONS_ZKNODE, null, true); + allCollections = zkClient.getChildren(ZkStateReader.COLLECTIONS_ZKNODE, null); } catch (KeeperException | InterruptedException e) { throw new SolrException(ErrorCode.SERVICE_UNAVAILABLE, e); } diff --git a/solr/core/src/java/org/apache/solr/packagemanager/RepositoryManager.java b/solr/core/src/java/org/apache/solr/packagemanager/RepositoryManager.java index 8ef29ba5552..9ee18360c31 100644 --- a/solr/core/src/java/org/apache/solr/packagemanager/RepositoryManager.java +++ b/solr/core/src/java/org/apache/solr/packagemanager/RepositoryManager.java @@ -119,17 +119,15 @@ public void addRepository(String repoName, String uri) throws Exception { @SuppressWarnings({"unchecked"}) List repos = getMapper().readValue(existingRepositoriesJson, List.class); repos.add(new DefaultPackageRepository(repoName, uri)); - if (packageManager.zkClient.exists(PackageUtils.REPOSITORIES_ZK_PATH, true) == false) { + if (packageManager.zkClient.exists(PackageUtils.REPOSITORIES_ZK_PATH) == false) { packageManager.zkClient.create( PackageUtils.REPOSITORIES_ZK_PATH, getMapper().writeValueAsString(repos).getBytes("UTF-8"), - CreateMode.PERSISTENT, - true); + CreateMode.PERSISTENT); } else { packageManager.zkClient.setData( PackageUtils.REPOSITORIES_ZK_PATH, - getMapper().writeValueAsString(repos).getBytes("UTF-8"), - true); + getMapper().writeValueAsString(repos).getBytes("UTF-8")); } try (InputStream is = new URL(uri + "/publickey.der").openStream()) { @@ -153,9 +151,8 @@ public void addKey(byte[] key, String destinationKeyFilename) throws Exception { private String getRepositoriesJson(SolrZkClient zkClient) throws UnsupportedEncodingException, KeeperException, InterruptedException { - if (zkClient.exists(PackageUtils.REPOSITORIES_ZK_PATH, true)) { - return new String( - zkClient.getData(PackageUtils.REPOSITORIES_ZK_PATH, null, null, true), "UTF-8"); + if (zkClient.exists(PackageUtils.REPOSITORIES_ZK_PATH)) { + return new String(zkClient.getData(PackageUtils.REPOSITORIES_ZK_PATH, null, null), "UTF-8"); } return "[]"; } diff --git a/solr/core/src/java/org/apache/solr/pkg/PackageAPI.java b/solr/core/src/java/org/apache/solr/pkg/PackageAPI.java index 0f9a8d50845..3bb8f6578d0 100644 --- a/solr/core/src/java/org/apache/solr/pkg/PackageAPI.java +++ b/solr/core/src/java/org/apache/solr/pkg/PackageAPI.java @@ -113,18 +113,14 @@ public void process(WatchedEvent event) { refreshPackages(thisWatch); } } - }, - true); + }); } public void refreshPackages(Watcher watcher) { final Stat stat = new Stat(); try { final byte[] data = - coreContainer - .getZkController() - .getZkClient() - .getData(SOLR_PKGS_PATH, watcher, stat, true); + coreContainer.getZkController().getZkClient().getData(SOLR_PKGS_PATH, watcher, stat); pkgs = readPkgsFromZk(data, stat); packageLoader.refreshPackageConf(); } catch (KeeperException.ConnectionLossException | KeeperException.SessionExpiredException e) { @@ -144,8 +140,7 @@ private Packages readPkgsFromZk(byte[] data, Stat stat) if (data == null || stat == null) { stat = new Stat(); - data = - coreContainer.getZkController().getZkClient().getData(SOLR_PKGS_PATH, null, stat, true); + data = coreContainer.getZkController().getZkClient().getData(SOLR_PKGS_PATH, null, stat); } Packages packages = null; if (data == null || data.length == 0) { diff --git a/solr/core/src/java/org/apache/solr/rest/ManagedResourceStorage.java b/solr/core/src/java/org/apache/solr/rest/ManagedResourceStorage.java index b28f4f57c36..aed8b6090a2 100644 --- a/solr/core/src/java/org/apache/solr/rest/ManagedResourceStorage.java +++ b/solr/core/src/java/org/apache/solr/rest/ManagedResourceStorage.java @@ -227,7 +227,6 @@ public static class ZooKeeperStorageIO implements StorageIO { protected SolrZkClient zkClient; protected String znodeBase; - protected boolean retryOnConnLoss = true; public ZooKeeperStorageIO(SolrZkClient zkClient, String znodeBase) { this.zkClient = zkClient; @@ -239,8 +238,8 @@ public void configure(SolrResourceLoader loader, NamedList initArgs) throws SolrException { // validate connectivity and the configured znode base try { - if (!zkClient.exists(znodeBase, retryOnConnLoss)) { - zkClient.makePath(znodeBase, retryOnConnLoss); + if (!zkClient.exists(znodeBase)) { + zkClient.makePath(znodeBase); } } catch (Exception exc) { String errMsg = @@ -257,7 +256,7 @@ public void configure(SolrResourceLoader loader, NamedList initArgs) public boolean exists(String storedResourceId) throws IOException { final String znodePath = getZnodeForResource(storedResourceId); try { - return zkClient.exists(znodePath, retryOnConnLoss); + return zkClient.exists(znodePath); } catch (Exception e) { if (e instanceof IOException) { throw (IOException) e; @@ -272,8 +271,8 @@ public InputStream openInputStream(String storedResourceId) throws IOException { final String znodePath = getZnodeForResource(storedResourceId); byte[] znodeData = null; try { - if (zkClient.exists(znodePath, retryOnConnLoss)) { - znodeData = zkClient.getData(znodePath, null, null, retryOnConnLoss); + if (zkClient.exists(znodePath)) { + znodeData = zkClient.getData(znodePath, null, null); } } catch (Exception e) { if (e instanceof IOException) { @@ -296,18 +295,17 @@ public InputStream openInputStream(String storedResourceId) throws IOException { @Override public OutputStream openOutputStream(String storedResourceId) throws IOException { final String znodePath = getZnodeForResource(storedResourceId); - final boolean retryOnConnLoss = this.retryOnConnLoss; ByteArrayOutputStream baos = new ByteArrayOutputStream() { @Override public void close() { byte[] znodeData = toByteArray(); try { - if (zkClient.exists(znodePath, retryOnConnLoss)) { - zkClient.setData(znodePath, znodeData, retryOnConnLoss); + if (zkClient.exists(znodePath)) { + zkClient.setData(znodePath, znodeData); log.info("Wrote {} bytes to existing znode {}", znodeData.length, znodePath); } else { - zkClient.makePath(znodePath, znodeData, retryOnConnLoss); + zkClient.makePath(znodePath, znodeData); log.info("Wrote {} bytes to new znode {}", znodeData.length, znodePath); } } catch (Exception e) { @@ -339,10 +337,10 @@ public boolean delete(String storedResourceId) throws IOException { // this might be overkill for a delete operation try { - if (zkClient.exists(znodePath, retryOnConnLoss)) { + if (zkClient.exists(znodePath)) { log.debug("Attempting to delete znode {}", znodePath); - zkClient.delete(znodePath, -1, retryOnConnLoss); - wasDeleted = zkClient.exists(znodePath, retryOnConnLoss); + zkClient.delete(znodePath, -1); + wasDeleted = zkClient.exists(znodePath); if (wasDeleted) { log.info("Deleted znode {}", znodePath); diff --git a/solr/core/src/java/org/apache/solr/schema/ManagedIndexSchema.java b/solr/core/src/java/org/apache/solr/schema/ManagedIndexSchema.java index 0bcfda95823..cc6e2e01277 100644 --- a/solr/core/src/java/org/apache/solr/schema/ManagedIndexSchema.java +++ b/solr/core/src/java/org/apache/solr/schema/ManagedIndexSchema.java @@ -187,7 +187,7 @@ boolean persistManagedSchemaToZooKeeper(boolean createOnly) { final byte[] data = writer.toString().getBytes(StandardCharsets.UTF_8); if (createOnly) { try { - zkClient.create(managedSchemaPath, data, CreateMode.PERSISTENT, true); + zkClient.create(managedSchemaPath, data, CreateMode.PERSISTENT); schemaZkVersion = 0; log.info("Created and persisted managed schema znode at {}", managedSchemaPath); } catch (KeeperException.NodeExistsException e) { @@ -199,7 +199,7 @@ boolean persistManagedSchemaToZooKeeper(boolean createOnly) { } else { try { // Assumption: the path exists - Stat stat = zkClient.setData(managedSchemaPath, data, schemaZkVersion, true); + Stat stat = zkClient.setData(managedSchemaPath, data, schemaZkVersion); schemaZkVersion = stat.getVersion(); log.info( "Persisted managed schema version {} at {}", schemaZkVersion, managedSchemaPath); diff --git a/solr/core/src/java/org/apache/solr/schema/ManagedIndexSchemaFactory.java b/solr/core/src/java/org/apache/solr/schema/ManagedIndexSchemaFactory.java index 73187383bd8..8bf2f3d1668 100644 --- a/solr/core/src/java/org/apache/solr/schema/ManagedIndexSchemaFactory.java +++ b/solr/core/src/java/org/apache/solr/schema/ManagedIndexSchemaFactory.java @@ -125,7 +125,7 @@ public String lookupZKManagedSchemaPath() { + ManagedIndexSchemaFactory.LEGACY_MANAGED_SCHEMA_RESOURCE_NAME; try { // check if we are using the legacy managed-schema file name. - if (zkClient.exists(legacyManagedSchemaPath, true)) { + if (zkClient.exists(legacyManagedSchemaPath)) { log.debug( "Legacy managed schema resource {} found - loading legacy managed schema instead of {} file.", ManagedIndexSchemaFactory.LEGACY_MANAGED_SCHEMA_RESOURCE_NAME, @@ -221,7 +221,7 @@ public ManagedIndexSchema create( Stat stat = new Stat(); try { // Attempt to load the managed schema - byte[] data = zkClient.getData(managedSchemaPath, null, stat, true); + byte[] data = zkClient.getData(managedSchemaPath, null, stat); schemaZkVersion = stat.getVersion(); schemaInputStream = new ZkSolrResourceLoader.ZkByteArrayInputStream(data, managedSchemaPath, stat); @@ -250,7 +250,7 @@ public ManagedIndexSchema create( } catch (IOException e) { try { // Retry to load the managed schema, in case it was created since the first attempt - byte[] data = zkClient.getData(managedSchemaPath, null, stat, true); + byte[] data = zkClient.getData(managedSchemaPath, null, stat); schemaZkVersion = stat.getVersion(); schemaInputStream = new ByteArrayInputStream(data); loadedResource = managedSchemaPath; @@ -470,7 +470,7 @@ private void zkUgradeToManagedSchema() { boolean locked = false; try { try { - zkClient.makePath(lockPath, null, CreateMode.EPHEMERAL, null, true, true); + zkClient.makePath(lockPath, null, CreateMode.EPHEMERAL, null, true); locked = true; } catch (Exception e) { // some other node already started the upgrade, or an error occurred - bail out @@ -487,14 +487,14 @@ private void zkUgradeToManagedSchema() { try { if (zkController.pathExists(nonManagedSchemaPath)) { // First, copy the non-managed schema znode content to the upgraded schema znode - byte[] bytes = zkController.getZkClient().getData(nonManagedSchemaPath, null, null, true); + byte[] bytes = zkController.getZkClient().getData(nonManagedSchemaPath, null, null); final String upgradedSchemaPath = nonManagedSchemaPath + UPGRADED_SCHEMA_EXTENSION; ZkMaintenanceUtils.ensureExists(upgradedSchemaPath, zkController.getZkClient()); - zkController.getZkClient().setData(upgradedSchemaPath, bytes, true); + zkController.getZkClient().setData(upgradedSchemaPath, bytes); // Then delete the non-managed schema znode - if (zkController.getZkClient().exists(nonManagedSchemaPath, true)) { + if (zkController.getZkClient().exists(nonManagedSchemaPath)) { try { - zkController.getZkClient().delete(nonManagedSchemaPath, -1, true); + zkController.getZkClient().delete(nonManagedSchemaPath, -1); } catch (KeeperException.NoNodeException ex) { // ignore - someone beat us to it } @@ -524,7 +524,7 @@ private void zkUgradeToManagedSchema() { if (locked) { // unlock try { - zkClient.delete(lockPath, -1, true); + zkClient.delete(lockPath, -1); } catch (KeeperException.NoNodeException nne) { // ignore - someone else deleted it } catch (Exception e) { diff --git a/solr/core/src/java/org/apache/solr/schema/SchemaManager.java b/solr/core/src/java/org/apache/solr/schema/SchemaManager.java index 801863fa882..e99270078a1 100644 --- a/solr/core/src/java/org/apache/solr/schema/SchemaManager.java +++ b/solr/core/src/java/org/apache/solr/schema/SchemaManager.java @@ -490,10 +490,10 @@ private ManagedIndexSchema getFreshManagedSchema(SolrCore core) SolrZkClient zkClient = zkLoader.getZkController().getZkClient(); String managedSchemaPath = zkLoader.getConfigSetZkPath() + "/" + schemaResourceName; try { - if (!zkClient.exists(managedSchemaPath, true)) { + if (!zkClient.exists(managedSchemaPath)) { String backupName = schemaResourceName + ManagedIndexSchemaFactory.UPGRADED_SCHEMA_EXTENSION; - if (!zkClient.exists(zkLoader.getConfigSetZkPath() + "/" + backupName, true)) { + if (!zkClient.exists(zkLoader.getConfigSetZkPath() + "/" + backupName)) { log.warn( "Unable to retrieve fresh managed schema, neither {} nor {} exist.", schemaResourceName, diff --git a/solr/core/src/java/org/apache/solr/schema/ZkIndexSchemaReader.java b/solr/core/src/java/org/apache/solr/schema/ZkIndexSchemaReader.java index d37e812a891..40be270e09e 100644 --- a/solr/core/src/java/org/apache/solr/schema/ZkIndexSchemaReader.java +++ b/solr/core/src/java/org/apache/solr/schema/ZkIndexSchemaReader.java @@ -101,7 +101,7 @@ public SchemaWatcher createSchemaWatcher() { SchemaWatcher watcher = new SchemaWatcher(this); try { - zkClient.exists(managedSchemaPath, watcher, true); + zkClient.exists(managedSchemaPath, watcher); } catch (KeeperException e) { final String msg = "Error creating ZooKeeper watch for the managed schema"; log.error(msg, e); @@ -173,7 +173,7 @@ void updateSchema(Watcher watcher, int expectedZkVersion) synchronized (getSchemaUpdateLock()) { final ManagedIndexSchema oldSchema = managedIndexSchemaFactory.getSchema(); if (expectedZkVersion == -1 || oldSchema.schemaZkVersion < expectedZkVersion) { - byte[] data = zkClient.getData(managedSchemaPath, watcher, stat, true); + byte[] data = zkClient.getData(managedSchemaPath, watcher, stat); if (stat.getVersion() != oldSchema.schemaZkVersion) { if (log.isInfoEnabled()) { log.info("Retrieved schema version {} from Zookeeper", stat.getVersion()); diff --git a/solr/core/src/java/org/apache/solr/servlet/HttpSolrCall.java b/solr/core/src/java/org/apache/solr/servlet/HttpSolrCall.java index ce9b1f8e6be..3dfd33ee6b9 100644 --- a/solr/core/src/java/org/apache/solr/servlet/HttpSolrCall.java +++ b/solr/core/src/java/org/apache/solr/servlet/HttpSolrCall.java @@ -471,7 +471,7 @@ protected void extractRemotePath(String collectionName, String origCorename) .getZkController() .zkStateReader .getZkClient() - .exists(DocCollection.getCollectionPath(collectionName), true)) { + .exists(DocCollection.getCollectionPath(collectionName))) { // no change and such a collection does not exist. go back return; } diff --git a/solr/core/src/java/org/apache/solr/servlet/QueryRateLimiter.java b/solr/core/src/java/org/apache/solr/servlet/QueryRateLimiter.java index 6b54ce450cd..5b57617fa83 100644 --- a/solr/core/src/java/org/apache/solr/servlet/QueryRateLimiter.java +++ b/solr/core/src/java/org/apache/solr/servlet/QueryRateLimiter.java @@ -69,7 +69,7 @@ private static RateLimiterConfig constructQueryRateLimiterConfig(SolrZkClient zk new RateLimiterConfig(SolrRequest.SolrRequestType.QUERY); Map clusterPropsJson = (Map) - Utils.fromJSON(zkClient.getData(ZkStateReader.CLUSTER_PROPS, null, new Stat(), true)); + Utils.fromJSON(zkClient.getData(ZkStateReader.CLUSTER_PROPS, null, new Stat())); byte[] configInput = Utils.toJSON(clusterPropsJson.get(RL_CONFIG_KEY)); if (configInput.length == 0) { diff --git a/solr/core/src/java/org/apache/solr/update/processor/DistributedZkUpdateProcessor.java b/solr/core/src/java/org/apache/solr/update/processor/DistributedZkUpdateProcessor.java index a1e491c82bb..5893c41763b 100644 --- a/solr/core/src/java/org/apache/solr/update/processor/DistributedZkUpdateProcessor.java +++ b/solr/core/src/java/org/apache/solr/update/processor/DistributedZkUpdateProcessor.java @@ -1458,7 +1458,7 @@ private void zkCheck(UpdateCommand updateCommand) { return; } - if (!zkController.getZkClient().getConnectionManager().isLikelyExpired()) { + if (zkController.isConnected()) { return; } diff --git a/solr/core/src/test/org/apache/solr/cloud/AliasIntegrationTest.java b/solr/core/src/test/org/apache/solr/cloud/AliasIntegrationTest.java index 970f4d8478f..5b4fb191dad 100644 --- a/solr/core/src/test/org/apache/solr/cloud/AliasIntegrationTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/AliasIntegrationTest.java @@ -124,7 +124,7 @@ public void testProperties() throws Exception { assertEquals("collection1meta", aliases.get(0)); assertEquals("collection2meta", aliases.get(1)); // ensure we have the back-compat format in ZK: - final byte[] rawBytes = zkStateReader.getZkClient().getData(ALIASES, null, null, true); + final byte[] rawBytes = zkStateReader.getZkClient().getData(ALIASES, null, null); assertTrue( ((Map>) Utils.fromJSON(rawBytes)).get("collection").get("meta1") instanceof String); diff --git a/solr/core/src/test/org/apache/solr/cloud/AssignBackwardCompatibilityTest.java b/solr/core/src/test/org/apache/solr/cloud/AssignBackwardCompatibilityTest.java index 0587fada196..7275293c6de 100644 --- a/solr/core/src/test/org/apache/solr/cloud/AssignBackwardCompatibilityTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/AssignBackwardCompatibilityTest.java @@ -73,7 +73,7 @@ public void test() if (random().nextBoolean() && i > 5 && !clearedCounter) { log.info("Clear collection counter"); // clear counter - cluster.getZkClient().delete("/collections/" + COLLECTION + "/counter", -1, true); + cluster.getZkClient().delete("/collections/" + COLLECTION + "/counter", -1); clearedCounter = true; } if (deleteReplica) { @@ -115,7 +115,7 @@ private int getCounter() throws InterruptedException { byte[] data = cluster .getZkClient() - .getData("/collections/" + COLLECTION + "/counter", null, new Stat(), true); + .getData("/collections/" + COLLECTION + "/counter", null, new Stat()); int count = NumberUtils.bytesToInt(data); if (count < 0) throw new AssertionError("Found negative collection counter " + count); return count; diff --git a/solr/core/src/test/org/apache/solr/cloud/CollectionPropsTest.java b/solr/core/src/test/org/apache/solr/cloud/CollectionPropsTest.java index 7d963ee6b9a..87f71cc0570 100644 --- a/solr/core/src/test/org/apache/solr/cloud/CollectionPropsTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/CollectionPropsTest.java @@ -171,8 +171,7 @@ private void waitForValue(String propertyName, String expectedValue) throws Inte new String( cluster .getZkClient() - .getData( - "/collections/" + collectionName + "/collectionprops.json", null, null, true), + .getData("/collections/" + collectionName + "/collectionprops.json", null, null), StandardCharsets.UTF_8); } catch (Exception e) { collectionpropsInZk = "Could not get file from ZooKeeper: " + e.getMessage(); @@ -222,7 +221,7 @@ public void testWatcher() throws KeeperException, InterruptedException, IOExcept log.info("deleting props"); zkStateReader .getZkClient() - .delete("/collections/" + collectionName + "/collectionprops.json", -1, true); + .delete("/collections/" + collectionName + "/collectionprops.json", -1); assertEquals(1, watcher.waitForTrigger()); final Map props = watcher.getProps(); assertTrue(props.toString(), props.isEmpty()); diff --git a/solr/core/src/test/org/apache/solr/cloud/CollectionStateZnodeTest.java b/solr/core/src/test/org/apache/solr/cloud/CollectionStateZnodeTest.java index 0c43b93ea80..05eb9e5c71b 100644 --- a/solr/core/src/test/org/apache/solr/cloud/CollectionStateZnodeTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/CollectionStateZnodeTest.java @@ -50,10 +50,10 @@ public void testZkNodeLocation() throws Exception { (n, c) -> DocCollection.isFullyActive(n, c, 2, 2)); assertTrue( "Collection path does not exist", - zkClient().exists(DocCollection.getCollectionPath(collectionName), true)); + zkClient().exists(DocCollection.getCollectionPath(collectionName))); Stat stat = new Stat(); - zkClient().getData(DocCollection.getCollectionPath(collectionName), null, stat, true); + zkClient().getData(DocCollection.getCollectionPath(collectionName), null, stat); DocCollection c = getCollectionState(collectionName); @@ -68,6 +68,6 @@ public void testZkNodeLocation() throws Exception { assertFalse( "collection state should not exist", - zkClient().exists(DocCollection.getCollectionPath(collectionName), true)); + zkClient().exists(DocCollection.getCollectionPath(collectionName))); } } diff --git a/solr/core/src/test/org/apache/solr/cloud/ConnectionManagerTest.java b/solr/core/src/test/org/apache/solr/cloud/ConnectionManagerTest.java deleted file mode 100644 index d48ba5bc3cc..00000000000 --- a/solr/core/src/test/org/apache/solr/cloud/ConnectionManagerTest.java +++ /dev/null @@ -1,186 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.solr.cloud; - -import java.io.IOException; -import java.nio.file.Path; -import java.util.concurrent.Executors; -import java.util.concurrent.ScheduledExecutorService; -import java.util.concurrent.TimeUnit; -import java.util.concurrent.TimeoutException; -import org.apache.solr.SolrTestCaseJ4; -import org.apache.solr.common.cloud.ConnectionManager; -import org.apache.solr.common.cloud.SolrZkClient; -import org.apache.solr.common.util.SolrNamedThreadFactory; -import org.apache.zookeeper.TestableZooKeeper; -import org.apache.zookeeper.WatchedEvent; -import org.apache.zookeeper.Watcher; -import org.apache.zookeeper.Watcher.Event.EventType; -import org.apache.zookeeper.Watcher.Event.KeeperState; -import org.apache.zookeeper.ZooKeeper; -import org.junit.Ignore; -import org.junit.Test; - -public class ConnectionManagerTest extends SolrTestCaseJ4 { - - static final int TIMEOUT = 3000; - - @Ignore - public void testConnectionManager() throws Exception { - - // setup a SolrZkClient to do some getBaseUrlForNodeName testing - Path zkDir = createTempDir("zkData"); - ZkTestServer server = new ZkTestServer(zkDir); - try { - server.run(); - - SolrZkClient zkClient = - new SolrZkClient.Builder() - .withUrl(server.getZkAddress()) - .withTimeout(TIMEOUT, TimeUnit.MILLISECONDS) - .build(); - ConnectionManager cm = zkClient.getConnectionManager(); - try { - assertFalse(cm.isLikelyExpired()); - - ZooKeeper zk = zkClient.getZooKeeper(); - assertTrue(zk instanceof TestableZooKeeper); - ((TestableZooKeeper) zk).testableConnloss(); - server.expire(zkClient.getZooKeeper().getSessionId()); - - Thread.sleep(TIMEOUT); - - assertTrue(cm.isLikelyExpired()); - } finally { - cm.close(); - zkClient.close(); - } - } finally { - server.shutdown(); - } - } - - public void testLikelyExpired() throws Exception { - - // setup a SolrZkClient to do some getBaseUrlForNodeName testing - Path zkDir = createTempDir("zkData"); - ZkTestServer server = new ZkTestServer(zkDir); - try { - server.run(); - - SolrZkClient zkClient = - new SolrZkClient.Builder() - .withUrl(server.getZkAddress()) - .withTimeout(TIMEOUT, TimeUnit.MILLISECONDS) - .build(); - ConnectionManager cm = zkClient.getConnectionManager(); - try { - assertFalse(cm.isLikelyExpired()); - assertTrue(cm.isConnectedAndNotClosed()); - cm.process(new WatchedEvent(EventType.None, KeeperState.Disconnected, "")); - // disconnect shouldn't immediately set likelyExpired - assertFalse(cm.isConnectedAndNotClosed()); - assertFalse(cm.isLikelyExpired()); - - // but it should after the timeout - Thread.sleep((long) (zkClient.getZkClientTimeout() * 1.5)); - assertFalse(cm.isConnectedAndNotClosed()); - assertTrue(cm.isLikelyExpired()); - - // even if we disconnect immediately again - cm.process(new WatchedEvent(EventType.None, KeeperState.Disconnected, "")); - assertFalse(cm.isConnectedAndNotClosed()); - assertTrue(cm.isLikelyExpired()); - - // reconnect -- should no longer be likely expired - cm.process(new WatchedEvent(EventType.None, KeeperState.SyncConnected, "")); - assertFalse(cm.isLikelyExpired()); - assertTrue(cm.isConnectedAndNotClosed()); - } finally { - cm.close(); - zkClient.close(); - } - } finally { - server.shutdown(); - } - } - - @Test - public void testReconnectWhenZkDisappeared() throws Exception { - ScheduledExecutorService executor = - Executors.newSingleThreadScheduledExecutor( - new SolrNamedThreadFactory("connectionManagerTest")); - - // setup a SolrZkClient to do some getBaseUrlForNodeName testing - Path zkDir = createTempDir("zkData"); - ZkTestServer server = new ZkTestServer(zkDir); - try { - server.run(); - - MockZkClientConnectionStrategy strategy = new MockZkClientConnectionStrategy(); - SolrZkClient zkClient = - new SolrZkClient.Builder() - .withUrl(server.getZkAddress()) - .withTimeout(TIMEOUT, TimeUnit.MILLISECONDS) - .withConnStrategy(strategy) - .build(); - ConnectionManager cm = zkClient.getConnectionManager(); - - try { - assertFalse(cm.isLikelyExpired()); - assertTrue(cm.isConnectedAndNotClosed()); - - // reconnect -- should no longer be likely expired - cm.process(new WatchedEvent(EventType.None, KeeperState.Expired, "")); - assertFalse(cm.isLikelyExpired()); - assertTrue(cm.isConnectedAndNotClosed()); - assertTrue(strategy.isExceptionThrow()); - } finally { - cm.close(); - zkClient.close(); - executor.shutdown(); - } - } finally { - server.shutdown(); - } - } - - private static class MockZkClientConnectionStrategy extends TestConnectionStrategy { - int called = 0; - boolean exceptionThrown = false; - - @Override - public void reconnect( - final String serverAddress, - final int zkClientTimeout, - final Watcher watcher, - final ZkUpdate updater) - throws IOException, InterruptedException, TimeoutException { - - if (called++ < 1) { - exceptionThrown = true; - throw new IOException("Testing"); - } - - super.reconnect(serverAddress, zkClientTimeout, watcher, updater); - } - - public boolean isExceptionThrow() { - return exceptionThrown; - } - } -} diff --git a/solr/core/src/test/org/apache/solr/cloud/DistributedQueueTest.java b/solr/core/src/test/org/apache/solr/cloud/DistributedQueueTest.java index 7dd57605a9d..7a5836391c8 100644 --- a/solr/core/src/test/org/apache/solr/cloud/DistributedQueueTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/DistributedQueueTest.java @@ -19,6 +19,7 @@ import java.nio.charset.Charset; import java.nio.charset.StandardCharsets; import java.util.NoSuchElementException; +import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Future; import java.util.concurrent.TimeUnit; @@ -26,6 +27,7 @@ import java.util.function.Predicate; import org.apache.solr.SolrTestCaseJ4; import org.apache.solr.client.solrj.cloud.DistributedQueue; +import org.apache.solr.common.cloud.OnDisconnect; import org.apache.solr.common.cloud.SolrZkClient; import org.apache.solr.common.util.ExecutorUtil; import org.apache.solr.common.util.SolrNamedThreadFactory; @@ -289,18 +291,19 @@ public void testPeekElements() throws Exception { } private void forceSessionExpire() throws InterruptedException, TimeoutException { - long sessionId = zkClient.getZooKeeper().getSessionId(); + final CountDownLatch hasDisconnected = new CountDownLatch(1); + zkClient + .getCuratorFramework() + .getConnectionStateListenable() + .addListener((OnDisconnect) hasDisconnected::countDown); + long sessionId = zkClient.getZkSessionId(); zkServer.expire(sessionId); - zkClient.getConnectionManager().waitForDisconnected(10000); - zkClient.getConnectionManager().waitForConnected(10000); - for (int i = 0; i < 100; ++i) { - if (zkClient.isConnected()) { - break; - } - Thread.sleep(50); - } + hasDisconnected.await(10, TimeUnit.SECONDS); + assertEquals( + "ZK Client did not disconnect after session expiration", 0, hasDisconnected.getCount()); + zkClient.getCuratorFramework().blockUntilConnected(10, TimeUnit.SECONDS); assertTrue(zkClient.isConnected()); - assertNotEquals(sessionId, zkClient.getZooKeeper().getSessionId()); + assertNotEquals(sessionId, zkClient.getZkSessionId()); } protected ZkDistributedQueue makeDistributedQueue(String dqZNode) throws Exception { @@ -331,9 +334,9 @@ public void run() { } protected String setupNewDistributedQueueZNode(String znodePath) throws Exception { - if (!zkClient.exists("/", true)) zkClient.makePath("/", false, true); - if (zkClient.exists(znodePath, true)) zkClient.clean(znodePath); - zkClient.makePath(znodePath, false, true); + if (!zkClient.exists("/")) zkClient.makePath("/", false); + if (zkClient.exists(znodePath)) zkClient.clean(znodePath); + zkClient.makePath(znodePath, false); return znodePath; } diff --git a/solr/core/src/test/org/apache/solr/cloud/LeaderElectionContextKeyTest.java b/solr/core/src/test/org/apache/solr/cloud/LeaderElectionContextKeyTest.java index 0fd64f1306c..6e0860023fd 100644 --- a/solr/core/src/test/org/apache/solr/cloud/LeaderElectionContextKeyTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/LeaderElectionContextKeyTest.java @@ -130,7 +130,6 @@ private List getElectionNodes(String collection, String shard, SolrZkCli throws KeeperException, InterruptedException { return client.getChildren( "/collections/" + collection + "/leader_elect/" + shard + LeaderElector.ELECTION_NODE, - null, - true); + null); } } diff --git a/solr/core/src/test/org/apache/solr/cloud/LeaderElectionTest.java b/solr/core/src/test/org/apache/solr/cloud/LeaderElectionTest.java index 44e226afdf0..6446a7ced54 100644 --- a/solr/core/src/test/org/apache/solr/cloud/LeaderElectionTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/LeaderElectionTest.java @@ -28,6 +28,7 @@ import java.util.concurrent.Executors; import java.util.concurrent.ScheduledExecutorService; import java.util.concurrent.TimeUnit; +import org.apache.curator.test.KillSession; import org.apache.solr.SolrTestCaseJ4; import org.apache.solr.common.cloud.OnReconnect; import org.apache.solr.common.cloud.SolrZkClient; @@ -39,8 +40,6 @@ import org.apache.zookeeper.KeeperException; import org.apache.zookeeper.KeeperException.NoNodeException; import org.apache.zookeeper.KeeperException.SessionExpiredException; -import org.apache.zookeeper.TestableZooKeeper; -import org.apache.zookeeper.ZooKeeper; import org.junit.Test; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -73,8 +72,8 @@ public void setUp() throws Exception { .build(); zkStateReader = new ZkStateReader(zkClient); seqToThread = Collections.synchronizedMap(new HashMap()); - zkClient.makePath("/collections/collection1", true); - zkClient.makePath("/collections/collection2", true); + zkClient.makePath("/collections/collection1"); + zkClient.makePath("/collections/collection2"); } static class TestLeaderElectionContext extends ShardLeaderElectionContextBase { @@ -119,7 +118,7 @@ public ElectorSetup(OnReconnect onReconnect) { .build(); zkStateReader = new ZkStateReader(zkClient); elector = new LeaderElector(zkClient); - zkController = MockSolrSource.makeSimpleMock(null, zkStateReader, null); + zkController = MockSolrSource.makeSimpleMock(null, zkStateReader, zkClient); } public void close() { @@ -187,9 +186,10 @@ private void setupOnConnect() throws InterruptedException, KeeperException { public void run() { try { setupOnConnect(); + } catch (IllegalStateException ignored) { + return; } catch (Throwable e) { log.error("setup failed", e); - es.close(); return; } @@ -292,8 +292,7 @@ private String getLeaderUrl(final String collection, final String slice) while (iterCount-- > 0) { try { byte[] data = - zkClient.getData( - ZkStateReader.getShardLeadersPath(collection, slice), null, null, true); + zkClient.getData(ZkStateReader.getShardLeadersPath(collection, slice), null, null); ZkCoreNodeProps leaderProps = new ZkCoreNodeProps(ZkNodeProps.load(data)); return leaderProps.getCoreUrl(); } catch (NoNodeException | SessionExpiredException e) { @@ -478,8 +477,7 @@ public void testStressElection() throws Exception { final List threads = Collections.synchronizedList(new ArrayList()); // start with a leader - ClientThread thread1 = null; - thread1 = new ClientThread("shard1", 0); + ClientThread thread1 = new ClientThread("shard1", 0); threads.add(thread1); scheduler.schedule(thread1, 0, TimeUnit.MILLISECONDS); @@ -539,11 +537,15 @@ public void run() { int j; j = random().nextInt(threads.size()); try { - ZooKeeper zk = threads.get(j).es.zkClient.getZooKeeper(); - assertTrue(zk instanceof TestableZooKeeper); - ((TestableZooKeeper) zk).testableConnloss(); if (random().nextBoolean()) { - server.expire(zk.getSessionId()); + KillSession.kill( + threads + .get(j) + .es + .zkClient + .getCuratorFramework() + .getZookeeperClient() + .getZooKeeper()); } } catch (Exception e) { log.error("error expiring session", e); @@ -555,36 +557,43 @@ public void run() { } }); - scheduleThread.start(); - connLossThread.start(); - killThread.start(); + try { + scheduleThread.start(); + connLossThread.start(); + killThread.start(); - Thread.sleep(4000); + Thread.sleep(4000); - stopStress = true; + stopStress = true; - scheduleThread.interrupt(); - connLossThread.interrupt(); - killThread.interrupt(); + scheduleThread.interrupt(); + connLossThread.interrupt(); + killThread.interrupt(); - scheduleThread.join(); - scheduler.shutdownNow(); + scheduleThread.join(); + scheduler.shutdownNow(); - connLossThread.join(); - killThread.join(); + connLossThread.join(); + killThread.join(); - int seq = threads.get(getLeaderThread()).getSeq(); + int seq = threads.get(getLeaderThread()).getSeq(); - // we have a leader we know, TODO: lets check some other things + // we have a leader we know, TODO: lets check some other things + } finally { + // cleanup any threads still running + for (ClientThread thread : threads) { + thread.close(); + } - // cleanup any threads still running - for (ClientThread thread : threads) { - thread.es.zkClient.getZooKeeper().close(); - thread.close(); - } + // cleanup any threads still running + for (ClientThread thread : threads) { + thread.es.zkClient.close(); + thread.close(); + } - for (Thread thread : threads) { - thread.join(); + for (Thread thread : threads) { + thread.join(); + } } } diff --git a/solr/core/src/test/org/apache/solr/cloud/LeaderVoteWaitTimeoutTest.java b/solr/core/src/test/org/apache/solr/cloud/LeaderVoteWaitTimeoutTest.java index 146a05388e8..064a9e5ae3c 100644 --- a/solr/core/src/test/org/apache/solr/cloud/LeaderVoteWaitTimeoutTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/LeaderVoteWaitTimeoutTest.java @@ -279,7 +279,7 @@ public void testMostInSyncReplicasCanWinElection() throws Exception { List children = zkClient() .getChildren( - "/collections/" + collectionName + "/leader_elect/shard1/election", null, true); + "/collections/" + collectionName + "/leader_elect/shard1/election", null); log.info("{} election nodes:{}", collectionName, children); throw e; } diff --git a/solr/core/src/test/org/apache/solr/cloud/OutOfBoxZkACLAndCredentialsProvidersTest.java b/solr/core/src/test/org/apache/solr/cloud/OutOfBoxZkACLAndCredentialsProvidersTest.java index 8c45324946c..b211096aae3 100644 --- a/solr/core/src/test/org/apache/solr/cloud/OutOfBoxZkACLAndCredentialsProvidersTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/OutOfBoxZkACLAndCredentialsProvidersTest.java @@ -76,7 +76,7 @@ public void setUp() throws Exception { .withUrl(zkServer.getZkHost()) .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build(); - zkClient.makePath("/solr", false, true); + zkClient.makePath("/solr", false); zkClient.close(); zkClient = @@ -85,21 +85,17 @@ public void setUp() throws Exception { .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build(); zkClient.create( - "/protectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); + "/protectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.makePath( - "/protectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); + "/protectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.create( - "/unprotectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); + "/unprotectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.makePath( - "/unprotectedMakePathNode", - "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); + "/unprotectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.create( SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH, "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); + CreateMode.PERSISTENT); zkClient.close(); if (log.isInfoEnabled()) { @@ -152,7 +148,7 @@ public void testOpenACLUnsafeAllover() throws Exception { protected void assertOpenACLUnsafeAllover( SolrZkClient zkClient, String path, List verifiedList) throws Exception { - List acls = zkClient.getZooKeeper().getACL(path, new Stat()); + List acls = zkClient.getACL(path, new Stat()); if (log.isInfoEnabled()) { log.info("Verifying {}", path); } @@ -169,7 +165,7 @@ protected void assertOpenACLUnsafeAllover( "Path " + path + " does not have OPEN_ACL_UNSAFE", ZooDefs.Ids.OPEN_ACL_UNSAFE, acls); } verifiedList.add(path); - List children = zkClient.getChildren(path, null, false); + List children = zkClient.getChildren(path, null); for (String child : children) { assertOpenACLUnsafeAllover( zkClient, path + ((path.endsWith("/")) ? "" : "/") + child, verifiedList); diff --git a/solr/core/src/test/org/apache/solr/cloud/OverriddenZkACLAndCredentialsProvidersTest.java b/solr/core/src/test/org/apache/solr/cloud/OverriddenZkACLAndCredentialsProvidersTest.java index 79fdac41acf..cc593562d4e 100644 --- a/solr/core/src/test/org/apache/solr/cloud/OverriddenZkACLAndCredentialsProvidersTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/OverriddenZkACLAndCredentialsProvidersTest.java @@ -29,15 +29,17 @@ import java.util.ArrayList; import java.util.List; import java.util.concurrent.TimeUnit; +import org.apache.curator.framework.AuthInfo; +import org.apache.curator.framework.api.ACLProvider; import org.apache.solr.SolrTestCaseJ4; import org.apache.solr.common.cloud.DigestZkACLProvider; import org.apache.solr.common.cloud.DigestZkCredentialsProvider; import org.apache.solr.common.cloud.SecurityAwareZkACLProvider; import org.apache.solr.common.cloud.SolrZkClient; import org.apache.solr.common.cloud.VMParamsZkCredentialsInjector; -import org.apache.solr.common.cloud.ZkACLProvider; import org.apache.solr.common.cloud.ZkCredentialsInjector; import org.apache.solr.common.cloud.ZkCredentialsProvider; +import org.apache.solr.common.util.StrUtils; import org.apache.zookeeper.CreateMode; import org.junit.AfterClass; import org.junit.BeforeClass; @@ -80,50 +82,47 @@ public void setUp() throws Exception { System.setProperty("zkHost", zkServer.getZkAddress()); - SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClientFactoryUsingCompletelyNewProviders( "connectAndAllACLUsername", "connectAndAllACLPassword", "readonlyACLUsername", "readonlyACLPassword") - .getSolrZkClient(zkServer.getZkHost(), AbstractZkTestCase.TIMEOUT); - zkClient.makePath("/solr", false, true); - zkClient.close(); + .getSolrZkClient(zkServer.getZkHost(), AbstractZkTestCase.TIMEOUT)) { + zkClient.makePath("/solr", false); + } - zkClient = + try (SolrZkClient zkClient = new SolrZkClientFactoryUsingCompletelyNewProviders( "connectAndAllACLUsername", "connectAndAllACLPassword", "readonlyACLUsername", "readonlyACLPassword") - .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT); - zkClient.create( - "/protectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); - zkClient.makePath( - "/protectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); - zkClient.create( - SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH, - "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); - zkClient.close(); - - zkClient = + .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT)) { + zkClient.create( + "/protectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); + zkClient.makePath( + "/protectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); + zkClient.create( + SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH, + "content".getBytes(DATA_ENCODING), + CreateMode.PERSISTENT); + } + + try (SolrZkClient zkClient = new SolrZkClientFactoryUsingCompletelyNewProviders(null, null, null, null) - .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT); - zkClient - .getZooKeeper() - .addAuthInfo( - "digest", - ("connectAndAllACLUsername:connectAndAllACLPassword").getBytes(DATA_ENCODING)); - zkClient.create( - "/unprotectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); - zkClient.makePath( - "/unprotectedMakePathNode", - "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); - zkClient.close(); + .getSolrZkClient( + zkServer.getZkAddress(), + AbstractZkTestCase.TIMEOUT, + new AuthInfo( + "digest", + ("connectAndAllACLUsername:connectAndAllACLPassword") + .getBytes(DATA_ENCODING)))) { + zkClient.create( + "/unprotectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); + zkClient.makePath( + "/unprotectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); + } if (log.isInfoEnabled()) { log.info("####SETUP_END {}", getTestName()); @@ -141,58 +140,46 @@ public void tearDown() throws Exception { @Test public void testNoCredentialsSolrZkClientFactoryUsingCompletelyNewProviders() throws Exception { - SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClientFactoryUsingCompletelyNewProviders(null, null, null, null) - .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT); - try { + .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT)) { AbstractDigestZkACLAndCredentialsProvidersTestBase.doTest( zkClient, false, false, false, false, false, false, false, false, false, false); - } finally { - zkClient.close(); } } @Test public void testWrongCredentialsSolrZkClientFactoryUsingCompletelyNewProviders() throws Exception { - SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClientFactoryUsingCompletelyNewProviders( "connectAndAllACLUsername", "connectAndAllACLPasswordWrong", null, null) - .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT); - try { + .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT)) { AbstractDigestZkACLAndCredentialsProvidersTestBase.doTest( zkClient, false, false, false, false, false, false, false, false, false, false); - } finally { - zkClient.close(); } } @Test public void testAllCredentialsSolrZkClientFactoryUsingCompletelyNewProviders() throws Exception { - SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClientFactoryUsingCompletelyNewProviders( "connectAndAllACLUsername", "connectAndAllACLPassword", null, null) - .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT); - try { + .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT)) { AbstractDigestZkACLAndCredentialsProvidersTestBase.doTest( zkClient, true, true, true, true, true, true, true, true, true, true); - } finally { - zkClient.close(); } } @Test public void testReadonlyCredentialsSolrZkClientFactoryUsingCompletelyNewProviders() throws Exception { - SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClientFactoryUsingCompletelyNewProviders( "readonlyACLUsername", "readonlyACLPassword", null, null) - .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT); - try { + .getSolrZkClient(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT)) { AbstractDigestZkACLAndCredentialsProvidersTestBase.doTest( zkClient, true, true, false, false, false, false, false, false, false, false); - } finally { - zkClient.close(); } } @@ -202,16 +189,13 @@ public void testReadonlyCredentialsSolrZkClientFactoryUsingCompletelyNewProvider throws Exception { useNoCredentials(); - SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClientUsingVMParamsProvidersButWithDifferentVMParamsNames( new SolrZkClient.Builder() .withUrl(zkServer.getZkAddress()) - .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS)); - try { + .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS))) { AbstractDigestZkACLAndCredentialsProvidersTestBase.doTest( zkClient, false, false, false, false, false, false, false, false, false, false); - } finally { - zkClient.close(); } } @@ -221,16 +205,13 @@ public void testReadonlyCredentialsSolrZkClientFactoryUsingCompletelyNewProvider throws Exception { useWrongCredentials(); - SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClientUsingVMParamsProvidersButWithDifferentVMParamsNames( new SolrZkClient.Builder() .withUrl(zkServer.getZkAddress()) - .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS)); - try { + .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS))) { AbstractDigestZkACLAndCredentialsProvidersTestBase.doTest( zkClient, false, false, false, false, false, false, false, false, false, false); - } finally { - zkClient.close(); } } @@ -240,16 +221,13 @@ public void testReadonlyCredentialsSolrZkClientFactoryUsingCompletelyNewProvider throws Exception { useAllCredentials(); - SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClientUsingVMParamsProvidersButWithDifferentVMParamsNames( new SolrZkClient.Builder() .withUrl(zkServer.getZkAddress()) - .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS)); - try { + .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS))) { AbstractDigestZkACLAndCredentialsProvidersTestBase.doTest( zkClient, true, true, true, true, true, true, true, true, true, true); - } finally { - zkClient.close(); } } @@ -259,16 +237,13 @@ public void testReadonlyCredentialsSolrZkClientFactoryUsingCompletelyNewProvider throws Exception { useReadonlyCredentials(); - SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClientUsingVMParamsProvidersButWithDifferentVMParamsNames( new SolrZkClient.Builder() .withUrl(zkServer.getZkAddress()) - .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS)); - try { + .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS))) { AbstractDigestZkACLAndCredentialsProvidersTestBase.doTest( zkClient, true, true, false, false, false, false, false, false, false, false); - } finally { - zkClient.close(); } } @@ -291,35 +266,38 @@ public SolrZkClientFactoryUsingCompletelyNewProviders( this.digestReadonlyPassword = digestReadonlyPassword; zkCredentialsInjector = () -> { - List zkCredentials = new ArrayList<>(2); ZkCredentialsInjector.ZkCredential allCreds = new ZkCredentialsInjector.ZkCredential(digestUsername, digestPassword, Perms.ALL); ZkCredentialsInjector.ZkCredential readCreds = new ZkCredentialsInjector.ZkCredential( digestReadonlyUsername, digestReadonlyPassword, Perms.READ); - zkCredentials.add(allCreds); - zkCredentials.add(readCreds); - return zkCredentials; + return List.of(allCreds, readCreds); }; } public SolrZkClient getSolrZkClient(String zkServerAddress, int zkClientTimeout) { + AuthInfo authInfo = null; + if (StrUtils.isNotNullOrEmpty(digestUsername) && StrUtils.isNotNullOrEmpty(digestPassword)) { + authInfo = + new AuthInfo( + "digest", (digestUsername + ":" + digestPassword).getBytes(StandardCharsets.UTF_8)); + } + return getSolrZkClient(zkServerAddress, zkClientTimeout, authInfo); + } - return new SolrZkClient( - new SolrZkClient.Builder() - .withUrl(zkServerAddress) - .withTimeout(zkClientTimeout, TimeUnit.MILLISECONDS)) { - - @Override - protected ZkCredentialsProvider createZkCredentialsToAddAutomatically() { - return new DigestZkCredentialsProvider(zkCredentialsInjector); - } - - @Override - public ZkACLProvider createZkACLProvider() { - return new DigestZkACLProvider(zkCredentialsInjector); - } - }; + public SolrZkClient getSolrZkClient( + String zkServerAddress, int zkClientTimeout, AuthInfo authInfo) { + final List authInfos = new ArrayList<>(); + if (authInfo != null) { + authInfos.add(authInfo); + } + return new SolrZkClient.Builder() + .withUrl(zkServerAddress) + .withZkCredentialsProvider( + new DigestZkCredentialsProvider(zkCredentialsInjector, authInfos)) + .withAclProvider(new DigestZkACLProvider(zkCredentialsInjector)) + .withTimeout(zkClientTimeout, TimeUnit.MILLISECONDS) + .build(); } } @@ -349,7 +327,7 @@ protected ZkCredentialsProvider createZkCredentialsToAddAutomatically() { } @Override - public ZkACLProvider createZkACLProvider() { + public ACLProvider createACLProvider() { return new DigestZkACLProvider(vmParamsZkCredentialsInjector); } } diff --git a/solr/core/src/test/org/apache/solr/cloud/OverseerCollectionConfigSetProcessorTest.java b/solr/core/src/test/org/apache/solr/cloud/OverseerCollectionConfigSetProcessorTest.java index ac3df8b4373..a64e35a7753 100644 --- a/solr/core/src/test/org/apache/solr/cloud/OverseerCollectionConfigSetProcessorTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/OverseerCollectionConfigSetProcessorTest.java @@ -401,7 +401,7 @@ protected Set commonMocks(int liveNodesCount, boolean distributedCluster when(clusterStateMock.getLiveNodes()).thenReturn(liveNodes); - when(solrZkClientMock.setData(anyString(), any(), anyInt(), anyBoolean())) + when(solrZkClientMock.setData(anyString(), any(), anyInt())) .then( invocation -> { System.out.println( @@ -414,7 +414,7 @@ protected Set commonMocks(int liveNodesCount, boolean distributedCluster return null; }); - when(solrZkClientMock.getData(anyString(), any(), any(), anyBoolean())) + when(solrZkClientMock.getData(anyString(), any(), any())) .thenAnswer( invocation -> { byte[] data = zkClientData.get(invocation.getArgument(0)); @@ -424,14 +424,14 @@ protected Set commonMocks(int liveNodesCount, boolean distributedCluster return data; }); - when(solrZkClientMock.create(any(), any(), any(), anyBoolean())) + when(solrZkClientMock.create(any(), any(), any())) .thenAnswer( invocation -> { zkClientData.put(invocation.getArgument(0), invocation.getArgument(1)); return invocation.getArgument(0); }); - when(solrZkClientMock.exists(any(String.class), anyBoolean())) + when(solrZkClientMock.exists(any(String.class))) .thenAnswer( invocation -> { String key = invocation.getArgument(0); @@ -519,7 +519,7 @@ public Void answer(InvocationOnMock invocation) { .when(distribStateManagerMock) .makePath(anyString()); - when(solrZkClientMock.exists(any(String.class), isNull(), anyBoolean())) + when(solrZkClientMock.exists(any(String.class), isNull())) .thenAnswer( invocation -> { String key = invocation.getArgument(0); diff --git a/solr/core/src/test/org/apache/solr/cloud/OverseerTest.java b/solr/core/src/test/org/apache/solr/cloud/OverseerTest.java index f6e108e0bf5..573a7d0191c 100644 --- a/solr/core/src/test/org/apache/solr/cloud/OverseerTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/OverseerTest.java @@ -58,7 +58,6 @@ import org.apache.solr.cloud.overseer.NodeMutator; import org.apache.solr.cloud.overseer.OverseerAction; import org.apache.solr.cloud.overseer.ZkWriteCommand; -import org.apache.solr.common.AlreadyClosedException; import org.apache.solr.common.SolrException; import org.apache.solr.common.cloud.ClusterState; import org.apache.solr.common.cloud.DocCollection; @@ -156,13 +155,13 @@ public MockZKController(String zkAddress, String nodeName, List overse // live node final String nodePath = ZkStateReader.LIVE_NODES_ZKNODE + "/" + nodeName; - zkClient.makePath(nodePath, CreateMode.EPHEMERAL, true); + zkClient.makePath(nodePath, CreateMode.EPHEMERAL); } private void deleteNode(final String path) { try { - zkClient.delete(path, -1, true); + zkClient.delete(path, -1); } catch (NoNodeException e) { // fine log.warn("cancelElection did not find election node to remove"); @@ -193,7 +192,7 @@ public void close() { public void createCollection(String collection, int numShards) throws Exception { // Create collection znode before having ClusterStateUpdater create state.json below, or it // will fail. - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collection, true); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collection); ZkNodeProps m = new ZkNodeProps( @@ -288,7 +287,7 @@ public String publishState( try { zkClient.makePath( - "/collections/" + collection + "/leader_elect/" + shardId + "/election", true); + "/collections/" + collection + "/leader_elect/" + shardId + "/election"); } catch (NodeExistsException nee) { } ZkNodeProps props = @@ -449,7 +448,7 @@ public void tearDown() throws Exception { private void createCollection(String collection, int numShards) throws Exception { // Create collection znode before having ClusterStateUpdater create state.json below, or it // will fail. - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collection, true); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collection); ZkNodeProps m = new ZkNodeProps( @@ -1204,7 +1203,7 @@ public void testShardLeaderChange() throws Exception { // Create collection znode before repeatedly trying to enqueue the cluster state update // message - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + COLLECTION, true); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + COLLECTION); for (int i = 0; i < atLeast(4); i++) { killCounter.incrementAndGet(); // for each round allow 1 kill @@ -1231,7 +1230,7 @@ public void testShardLeaderChange() throws Exception { ZkDistributedQueue q = getOpenOverseer().getStateUpdateQueue(); q.offer(m); break; - } catch (SolrException | KeeperException | AlreadyClosedException e) { + } catch (SolrException | KeeperException | IllegalStateException e) { log.error("error updating state", e); } } @@ -1249,7 +1248,7 @@ public void testShardLeaderChange() throws Exception { true, getOpenOverseer()); break; - } catch (SolrException | KeeperException | AlreadyClosedException e) { + } catch (SolrException | KeeperException | IllegalStateException e) { log.error("error publishing state", e); } } @@ -1274,7 +1273,7 @@ public void testShardLeaderChange() throws Exception { true, getOpenOverseer()); break; - } catch (SolrException | AlreadyClosedException e) { + } catch (SolrException | IllegalStateException e) { log.error("error publishing state", e); } } @@ -1294,7 +1293,7 @@ public void testShardLeaderChange() throws Exception { true, getOpenOverseer()); break; - } catch (SolrException | AlreadyClosedException e) { + } catch (SolrException | IllegalStateException e) { log.error("error publishing state", e); } } @@ -1314,7 +1313,7 @@ public void testShardLeaderChange() throws Exception { true, getOpenOverseer()); break; - } catch (SolrException | AlreadyClosedException e) { + } catch (SolrException | IllegalStateException e) { log.error("error publishing state", e); } } @@ -1453,7 +1452,7 @@ public void testPerformance() throws Exception { final int MAX_COLLECTIONS = 10, MAX_CORES = 10, MAX_STATE_CHANGES = 20000; for (int i = 0; i < MAX_COLLECTIONS; i++) { - zkClient.makePath("/collections/perf" + i, true); + zkClient.makePath("/collections/perf" + i); ZkNodeProps m = new ZkNodeProps( Overseer.QUEUE_OPERATION, @@ -1574,7 +1573,7 @@ public void testReplay() throws Exception { // state DistributedQueue queue = Overseer.getInternalWorkQueue(zkClient, new Stats()); - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + COLLECTION, true); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + COLLECTION); ZkNodeProps m = new ZkNodeProps( @@ -1752,7 +1751,7 @@ public void testExternalClusterStateChangeBehavior() throws Exception { q.offer(m); final String testCollectionName = "test"; - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + testCollectionName, true); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + testCollectionName); m = new ZkNodeProps( Overseer.QUEUE_OPERATION, @@ -1770,9 +1769,9 @@ public void testExternalClusterStateChangeBehavior() throws Exception { final String path = ZkStateReader.COLLECTIONS_ZKNODE + "/" + testCollectionName + "/state.json"; - byte[] data = zkClient.getData(path, null, null, true); + byte[] data = zkClient.getData(path, null, null); // Simulate an external modification of state.json - zkClient.setData(path, data, true); + zkClient.setData(path, data); m = new ZkNodeProps( @@ -1974,7 +1973,7 @@ public void testRemovalOfLastReplica() throws Exception { // create collection { - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + COLLECTION, true); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + COLLECTION); ZkNodeProps m = new ZkNodeProps( Overseer.QUEUE_OPERATION, diff --git a/solr/core/src/test/org/apache/solr/cloud/SolrCLIZkUtilsTest.java b/solr/core/src/test/org/apache/solr/cloud/SolrCLIZkUtilsTest.java index 38f6a674dd3..a5439a1c2e0 100644 --- a/solr/core/src/test/org/apache/solr/cloud/SolrCLIZkUtilsTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/SolrCLIZkUtilsTest.java @@ -124,8 +124,7 @@ public void testUpconfig() throws Exception { String content = new String( - zkClient.getData("/configs/upconfig2/schema.xml", null, null, true), - StandardCharsets.UTF_8); + zkClient.getData("/configs/upconfig2/schema.xml", null, null), StandardCharsets.UTF_8); assertTrue( "There should be content in the node! ", content.contains("Apache Software Foundation")); } @@ -354,7 +353,7 @@ public void testCp() throws Exception { assertEquals("Copy up to intermediate file should have succeeded.", 0, res); assertTrue( "Should have created an intermediate node on ZK", - zkClient.exists("/powerup/solrconfig.xml", true)); + zkClient.exists("/powerup/solrconfig.xml")); // copy individual file up // src and cp3 are valid @@ -374,8 +373,7 @@ public void testCp() throws Exception { cpTool.runTool(SolrCLI.processCommandLineArgs(cpTool.getName(), cpTool.getOptions(), args)); assertEquals("Copy up to named file should have succeeded.", 0, res); assertTrue( - "Should NOT have created an intermediate node on ZK", - zkClient.exists("/copyUpFile.xml", true)); + "Should NOT have created an intermediate node on ZK", zkClient.exists("/copyUpFile.xml")); // copy individual file down // src and cp3 are valid @@ -422,8 +420,7 @@ public void testCp() throws Exception { res = cpTool.runTool(SolrCLI.processCommandLineArgs(cpTool.getName(), cpTool.getOptions(), args)); assertEquals("Copy from somewhere in ZK to ZK root should have succeeded.", 0, res); - assertTrue( - "Should have found znode /solrconfig.xml: ", zkClient.exists("/solrconfig.xml", true)); + assertTrue("Should have found znode /solrconfig.xml: ", zkClient.exists("/solrconfig.xml")); // Check that the form path/ works for copying files up. Should append the last bit of the // source path to the dst @@ -468,8 +465,7 @@ public void testCp() throws Exception { assertEquals("Copy should have succeeded.", 0, res); String content = - new String( - zkClient.getData("/cp7/conf/stopwords", null, null, true), StandardCharsets.UTF_8); + new String(zkClient.getData("/cp7/conf/stopwords", null, null), StandardCharsets.UTF_8); assertTrue("There should be content in the node! ", content.contains("{Some Arbitrary Data}")); res = @@ -514,8 +510,7 @@ public void testCp() throws Exception { assertEquals("Copy should have succeeded.", 0, res); content = - new String( - zkClient.getData("/cp9/conf/stopwords", null, null, true), StandardCharsets.UTF_8); + new String(zkClient.getData("/cp9/conf/stopwords", null, null), StandardCharsets.UTF_8); assertTrue("There should be content in the node! ", content.contains("{Some Arbitrary Data}")); // Copy an individual empty file up and back down and insure it's still a file @@ -623,7 +618,7 @@ public void testMv() throws Exception { // Now does the moved directory match the original on disk? verifyZkLocalPathsMatch(srcPathCheck, "/mv2"); // And are we sure the old path is gone? - assertFalse("/configs/mv1 Znode should not be there: ", zkClient.exists("/configs/mv1", true)); + assertFalse("/configs/mv1 Znode should not be there: ", zkClient.exists("/configs/mv1")); // Files are in mv2 // Now fail if we specify "file:". Everything should still be in /mv2 @@ -649,7 +644,7 @@ public void testMv() throws Exception { mvTool.runTool(SolrCLI.processCommandLineArgs(mvTool.getName(), mvTool.getOptions(), args)); assertEquals("Move should have succeeded.", 0, res); - assertFalse("Znode /mv3 really should be gone", zkClient.exists("/mv3", true)); + assertFalse("Znode /mv3 really should be gone", zkClient.exists("/mv3")); // Now does the moved directory match the original on disk? verifyZkLocalPathsMatch(srcPathCheck, "/mv4"); @@ -665,10 +660,9 @@ public void testMv() throws Exception { mvTool.runTool(SolrCLI.processCommandLineArgs(mvTool.getName(), mvTool.getOptions(), args)); assertEquals("Move should have succeeded.", 0, res); assertTrue( - "Should be able to move a single file", - zkClient.exists("/testmvsingle/solrconfig.xml", true)); + "Should be able to move a single file", zkClient.exists("/testmvsingle/solrconfig.xml")); - zkClient.makePath("/parentNode", true); + zkClient.makePath("/parentNode"); // what happens if the destination ends with a slash? args = @@ -683,10 +677,9 @@ public void testMv() throws Exception { assertEquals("Move should have succeeded.", 0, res); assertTrue( "Should be able to move a single file to a parent znode", - zkClient.exists("/parentnode/schema.xml", true)); + zkClient.exists("/parentnode/schema.xml")); String content = - new String( - zkClient.getData("/parentnode/schema.xml", null, null, true), StandardCharsets.UTF_8); + new String(zkClient.getData("/parentnode/schema.xml", null, null), StandardCharsets.UTF_8); assertTrue( "There should be content in the node! ", content.contains("Apache Software Foundation")); } @@ -832,8 +825,7 @@ public void testRm() throws Exception { res = tool.runTool(SolrCLI.processCommandLineArgs(tool.getName(), tool.getOptions(), args)); assertEquals("Should have removed node /configs/rm1", res, 0); - assertFalse( - "Znode /configs/toremove really should be gone", zkClient.exists("/configs/rm1", true)); + assertFalse("Znode /configs/toremove really should be gone", zkClient.exists("/configs/rm1")); // Check that zk prefix also works. args = @@ -845,8 +837,7 @@ public void testRm() throws Exception { res = tool.runTool(SolrCLI.processCommandLineArgs(tool.getName(), tool.getOptions(), args)); assertEquals("Should have removed node /configs/rm2", res, 0); - assertFalse( - "Znode /configs/toremove2 really should be gone", zkClient.exists("/configs/rm2", true)); + assertFalse("Znode /configs/toremove2 really should be gone", zkClient.exists("/configs/rm2")); // This should silently just refuse to do anything to the / or /zookeeper args = @@ -869,14 +860,14 @@ private void verifyZkLocalPathsMatch(Path fileRoot, String zkRoot) } private static boolean isEphemeral(String zkPath) throws KeeperException, InterruptedException { - Stat znodeStat = zkClient.exists(zkPath, null, true); + Stat znodeStat = zkClient.exists(zkPath, null); return znodeStat.getEphemeralOwner() != 0; } void verifyAllZNodesAreFiles(Path fileRoot, String zkRoot) throws KeeperException, InterruptedException { - for (String child : zkClient.getChildren(zkRoot, null, true)) { + for (String child : zkClient.getChildren(zkRoot, null)) { // Skip ephemeral nodes if (zkRoot.endsWith("/") == false) zkRoot += "/"; if (isEphemeral(zkRoot + child)) continue; @@ -896,8 +887,7 @@ void verifyAllFilesAreZNodes(Path fileRoot, String zkRoot) throws IOException { void checkPathOnZk(Path path) { String znode = ZkMaintenanceUtils.createZkNodeName(zkRoot, fileRoot, path); try { // It's easier to catch this exception and fail than catch it everywhere else. - assertTrue( - "Should have found " + znode + " on Zookeeper", zkClient.exists(znode, true)); + assertTrue("Should have found " + znode + " on Zookeeper", zkClient.exists(znode)); } catch (Exception e) { fail( "Caught unexpected exception " @@ -933,10 +923,10 @@ private void verifyZnodesMatch(String first, String second) // Note, no fuss here with Windows path names. private void verifyFirstZNodesInSecond(String first, String second) throws KeeperException, InterruptedException { - for (String node : zkClient.getChildren(first, null, true)) { + for (String node : zkClient.getChildren(first, null)) { String fNode = first + "/" + node; String sNode = second + "/" + node; - assertTrue("Node " + sNode + " not found. Exists on " + fNode, zkClient.exists(sNode, true)); + assertTrue("Node " + sNode + " not found. Exists on " + fNode, zkClient.exists(sNode)); verifyFirstZNodesInSecond(fNode, sNode); } } diff --git a/solr/core/src/test/org/apache/solr/cloud/SolrXmlInZkTest.java b/solr/core/src/test/org/apache/solr/cloud/SolrXmlInZkTest.java index 868cd91e62a..3dd6948fc3f 100644 --- a/solr/core/src/test/org/apache/solr/cloud/SolrXmlInZkTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/SolrXmlInZkTest.java @@ -69,7 +69,7 @@ private void setUpZkAndDiskXml(boolean toZk, boolean leaveOnLocal) throws Except .build(); if (toZk) { - zkClient.makePath("solr.xml", XML_FOR_ZK.getBytes(StandardCharsets.UTF_8), true); + zkClient.makePath("solr.xml", XML_FOR_ZK.getBytes(StandardCharsets.UTF_8)); } zkClient.close(); diff --git a/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPI.java b/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPI.java index 1da60d85ff9..0272ac5f806 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPI.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPI.java @@ -354,7 +354,7 @@ private NamedList getConfigSetPropertiesFromZk(SolrZkClient zkClient, St throws Exception { byte[] oldPropsData = null; try { - oldPropsData = zkClient.getData(path, null, null, true); + oldPropsData = zkClient.getData(path, null, null); } catch (KeeperException.NoNodeException e) { // okay, properties just don't exist } @@ -444,17 +444,15 @@ public void testUploadErrors() throws Exception { .build(); // Create dummy config files in zookeeper - zkClient.makePath("/configs/myconf", true); + zkClient.makePath("/configs/myconf"); zkClient.create( "/configs/myconf/firstDummyFile", "first dummy content".getBytes(UTF_8), - CreateMode.PERSISTENT, - true); + CreateMode.PERSISTENT); zkClient.create( "/configs/myconf/anotherDummyFile", "second dummy content".getBytes(UTF_8), - CreateMode.PERSISTENT, - true); + CreateMode.PERSISTENT); // Checking error when configuration name specified already exists ignoreException("already exists"); @@ -472,10 +470,10 @@ public void testUploadErrors() throws Exception { assertEquals(400l, statusCode); assertTrue( "Expected file doesnt exist in zk. It's possibly overwritten", - zkClient.exists("/configs/myconf/firstDummyFile", true)); + zkClient.exists("/configs/myconf/firstDummyFile")); assertTrue( "Expected file doesnt exist in zk. It's possibly overwritten", - zkClient.exists("/configs/myconf/anotherDummyFile", true)); + zkClient.exists("/configs/myconf/anotherDummyFile")); zkClient.close(); solrClient.close(); @@ -533,7 +531,7 @@ public void testUploadLegacyManagedSchemaFile() throws Exception { assertTrue( "managed-schema file should have been uploaded", - zkClient.exists("/configs/" + configSetName + "/managed-schema", true)); + zkClient.exists("/configs/" + configSetName + "/managed-schema")); } finally { zkClient.close(); } @@ -635,20 +633,19 @@ public void testOverwriteWithCleanup(boolean v2) throws Exception { configPath + "/foo2/1", configPath + "/foo2/2"); for (String f : extraFiles) { - zkClient.makePath(f, true); + zkClient.makePath(f); } assertEquals( 0, uploadConfigSet(configsetName, configsetSuffix, null, true, false, v2, false)); for (String f : extraFiles) { assertTrue( - "Expecting file " + f + " to exist in ConfigSet but it's gone", - zkClient.exists(f, true)); + "Expecting file " + f + " to exist in ConfigSet but it's gone", zkClient.exists(f)); } assertEquals(0, uploadConfigSet(configsetName, configsetSuffix, null, true, true, v2, false)); for (String f : extraFiles) { assertFalse( "Expecting file " + f + " to be deleted from ConfigSet but it wasn't", - zkClient.exists(f, true)); + zkClient.exists(f)); } assertConfigsetFiles(configsetName, configsetSuffix, zkClient); } @@ -680,7 +677,7 @@ public void testOverwriteWithForbiddenFiles(boolean v2) throws Exception { String f = configPath + "/test." + fileEnding; assertFalse( "Expecting file " + f + " to not exist, because it has a forbidden file type", - zkClient.exists(f, true)); + zkClient.exists(f)); } } } @@ -989,8 +986,7 @@ public void testSingleWithCleanup(boolean v2) throws Exception { assertFalse( "New file should not exist, since the trust check did not succeed.", zkClient.exists( - "/configs/" + configsetName + configsetSuffix + "/test/upload/path/solrconfig.xml", - true)); + "/configs/" + configsetName + configsetSuffix + "/test/upload/path/solrconfig.xml")); assertConfigsetFiles(configsetName, configsetSuffix, zkClient); unIgnoreException("ConfigSet uploads do not allow cleanup=true when filePath is used."); } @@ -1051,8 +1047,10 @@ public void testSingleFileTrusted(boolean v2) throws Exception { assertFalse( "New file should not exist, since the trust check did not succeed.", zkClient.exists( - "/configs/" + configsetName + configsetSuffix + "/test/different/path/solrconfig.xml", - true)); + "/configs/" + + configsetName + + configsetSuffix + + "/test/different/path/solrconfig.xml")); assertTrue(isTrusted(zkClient, configsetName, configsetSuffix)); assertConfigsetFiles(configsetName, configsetSuffix, zkClient); unIgnoreException("Trying to make an unstrusted ConfigSet update on a trusted configSet"); @@ -1125,8 +1123,7 @@ public void testSingleFileForbiddenType(boolean v2) throws Exception { + configsetName + configsetSuffix + "/test/different/path/solrconfig." - + fileType, - true)); + + fileType)); unIgnoreException("is forbidden for use in configSets"); } } @@ -1309,8 +1306,7 @@ public void testSingleFileNewConfig(boolean v2) throws Exception { List children = zkClient.getChildren( String.format(Locale.ROOT, "/configs/%s%s", configsetName, configsetSuffixTrusted), - null, - true); + null); assertEquals("The configSet should only have one file uploaded.", 1, children.size()); assertEquals("Incorrect file uploaded.", "solrconfig.xml", children.get(0)); @@ -1335,8 +1331,7 @@ public void testSingleFileNewConfig(boolean v2) throws Exception { children = zkClient.getChildren( String.format(Locale.ROOT, "/configs/%s%s", configsetName, configsetSuffixUntrusted), - null, - true); + null); assertEquals("The configSet should only have one file uploaded.", 1, children.size()); assertEquals("Incorrect file uploaded.", "solrconfig.xml", children.get(0)); } @@ -1346,7 +1341,7 @@ private boolean isTrusted(SolrZkClient zkClient, String configsetName, String co throws KeeperException, InterruptedException { String configSetZkPath = String.format(Locale.ROOT, "/configs/%s%s", configsetName, configsetSuffix); - byte[] configSetNodeContent = zkClient.getData(configSetZkPath, null, null, true); + byte[] configSetNodeContent = zkClient.getData(configSetZkPath, null, null); ; @SuppressWarnings("unchecked") @@ -1361,8 +1356,7 @@ private int getConfigZNodeVersion( zkClient.getData( String.format(Locale.ROOT, "/configs/%s%s/%s", configsetName, configsetSuffix, configFile), null, - stat, - true); + stat); return stat.getVersion(); } @@ -1488,22 +1482,20 @@ private void assertConfigsetFiles(String configSetName, String suffix, SolrZkCli throws KeeperException, InterruptedException, IOException { assertTrue( "managed-schema.xml file should have been uploaded", - zkClient.exists("/configs/" + configSetName + suffix + "/managed-schema.xml", true)); + zkClient.exists("/configs/" + configSetName + suffix + "/managed-schema.xml")); assertArrayEquals( "managed-schema.xml file contents on zookeeper are not exactly same as that of the file uploaded in config", - zkClient.getData( - "/configs/" + configSetName + suffix + "/managed-schema.xml", null, null, true), + zkClient.getData("/configs/" + configSetName + suffix + "/managed-schema.xml", null, null), readFile("solr/configsets/upload/" + configSetName + "/managed-schema.xml")); assertTrue( "solrconfig.xml file should have been uploaded", - zkClient.exists("/configs/" + configSetName + suffix + "/solrconfig.xml", true)); - byte data[] = zkClient.getData("/configs/" + configSetName + suffix, null, null, true); + zkClient.exists("/configs/" + configSetName + suffix + "/solrconfig.xml")); + byte data[] = zkClient.getData("/configs/" + configSetName + suffix, null, null); // assertEquals("{\"trusted\": false}", new String(data, StandardCharsets.UTF_8)); assertArrayEquals( "solrconfig.xml file contents on zookeeper are not exactly same as that of the file uploaded in config", - zkClient.getData( - "/configs/" + configSetName + suffix + "/solrconfig.xml", null, null, true), + zkClient.getData("/configs/" + configSetName + suffix + "/solrconfig.xml", null, null), readFile("solr/configsets/upload/" + configSetName + "/solrconfig.xml")); } diff --git a/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPIExclusivity.java b/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPIExclusivity.java index 2920e4ece52..4c30011b7be 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPIExclusivity.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPIExclusivity.java @@ -96,8 +96,7 @@ private void setupBaseConfigSet(String baseConfigSetName) throws Exception { .getZkClient() .setData( "/configs/" + baseConfigSetName, - "{\"trusted\": false}".getBytes(StandardCharsets.UTF_8), - true); + "{\"trusted\": false}".getBytes(StandardCharsets.UTF_8)); } private Exception getFirstExceptionOrNull(List list) { diff --git a/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPIZkFailure.java b/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPIZkFailure.java index 2ba85cfa437..94b7b3585d0 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPIZkFailure.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestConfigSetsAPIZkFailure.java @@ -156,8 +156,7 @@ private void setupBaseConfigSet(String baseConfigSetName, Map ol .getZkClient() .setData( "/configs/" + baseConfigSetName, - "{\"trusted\": false}".getBytes(StandardCharsets.UTF_8), - true); + "{\"trusted\": false}".getBytes(StandardCharsets.UTF_8)); } private StringBuilder getConfigSetProps(Map map) { diff --git a/solr/core/src/test/org/apache/solr/cloud/TestDistributedMap.java b/solr/core/src/test/org/apache/solr/cloud/TestDistributedMap.java index aa5915f007b..7a5c12a1278 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestDistributedMap.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestDistributedMap.java @@ -64,9 +64,9 @@ public void testPut() throws KeeperException, InterruptedException { .build()) { String path = getAndMakeInitialPath(zkClient); DistributedMap map = createMap(zkClient, path); - assertFalse(zkClient.exists(path + "/" + DistributedMap.PREFIX + "foo", true)); + assertFalse(zkClient.exists(path + "/" + DistributedMap.PREFIX + "foo")); map.put("foo", new byte[0]); - assertTrue(zkClient.exists(path + "/" + DistributedMap.PREFIX + "foo", true)); + assertTrue(zkClient.exists(path + "/" + DistributedMap.PREFIX + "foo")); } } @@ -79,12 +79,7 @@ public void testGet() throws KeeperException, InterruptedException { String path = getAndMakeInitialPath(zkClient); byte[] data = "data".getBytes(Charset.defaultCharset()); zkClient.makePath( - path + "/" + DistributedMap.PREFIX + "foo", - data, - CreateMode.PERSISTENT, - null, - false, - true); + path + "/" + DistributedMap.PREFIX + "foo", data, CreateMode.PERSISTENT, null, false); DistributedMap map = createMap(zkClient, path); assertArrayEquals(data, map.get("foo")); } @@ -104,8 +99,7 @@ public void testContains() throws KeeperException, InterruptedException { new byte[0], CreateMode.PERSISTENT, null, - false, - true); + false); assertTrue(map.contains("foo")); } } @@ -124,11 +118,10 @@ public void testRemove() throws KeeperException, InterruptedException { new byte[0], CreateMode.PERSISTENT, null, - false, - true); + false); assertTrue(map.remove("foo")); assertFalse(map.contains("foo")); - assertFalse(zkClient.exists(path + "/" + DistributedMap.PREFIX + "foo", true)); + assertFalse(zkClient.exists(path + "/" + DistributedMap.PREFIX + "foo")); } } @@ -240,7 +233,7 @@ public void testRemoveMalformed() throws InterruptedException, KeeperException { String path = getAndMakeInitialPath(zkClient); // Add a "legacy" / malformed key final var key = "slash/test/0"; - zkClient.makePath(path + "/" + DistributedMap.PREFIX + key, new byte[0], true); + zkClient.makePath(path + "/" + DistributedMap.PREFIX + key, new byte[0]); DistributedMap map = createMap(zkClient, path); assertEquals(1, map.size()); @@ -256,7 +249,7 @@ protected DistributedMap createMap(SolrZkClient zkClient, String path) { protected String getAndMakeInitialPath(SolrZkClient zkClient) throws KeeperException, InterruptedException { String path = String.format(Locale.ROOT, "/%s/%s", getClass().getName(), getSaferTestName()); - zkClient.makePath(path, false, true); + zkClient.makePath(path, false); return path; } } diff --git a/solr/core/src/test/org/apache/solr/cloud/TestLazySolrCluster.java b/solr/core/src/test/org/apache/solr/cloud/TestLazySolrCluster.java index 7d7f7024953..9fa4f473d07 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestLazySolrCluster.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestLazySolrCluster.java @@ -71,14 +71,11 @@ public void test() throws Exception { assertEquals(5, solrCluster.nodes().size()); SolrZkClient zkClient = ZkStateReader.from(cloudClient).getZkClient(); - zkClient.create(ZkStateReader.CONFIGS_ZKNODE + "/conf1/a", null, CreateMode.PERSISTENT, true); + zkClient.create(ZkStateReader.CONFIGS_ZKNODE + "/conf1/a", null, CreateMode.PERSISTENT); zkClient.create( - ZkStateReader.CONFIGS_ZKNODE + "/conf1/a/aa1", new byte[1024], CreateMode.PERSISTENT, true); + ZkStateReader.CONFIGS_ZKNODE + "/conf1/a/aa1", new byte[1024], CreateMode.PERSISTENT); zkClient.create( - ZkStateReader.CONFIGS_ZKNODE + "/conf1/a/aa2", - new byte[1024 * 2], - CreateMode.PERSISTENT, - true); + ZkStateReader.CONFIGS_ZKNODE + "/conf1/a/aa2", new byte[1024 * 2], CreateMode.PERSISTENT); List allFiles = new ArrayList<>(); byte[] buf = new byte[3 * 1024]; diff --git a/solr/core/src/test/org/apache/solr/cloud/TestLeaderElectionZkExpiry.java b/solr/core/src/test/org/apache/solr/cloud/TestLeaderElectionZkExpiry.java index 28b05444ca2..c0409d6475d 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestLeaderElectionZkExpiry.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestLeaderElectionZkExpiry.java @@ -69,7 +69,8 @@ public void testLeaderElectionWithZkExpiry() throws Exception { () -> { TimeOut timeout = new TimeOut(10, TimeUnit.SECONDS, TimeSource.NANO_TIME); while (!timeout.hasTimedOut()) { - server.expire(zkController.getZkClient().getZooKeeper().getSessionId()); + long sessionId = zkController.getZkClient().getZkSessionId(); + server.expire(sessionId); try { timeout.sleep(10); } catch (InterruptedException e) { diff --git a/solr/core/src/test/org/apache/solr/cloud/TestPullReplica.java b/solr/core/src/test/org/apache/solr/cloud/TestPullReplica.java index a5b0ee21781..96ef9151720 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestPullReplica.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestPullReplica.java @@ -192,9 +192,7 @@ public void testCreateDelete() throws Exception { cluster .getZkClient() .getChildren( - ZkStateReader.getShardLeadersElectPath(collectionName, s.getName()), - null, - true); + ZkStateReader.getShardLeadersElectPath(collectionName, s.getName()), null); assertEquals( "Unexpected election nodes for Shard: " + s.getName() diff --git a/solr/core/src/test/org/apache/solr/cloud/TestQueryingOnDownCollection.java b/solr/core/src/test/org/apache/solr/cloud/TestQueryingOnDownCollection.java index 78f165613f2..9fe42b53af0 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestQueryingOnDownCollection.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestQueryingOnDownCollection.java @@ -123,7 +123,7 @@ private void downAllReplicas() throws Exception { byte[] collectionState = cluster .getZkClient() - .getData("/collections/" + COLLECTION_NAME + "/state.json", null, null, true); + .getData("/collections/" + COLLECTION_NAME + "/state.json", null, null); Map> infectedState = (Map>) Utils.fromJSON(collectionState); @@ -139,8 +139,7 @@ private void downAllReplicas() throws Exception { cluster .getZkClient() - .setData( - "/collections/" + COLLECTION_NAME + "/state.json", Utils.toJSON(infectedState), true); + .setData("/collections/" + COLLECTION_NAME + "/state.json", Utils.toJSON(infectedState)); } protected static final String STD_CONF = diff --git a/solr/core/src/test/org/apache/solr/cloud/TestRebalanceLeaders.java b/solr/core/src/test/org/apache/solr/cloud/TestRebalanceLeaders.java index bf870ad0eb2..e891e567136 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestRebalanceLeaders.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestRebalanceLeaders.java @@ -275,8 +275,7 @@ private void checkOneQueue(DocCollection coll, Slice slice, Set liveRep + "/leader_elect/" + slice.getName() + "/election", - null, - true); + null); if (leaderQueue.size() != liveReplicas.size()) { diff --git a/solr/core/src/test/org/apache/solr/cloud/TestSizeLimitedDistributedMap.java b/solr/core/src/test/org/apache/solr/cloud/TestSizeLimitedDistributedMap.java index a534e2e2a30..385c39c26d2 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestSizeLimitedDistributedMap.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestSizeLimitedDistributedMap.java @@ -149,7 +149,7 @@ public void testCleanupForKeysWithSlashes() throws InterruptedException, KeeperE String path = getAndMakeInitialPath(zkClient); // Add a "legacy" / malformed key - zkClient.makePath(path + "/" + DistributedMap.PREFIX + "slash/test/0", new byte[0], true); + zkClient.makePath(path + "/" + DistributedMap.PREFIX + "slash/test/0", new byte[0]); AtomicInteger overFlowCounter = new AtomicInteger(); DistributedMap map = diff --git a/solr/core/src/test/org/apache/solr/cloud/TestStressLiveNodes.java b/solr/core/src/test/org/apache/solr/cloud/TestStressLiveNodes.java index eb3bf597e4b..3865d665e20 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestStressLiveNodes.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestStressLiveNodes.java @@ -93,7 +93,7 @@ private static List getTrueLiveNodesFromZk() throws Exception { SolrZkClient client = newSolrZkClient(); try { ArrayList result = - new ArrayList<>(client.getChildren(ZkStateReader.LIVE_NODES_ZKNODE, null, true)); + new ArrayList<>(client.getChildren(ZkStateReader.LIVE_NODES_ZKNODE, null)); Collections.sort(result); return result; } finally { @@ -254,7 +254,7 @@ public Integer call() { for (int i = 0; running && i < numNodesToAdd; i++) { final String nodePath = ZkStateReader.LIVE_NODES_ZKNODE + "/thrasher-" + id + "-" + i; try { - client.makePath(nodePath, CreateMode.EPHEMERAL, true); + client.makePath(nodePath, CreateMode.EPHEMERAL); numAdded++; } catch (Exception e) { log.error("failed to create: {}", nodePath, e); diff --git a/solr/core/src/test/org/apache/solr/cloud/TestTlogReplica.java b/solr/core/src/test/org/apache/solr/cloud/TestTlogReplica.java index 937b8f1fe17..d2b772b44f7 100644 --- a/solr/core/src/test/org/apache/solr/cloud/TestTlogReplica.java +++ b/solr/core/src/test/org/apache/solr/cloud/TestTlogReplica.java @@ -222,9 +222,7 @@ public void testCreateDelete() throws Exception { cluster .getZkClient() .getChildren( - ZkStateReader.getShardLeadersElectPath(collectionName, s.getName()), - null, - true); + ZkStateReader.getShardLeadersElectPath(collectionName, s.getName()), null); assertEquals( "Unexpected election nodes for Shard: " + s.getName() diff --git a/solr/core/src/test/org/apache/solr/cloud/ZkCLITest.java b/solr/core/src/test/org/apache/solr/cloud/ZkCLITest.java index c84d180a6b9..95ca8d13ac0 100644 --- a/solr/core/src/test/org/apache/solr/cloud/ZkCLITest.java +++ b/solr/core/src/test/org/apache/solr/cloud/ZkCLITest.java @@ -99,7 +99,7 @@ public void setUp() throws Exception { .withUrl(zkServer.getZkHost()) .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build(); - zkClient.makePath("/solr", false, true); + zkClient.makePath("/solr", false); zkClient.close(); this.zkClient = @@ -124,7 +124,7 @@ public void testCmdConstants() { @Test public void testBootstrapWithChroot() throws Exception { String chroot = "/foo/bar"; - assertFalse(zkClient.exists(chroot, true)); + assertFalse(zkClient.exists(chroot)); String[] args = new String[] { @@ -138,7 +138,7 @@ public void testBootstrapWithChroot() throws Exception { ZkCLI.main(args); - assertTrue(zkClient.exists(chroot + ZkConfigSetService.CONFIGS_ZKNODE + "/collection1", true)); + assertTrue(zkClient.exists(chroot + ZkConfigSetService.CONFIGS_ZKNODE + "/collection1")); } @Test @@ -148,7 +148,7 @@ public void testMakePath() throws Exception { new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "makepath", "/path/mynewpath"}; ZkCLI.main(args); - assertTrue(zkClient.exists("/path/mynewpath", true)); + assertTrue(zkClient.exists("/path/mynewpath")); } @Test @@ -159,17 +159,17 @@ public void testPut() throws Exception { new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "put", "/data.txt", data}; ZkCLI.main(args); - zkClient.getData("/data.txt", null, null, true); + zkClient.getData("/data.txt", null, null); assertArrayEquals( - zkClient.getData("/data.txt", null, null, true), data.getBytes(StandardCharsets.UTF_8)); + zkClient.getData("/data.txt", null, null), data.getBytes(StandardCharsets.UTF_8)); // test re-put to existing data = "my data deux"; args = new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "put", "/data.txt", data}; ZkCLI.main(args); assertArrayEquals( - zkClient.getData("/data.txt", null, null, true), data.getBytes(StandardCharsets.UTF_8)); + zkClient.getData("/data.txt", null, null), data.getBytes(StandardCharsets.UTF_8)); } @Test @@ -188,7 +188,7 @@ public void testPutCompressed() throws Exception { String[] args = new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "put", "/state.json", data}; ZkCLI.main(args); - assertArrayEquals(zkClient.getZooKeeper().getData("/state.json", null, null), expected); + assertArrayEquals(zkClient.getCuratorFramework().getData().forPath("/state.json"), expected); // test re-put to existing data = "my data deux"; @@ -199,7 +199,7 @@ public void testPutCompressed() throws Exception { : zLibCompressor.compressBytes(dataBytes, dataBytes.length / 10); args = new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "put", "/state.json", data}; ZkCLI.main(args); - assertArrayEquals(zkClient.getZooKeeper().getData("/state.json", null, null), expected); + assertArrayEquals(zkClient.getCuratorFramework().getData().forPath("/state.json"), expected); } @Test @@ -216,8 +216,7 @@ public void testPutFile() throws Exception { }; ZkCLI.main(args); - String fromZk = - new String(zkClient.getData("/solr.xml", null, null, true), StandardCharsets.UTF_8); + String fromZk = new String(zkClient.getData("/solr.xml", null, null), StandardCharsets.UTF_8); Path locFile = Path.of(SOLR_HOME, "solr-stress-new.xml"); String fromLoc = Files.readString(locFile); assertEquals("Should get back what we put in ZK", fromZk, fromLoc); @@ -240,7 +239,7 @@ public void testPutFileCompressed() throws Exception { }; ZkCLI.main(args); - byte[] fromZk = zkClient.getZooKeeper().getData("/state.json", null, null); + byte[] fromZk = zkClient.getCuratorFramework().getData().forPath("/state.json"); Path locFile = Path.of(SOLR_HOME, "solr-stress-new.xml"); byte[] fromLoc = new ZLibCompressor().compressBytes(Files.readAllBytes(locFile)); assertArrayEquals("Should get back what we put in ZK", fromLoc, fromZk); @@ -266,7 +265,7 @@ public void testPutFileNotExists() { @Test public void testList() throws Exception { - zkClient.makePath("/test", true); + zkClient.makePath("/test"); String[] args = new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "list"}; ByteArrayOutputStream byteStream = new ByteArrayOutputStream(); @@ -282,7 +281,7 @@ public void testList() throws Exception { @Test public void testLs() throws Exception { - zkClient.makePath("/test/path", true); + zkClient.makePath("/test/path"); String[] args = new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "ls", "/test"}; ByteArrayOutputStream byteStream = new ByteArrayOutputStream(); @@ -335,7 +334,7 @@ public void testUpConfigLinkConfigClearZk() throws Exception { } ZkCLI.main(upconfigArgs); - assertTrue(zkClient.exists(ZkConfigSetService.CONFIGS_ZKNODE + "/" + confsetname, true)); + assertTrue(zkClient.exists(ZkConfigSetService.CONFIGS_ZKNODE + "/" + confsetname)); // print help // ZkCLI.main(new String[0]); @@ -356,7 +355,7 @@ public void testUpConfigLinkConfigClearZk() throws Exception { ZkNodeProps collectionProps = ZkNodeProps.load( - zkClient.getData(ZkStateReader.COLLECTIONS_ZKNODE + "/collection1", null, null, true)); + zkClient.getData(ZkStateReader.COLLECTIONS_ZKNODE + "/collection1", null, null)); assertTrue(collectionProps.containsKey("configName")); assertEquals(confsetname, collectionProps.getStr("configName")); @@ -381,7 +380,7 @@ public void testUpConfigLinkConfigClearZk() throws Exception { File[] files = confDir.listFiles(); List zkFiles = - zkClient.getChildren(ZkConfigSetService.CONFIGS_ZKNODE + "/" + confsetname, null, true); + zkClient.getChildren(ZkConfigSetService.CONFIGS_ZKNODE + "/" + confsetname, null); assertEquals(files.length, zkFiles.size()); File sourceConfDir = new File(ExternalPaths.TECHPRODUCTS_CONFIGSET); @@ -421,7 +420,7 @@ public void testUpConfigLinkConfigClearZk() throws Exception { args = new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "clear", "/"}; ZkCLI.main(args); - assertEquals(0, zkClient.getChildren("/", null, true).size()); + assertEquals(0, zkClient.getChildren("/", null).size()); } @Test @@ -429,7 +428,7 @@ public void testGet() throws Exception { String getNode = "/getNode"; byte[] data = "getNode-data".getBytes(StandardCharsets.UTF_8); ByteArrayOutputStream systemOut = new ByteArrayOutputStream(); - this.zkClient.create(getNode, data, CreateMode.PERSISTENT, true); + this.zkClient.create(getNode, data, CreateMode.PERSISTENT); String[] args = new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "get", getNode}; ZkCLI.setStdout(new PrintStream(systemOut, true, StandardCharsets.UTF_8)); ZkCLI.main(args); @@ -454,7 +453,7 @@ public void testGetCompressed() throws Exception { random().nextBoolean() ? zLibCompressor.compressBytes(data) : zLibCompressor.compressBytes(data, data.length / 10); - this.zkClient.create(getNode, compressedData, CreateMode.PERSISTENT, true); + this.zkClient.create(getNode, compressedData, CreateMode.PERSISTENT); String[] args = new String[] {"-zkhost", zkServer.getZkAddress(), "-cmd", "get", getNode}; ZkCLI.setStdout(new PrintStream(systemOut, true, StandardCharsets.UTF_8)); ZkCLI.main(args); @@ -472,7 +471,7 @@ public void testGetFile() throws Exception { String getNode = "/getFileNode"; byte[] data = "getFileNode-data".getBytes(StandardCharsets.UTF_8); - this.zkClient.create(getNode, data, CreateMode.PERSISTENT, true); + this.zkClient.create(getNode, data, CreateMode.PERSISTENT); Path file = tmpDir.resolve("solrtest-getfile-" + this.getClass().getName() + "-" + System.nanoTime()); @@ -501,7 +500,7 @@ public void testGetFileCompressed() throws Exception { random().nextBoolean() ? zLibCompressor.compressBytes(data) : zLibCompressor.compressBytes(data, data.length / 10); - this.zkClient.create(getNode, compressedData, CreateMode.PERSISTENT, true); + this.zkClient.create(getNode, compressedData, CreateMode.PERSISTENT); Path file = tmpDir.resolve("solrtest-getfile-" + this.getClass().getName() + "-" + System.nanoTime()); @@ -602,7 +601,7 @@ public void testUpdateAcls() throws Exception { .withTimeout( AbstractDistribZkTestBase.DEFAULT_CONNECTION_TIMEOUT, TimeUnit.MILLISECONDS) .build()) { - zkClient.getData("/", null, null, true); + zkClient.getData("/", null, null); } catch (KeeperException.NoAuthException e) { excepted = true; } diff --git a/solr/core/src/test/org/apache/solr/cloud/ZkControllerTest.java b/solr/core/src/test/org/apache/solr/cloud/ZkControllerTest.java index f1df3febab4..a83e5c31b1d 100644 --- a/solr/core/src/test/org/apache/solr/cloud/ZkControllerTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/ZkControllerTest.java @@ -233,8 +233,7 @@ public List getCoreDescriptors() { .makePath( DocCollection.getCollectionPathRoot(collectionName), new byte[0], - CreateMode.PERSISTENT, - true); + CreateMode.PERSISTENT); ZkNodeProps m = new ZkNodeProps( @@ -340,30 +339,29 @@ public void testTouchConfDir() throws Exception { // touchConfDir doesn't make the znode Stat s = new Stat(); - assertFalse(zkClient.exists(zkpath, true)); + assertFalse(zkClient.exists(zkpath)); zkClient.makePath(zkpath, true); - assertTrue(zkClient.exists(zkpath, true)); - assertNull(zkClient.getData(zkpath, null, s, true)); + assertTrue(zkClient.exists(zkpath)); + assertNull(zkClient.getData(zkpath, null, s)); assertEquals(0, s.getVersion()); // touchConfDir should only set the data to new byte[] {0} ZkController.touchConfDir(loader); - assertTrue(zkClient.exists(zkpath, true)); - assertArrayEquals( - ZkController.TOUCHED_ZNODE_DATA, zkClient.getData(zkpath, null, s, true)); + assertTrue(zkClient.exists(zkpath)); + assertArrayEquals(ZkController.TOUCHED_ZNODE_DATA, zkClient.getData(zkpath, null, s)); assertEquals(1, s.getVersion()); // set new data to check if touchConfDir overwrites later byte[] data = "{\"key\", \"new data\"".getBytes(StandardCharsets.UTF_8); - s = zkClient.setData(zkpath, data, true); + s = zkClient.setData(zkpath, data); assertEquals(2, s.getVersion()); // make sure touchConfDir doesn't overwrite existing data. // touchConfDir should update version. - assertTrue(zkClient.exists(zkpath, true)); + assertTrue(zkClient.exists(zkpath)); ZkController.touchConfDir(loader); - assertTrue(zkClient.exists(zkpath, true)); - assertArrayEquals(data, zkClient.getData(zkpath, null, s, true)); + assertTrue(zkClient.exists(zkpath)); + assertArrayEquals(data, zkClient.getData(zkpath, null, s)); assertEquals(3, s.getVersion()); } } @@ -390,10 +388,7 @@ public void testCheckNoOldClusterstate() throws Exception { server .getZkClient() .create( - "/clusterstate.json", - "{}".getBytes(StandardCharsets.UTF_8), - CreateMode.PERSISTENT, - true); + "/clusterstate.json", "{}".getBytes(StandardCharsets.UTF_8), CreateMode.PERSISTENT); AtomicInteger idx = new AtomicInteger(); CountDownLatch latch = new CountDownLatch(nThreads); CountDownLatch done = new CountDownLatch(nThreads); @@ -420,7 +415,7 @@ public void testCheckNoOldClusterstate() throws Exception { }); } done.await(); - assertFalse(server.getZkClient().exists("/clusterstate.json", true)); + assertFalse(server.getZkClient().exists("/clusterstate.json")); assertNull(exception.get()); } finally { ExecutorUtil.shutdownNowAndAwaitTermination(svc); diff --git a/solr/core/src/test/org/apache/solr/cloud/ZkSolrClientTest.java b/solr/core/src/test/org/apache/solr/cloud/ZkSolrClientTest.java index 4503c862d50..bf2f1389a30 100644 --- a/solr/core/src/test/org/apache/solr/cloud/ZkSolrClientTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/ZkSolrClientTest.java @@ -20,20 +20,16 @@ import java.io.IOException; import java.nio.file.Path; -import java.util.Arrays; import java.util.HashSet; -import java.util.List; import java.util.Set; import java.util.concurrent.CountDownLatch; import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicInteger; import org.apache.solr.SolrTestCaseJ4; import org.apache.solr.common.cloud.SolrZkClient; -import org.apache.solr.common.cloud.ZkCmdExecutor; import org.apache.solr.common.cloud.ZkMaintenanceUtils; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.Op; import org.apache.zookeeper.WatchedEvent; import org.apache.zookeeper.Watcher; import org.apache.zookeeper.data.Stat; @@ -51,8 +47,8 @@ public static void beforeClass() throws Exception { @SuppressWarnings({"try"}) static class ZkConnection implements AutoCloseable { - private ZkTestServer server = null; - private SolrZkClient zkClient = null; + private final ZkTestServer server; + private final SolrZkClient zkClient; ZkConnection() throws Exception { Path zkDir = createTempDir("zkData"); @@ -91,15 +87,12 @@ public void testConnect() throws Exception { @SuppressWarnings({"try"}) public void testMakeRootNode() throws Exception { try (ZkConnection conn = new ZkConnection()) { - final SolrZkClient zkClient = + try (SolrZkClient zkClient = new SolrZkClient.Builder() .withUrl(conn.getServer().getZkHost()) .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) - .build(); - try { - assertTrue(zkClient.exists("/solr", true)); - } finally { - zkClient.close(); + .build()) { + assertTrue(zkClient.exists("/solr")); } } } @@ -109,20 +102,20 @@ public void testClean() throws Exception { try (ZkConnection conn = new ZkConnection()) { final SolrZkClient zkClient = conn.getClient(); - zkClient.makePath("/test/path/here", true); + zkClient.makePath("/test/path/here"); - zkClient.makePath("/zz/path/here", true); + zkClient.makePath("/zz/path/here"); zkClient.clean("/"); - assertFalse(zkClient.exists("/test", true)); - assertFalse(zkClient.exists("/zz", true)); + assertFalse(zkClient.exists("/test")); + assertFalse(zkClient.exists("/zz")); } } public void testReconnect() throws Exception { Path zkDir = createTempDir("zkData"); - ZkTestServer server = null; + ZkTestServer server; server = new ZkTestServer(zkDir); server.run(); try (SolrZkClient zkClient = @@ -132,7 +125,7 @@ public void testReconnect() throws Exception { .build()) { String shardsPath = "/collections/collection1/shards"; - zkClient.makePath(shardsPath, false, true); + zkClient.makePath(shardsPath, false); int zkServerPort = server.getPort(); // this tests disconnect state @@ -145,7 +138,7 @@ public void testReconnect() throws Exception { @Override public void run() { try { - zkClient.makePath("collections/collection2", false); + zkClient.makePath("collections/collection2"); // Assert.fail("Server should be down here"); } catch (KeeperException | InterruptedException e) { @@ -169,7 +162,7 @@ public void run() { public void run() { try { - zkClient.makePath("collections/collection3", true); + zkClient.makePath("collections/collection3"); } catch (KeeperException e) { throw new RuntimeException(e); @@ -185,13 +178,14 @@ public void run() { thread2.join(); - assertNotNull(zkClient.exists("/collections/collection3", null, true)); - assertNotNull(zkClient.exists("/collections/collection1", null, true)); + assertNotNull(zkClient.exists("/collections/collection3", null)); + assertNotNull(zkClient.exists("/collections/collection1", null)); // simulate session expiration // one option - server.expire(zkClient.getZooKeeper().getSessionId()); + long sessionId = zkClient.getZkSessionId(); + server.expire(sessionId); // another option // zkClient.getSolrZooKeeper().getConnection().disconnect(); @@ -202,7 +196,7 @@ public void run() { for (int i = 0; i < 8; i++) { try { - zkClient.makePath("collections/collection4", true); + zkClient.makePath("collections/collection4"); break; } catch (KeeperException.SessionExpiredException | KeeperException.ConnectionLossException e) { @@ -212,8 +206,7 @@ public void run() { } assertNotNull( - "Node does not exist, but it should", - zkClient.exists("/collections/collection4", null, true)); + "Node does not exist, but it should", zkClient.exists("/collections/collection4", null)); } finally { @@ -223,43 +216,12 @@ public void run() { } } - public void testZkCmdExecutor() throws Exception { - Path zkDir = createTempDir("zkData"); - ZkTestServer server = null; - - try { - server = new ZkTestServer(zkDir); - server.run(); - - final int timeout = random().nextInt(10000) + 5000; - - ZkCmdExecutor zkCmdExecutor = new ZkCmdExecutor(timeout); - final long start = System.nanoTime(); - expectThrows( - KeeperException.SessionExpiredException.class, - () -> { - zkCmdExecutor.retryOperation( - () -> { - if (System.nanoTime() - start - > TimeUnit.NANOSECONDS.convert(timeout, TimeUnit.MILLISECONDS)) { - throw new KeeperException.SessionExpiredException(); - } - throw new KeeperException.ConnectionLossException(); - }); - }); - } finally { - if (server != null) { - server.shutdown(); - } - } - } - @Test @SuppressWarnings({"try"}) public void testMultipleWatchesAsync() throws Exception { try (ZkConnection conn = new ZkConnection()) { final SolrZkClient zkClient = conn.getClient(); - zkClient.makePath("/collections", true); + zkClient.makePath("/collections"); final int numColls = random().nextInt(100); final CountDownLatch latch = new CountDownLatch(numColls); @@ -269,7 +231,7 @@ public void testMultipleWatchesAsync() throws Exception { for (int i = 1; i <= numColls; i++) { String collPath = "/collections/collection" + i; - zkClient.makePath(collPath, true); + zkClient.makePath(collPath); zkClient.getChildren( collPath, new Watcher() { @@ -291,13 +253,12 @@ public void process(WatchedEvent event) { } watchesDone.countDown(); } - }, - true); + }); } for (int i = 1; i <= numColls; i++) { String shardsPath = "/collections/collection" + i + "/shards"; - zkClient.makePath(shardsPath, true); + zkClient.makePath(shardsPath); } assertTrue(latch.await(10000, TimeUnit.MILLISECONDS)); @@ -321,7 +282,7 @@ public void testWatchChildren() throws Exception { final AtomicInteger cnt = new AtomicInteger(); final CountDownLatch latch = new CountDownLatch(1); - zkClient.makePath("/collections", true); + zkClient.makePath("/collections"); zkClient.getChildren( "/collections", @@ -332,23 +293,22 @@ public void process(WatchedEvent event) { cnt.incrementAndGet(); // remake watch try { - zkClient.getChildren("/collections", this, true); + zkClient.getChildren("/collections", this); latch.countDown(); } catch (KeeperException | InterruptedException e) { throw new RuntimeException(e); } } - }, - true); + }); - zkClient.makePath("/collections/collection99/shards", true); + zkClient.makePath("/collections/collection99/shards"); latch.await(); // wait until watch has been re-created - zkClient.makePath("collections/collection99/config=collection1", true); + zkClient.makePath("collections/collection99/config=collection1"); - zkClient.makePath("collections/collection99/config=collection3", true); + zkClient.makePath("collections/collection99/config=collection3"); - zkClient.makePath("/collections/collection97/shards", true); + zkClient.makePath("/collections/collection97/shards"); // pause for the watches to fire Thread.sleep(700); @@ -373,8 +333,7 @@ public void testSkipPathPartsOnMakePath() throws Exception { zkClient.makePath("/test", true); // should work - zkClient.makePath( - "/test/path/here", (byte[]) null, CreateMode.PERSISTENT, (Watcher) null, true, true, 1); + zkClient.makePath("/test/path/here", null, CreateMode.PERSISTENT, null, true, 1); zkClient.clean("/"); @@ -384,14 +343,7 @@ public void testSkipPathPartsOnMakePath() throws Exception { KeeperException.NoNodeException.class, "We should not be able to create this path", () -> - zkClient.makePath( - "/test/path/here", - (byte[]) null, - CreateMode.PERSISTENT, - (Watcher) null, - true, - true, - 1)); + zkClient.makePath("/test/path/here", null, CreateMode.PERSISTENT, null, true, 1)); zkClient.clean("/"); @@ -424,14 +376,14 @@ public void testSkipPathPartsOnMakePath() throws Exception { ZkMaintenanceUtils.ensureExists( "/collection/collection", bytes, CreateMode.PERSISTENT, zkClient, 2); - byte[] returnedBytes = zkClient.getData("/collection/collection", null, null, true); + byte[] returnedBytes = zkClient.getData("/collection/collection", null, null); assertNull("We skipped 2 path parts, so data won't be written", returnedBytes); zkClient.makePath("/collection/collection/leader", true); ZkMaintenanceUtils.ensureExists( - "/collection/collection/leader", (byte[]) null, CreateMode.PERSISTENT, zkClient, 2); + "/collection/collection/leader", null, CreateMode.PERSISTENT, zkClient, 2); } } @@ -440,20 +392,14 @@ public void testZkBehavior() throws Exception { configureCluster(4).withJettyConfig(jetty -> jetty.enableV2(true)).configure(); try { SolrZkClient zkClient = cluster.getZkClient(); - zkClient.create("/test-node", null, CreateMode.PERSISTENT, true); + zkClient.create("/test-node", null, CreateMode.PERSISTENT); - Stat stat = zkClient.exists("/test-node", null, true); + Stat stat = zkClient.exists("/test-node", null); int cversion = stat.getCversion(); - List ops = - Arrays.asList( - Op.create( - "/test-node/abc", - null, - zkClient.getZkACLProvider().getACLsToAdd("/test-node/abc"), - CreateMode.PERSISTENT), - Op.delete("/test-node/abc", -1)); - zkClient.multi(ops, true); - stat = zkClient.exists("/test-node", null, true); + zkClient.multi( + op -> op.create().withMode(CreateMode.PERSISTENT).forPath("/test-node/abc", null), + op -> op.delete().withVersion(-1).forPath("/test-node/abc")); + stat = zkClient.exists("/test-node", null); assertTrue(stat.getCversion() >= cversion + 2); } finally { cluster.shutdown(); diff --git a/solr/core/src/test/org/apache/solr/cloud/api/collections/ShardSplitTest.java b/solr/core/src/test/org/apache/solr/cloud/api/collections/ShardSplitTest.java index f252c23e901..22d3a51b2c1 100644 --- a/solr/core/src/test/org/apache/solr/cloud/api/collections/ShardSplitTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/api/collections/ShardSplitTest.java @@ -708,7 +708,7 @@ public void testSplitLocking() throws Exception { TimeOut timeOut = new TimeOut(30, TimeUnit.SECONDS, TimeSource.NANO_TIME); while (!timeOut.hasTimedOut()) { timeOut.sleep(500); - if (ZkStateReader.from(cloudClient).getZkClient().exists(path, true)) { + if (ZkStateReader.from(cloudClient).getZkClient().exists(path)) { log.info("=== found lock node"); break; } @@ -726,13 +726,13 @@ public void testSplitLocking() throws Exception { // make sure the lock still exists assertTrue( "lock znode expected but missing", - ZkStateReader.from(cloudClient).getZkClient().exists(path, true)); + ZkStateReader.from(cloudClient).getZkClient().exists(path)); // let the first split proceed TestInjection.splitLatch.countDown(); timeOut = new TimeOut(30, TimeUnit.SECONDS, TimeSource.NANO_TIME); while (!timeOut.hasTimedOut()) { timeOut.sleep(500); - if (!ZkStateReader.from(cloudClient).getZkClient().exists(path, true)) { + if (!ZkStateReader.from(cloudClient).getZkClient().exists(path)) { break; } } diff --git a/solr/core/src/test/org/apache/solr/cloud/api/collections/SimpleCollectionCreateDeleteTest.java b/solr/core/src/test/org/apache/solr/cloud/api/collections/SimpleCollectionCreateDeleteTest.java index 9d8c18f42d7..021b93a9812 100644 --- a/solr/core/src/test/org/apache/solr/cloud/api/collections/SimpleCollectionCreateDeleteTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/api/collections/SimpleCollectionCreateDeleteTest.java @@ -65,15 +65,13 @@ public void testCreateAndDeleteThenCreateAgain() throws Exception { NamedList request = create.process(cloudClient).getResponse(); if (request.get("success") != null) { - assertTrue( - getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName, false)); + assertTrue(getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName)); CollectionAdminRequest.Delete delete = CollectionAdminRequest.deleteCollection(collectionName); cloudClient.request(delete); - assertFalse( - getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName, false)); + assertFalse(getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName)); // currently, removing a collection does not wait for cores to be unloaded TimeOut timeout = new TimeOut(30, TimeUnit.SECONDS, TimeSource.NANO_TIME); @@ -119,7 +117,7 @@ public void testPropertiesOfReplica() throws Exception { NamedList request = create.process(cloudClient).getResponse(); assertNotNull(request.get("success")); SolrZkClient.NodeData node = - getZkClient().getNode(DocCollection.getCollectionPath(collectionName), null, true); + getZkClient().getNode(DocCollection.getCollectionPath(collectionName), null); DocCollection c = ClusterState.createFromCollectionMap( @@ -151,26 +149,25 @@ public void testDeleteAlsoDeletesAutocreatedConfigSet() throws Exception { assertTrue( ZkStateReader.from(cloudClient) .getZkClient() - .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName, false)); + .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName)); String configName = cloudClient.getClusterStateProvider().getCollection(collectionName).getConfigName(); // config for this collection is '.AUTOCREATED', and exists globally assertTrue(configName.endsWith(".AUTOCREATED")); - assertTrue(getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName, true)); + assertTrue(getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName)); CollectionAdminRequest.Delete delete = CollectionAdminRequest.deleteCollection(collectionName); cloudClient.request(delete); // collection has been deleted - assertFalse( - getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName, false)); + assertFalse(getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName)); // ... and so has its autocreated config set assertFalse( "The auto-created config set should have been deleted with its collection", - getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName, true)); + getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName)); } } @@ -186,8 +183,7 @@ public void testDeleteDoesNotDeleteSharedAutocreatedConfigSet() throws Exception if (requestInitial.get("success") != null) { // collection exists now assertTrue( - getZkClient() - .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionNameInitial, false)); + getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionNameInitial)); String configName = cloudClient @@ -197,7 +193,7 @@ public void testDeleteDoesNotDeleteSharedAutocreatedConfigSet() throws Exception // config for this collection is '.AUTOCREATED', and exists globally assertTrue(configName.endsWith(".AUTOCREATED")); - assertTrue(getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName, true)); + assertTrue(getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName)); // create a second collection, sharing the same configSet String collectionNameWithSharedConfig = @@ -213,8 +209,7 @@ public void testDeleteDoesNotDeleteSharedAutocreatedConfigSet() throws Exception assertTrue( "The new collection should exist after a successful creation", getZkClient() - .exists( - ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionNameWithSharedConfig, false)); + .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionNameWithSharedConfig)); String configNameOfSecondCollection = cloudClient @@ -235,12 +230,11 @@ public void testDeleteDoesNotDeleteSharedAutocreatedConfigSet() throws Exception // initial collection has been deleted assertFalse( - getZkClient() - .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionNameInitial, false)); + getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionNameInitial)); // ... but not its autocreated config set, since it is shared with another collection assertTrue( "The auto-created config set should NOT have been deleted. Another collection is using it.", - getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName, true)); + getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName)); // delete the second collection - the config set should now be deleted, since it is no longer // shared any other collection @@ -251,13 +245,12 @@ public void testDeleteDoesNotDeleteSharedAutocreatedConfigSet() throws Exception // the collection has been deleted assertFalse( getZkClient() - .exists( - ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionNameWithSharedConfig, false)); + .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionNameWithSharedConfig)); // ... and the config set is now also deleted - once it doesn't get referenced by any // collection assertFalse( "The auto-created config set should have been deleted now. No collection is referencing it.", - getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName, true)); + getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + configName)); } } diff --git a/solr/core/src/test/org/apache/solr/cloud/api/collections/TestCollectionAPI.java b/solr/core/src/test/org/apache/solr/cloud/api/collections/TestCollectionAPI.java index 29c103cb9a3..d37017abda8 100644 --- a/solr/core/src/test/org/apache/solr/cloud/api/collections/TestCollectionAPI.java +++ b/solr/core/src/test/org/apache/solr/cloud/api/collections/TestCollectionAPI.java @@ -265,11 +265,11 @@ private void testNoConfigset() throws Exception { private void deleteThemAll(SolrZkClient zkClient, String node) throws KeeperException, InterruptedException { - List kids = zkClient.getChildren(node, null, true); + List kids = zkClient.getChildren(node, null); for (String kid : kids) { deleteThemAll(zkClient, node + "/" + kid); } - zkClient.delete(node, -1, true); + zkClient.delete(node, -1); } private void assertCountsForRepFactorAndNrtReplicas(CloudSolrClient client, String collectionName) diff --git a/solr/core/src/test/org/apache/solr/cloud/api/collections/TestLocalFSCloudBackupRestore.java b/solr/core/src/test/org/apache/solr/cloud/api/collections/TestLocalFSCloudBackupRestore.java index caa2e5f4c74..04e1fff06e7 100644 --- a/solr/core/src/test/org/apache/solr/cloud/api/collections/TestLocalFSCloudBackupRestore.java +++ b/solr/core/src/test/org/apache/solr/cloud/api/collections/TestLocalFSCloudBackupRestore.java @@ -76,9 +76,7 @@ public static void setupClass() throws Exception { cluster .getZkClient() .delete( - ZkConfigSetService.CONFIGS_ZKNODE + "/" + "confFaulty" + "/" + "solrconfig.xml", - -1, - true); + ZkConfigSetService.CONFIGS_ZKNODE + "/" + "confFaulty" + "/" + "solrconfig.xml", -1); boolean whitespacesInPath = random().nextBoolean(); if (whitespacesInPath) { diff --git a/solr/core/src/test/org/apache/solr/cloud/overseer/ZkStateReaderTest.java b/solr/core/src/test/org/apache/solr/cloud/overseer/ZkStateReaderTest.java index 3e1ca33963c..bb5a5fc0524 100644 --- a/solr/core/src/test/org/apache/solr/cloud/overseer/ZkStateReaderTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/overseer/ZkStateReaderTest.java @@ -178,7 +178,7 @@ public void testCollectionStateWatcherCaching() throws Exception { ZkWriteCommand wc = new ZkWriteCommand("c1", state); writer.enqueueUpdate(reader.getClusterState(), Collections.singletonList(wc), null); writer.writePendingUpdates(); - assertTrue(fixture.zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", true)); + assertTrue(fixture.zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json")); reader.waitForState( "c1", 1, TimeUnit.SECONDS, (liveNodes, collectionState) -> collectionState != null); @@ -239,7 +239,7 @@ public void testWatchedCollectionCreation() throws Exception { writer.enqueueUpdate(reader.getClusterState(), Collections.singletonList(wc), null); writer.writePendingUpdates(); - assertTrue(fixture.zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", true)); + assertTrue(fixture.zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json")); // reader.forceUpdateCollection("c1"); reader.waitForState("c1", TIMEOUT, TimeUnit.SECONDS, (n, c) -> c != null); @@ -397,7 +397,7 @@ public void testForciblyRefreshAllClusterState() throws Exception { writer.enqueueUpdate(reader.getClusterState(), Collections.singletonList(wc), null); writer.writePendingUpdates(); - assertTrue(fixture.zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", true)); + assertTrue(fixture.zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json")); reader.forciblyRefreshAllClusterStateSlow(); ClusterState.CollectionRef ref = reader.getClusterState().getCollectionRef("c1"); @@ -480,7 +480,7 @@ public void testForciblyRefreshAllClusterStateCompressed() throws Exception { writer.enqueueUpdate(reader.getClusterState(), Collections.singletonList(wc), null); writer.writePendingUpdates(); - assertTrue(fixture.zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", true)); + assertTrue(fixture.zkClient.exists(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json")); reader.forciblyRefreshAllClusterStateSlow(); ClusterState.CollectionRef ref = reader.getClusterState().getCollectionRef("c1"); diff --git a/solr/core/src/test/org/apache/solr/cloud/overseer/ZkStateWriterTest.java b/solr/core/src/test/org/apache/solr/cloud/overseer/ZkStateWriterTest.java index 1a2c940e8dd..1ef1cb28a0c 100644 --- a/solr/core/src/test/org/apache/solr/cloud/overseer/ZkStateWriterTest.java +++ b/solr/core/src/test/org/apache/solr/cloud/overseer/ZkStateWriterTest.java @@ -88,9 +88,9 @@ public void testZkStateWriterBatching() throws Exception { try (ZkStateReader reader = new ZkStateReader(zkClient)) { reader.createClusterStateWatchersAndUpdate(); - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c1", true); - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c2", true); - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c3", true); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c1"); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c2"); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c3"); Map props = Collections.singletonMap( @@ -327,7 +327,7 @@ public void testSingleExternalCollection() throws Exception { ZkStateWriter writer = new ZkStateWriter(reader, new Stats(), -1, STATE_COMPRESSION_PROVIDER); - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c1", true); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c1"); // create new collection ZkWriteCommand c1 = @@ -348,7 +348,7 @@ public void testSingleExternalCollection() throws Exception { (Map) Utils.fromJSON( zkClient.getData( - ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", null, null, true)); + ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", null, null)); assertNotNull(map.get("c1")); } } finally { @@ -380,8 +380,8 @@ public void testExternalModification() throws Exception { ZkStateWriter writer = new ZkStateWriter(reader, new Stats(), -1, STATE_COMPRESSION_PROVIDER); - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c1", true); - zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c2", true); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c1"); + zkClient.makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/c2"); ClusterState state = reader.getClusterState(); @@ -402,8 +402,8 @@ public void testExternalModification() throws Exception { int c2Version = state.getCollection("c2").getZNodeVersion(); // Simulate an external modification to /collections/c2/state.json - byte[] data = zkClient.getData(DocCollection.getCollectionPath("c2"), null, null, true); - zkClient.setData(DocCollection.getCollectionPath("c2"), data, true); + byte[] data = zkClient.getData(DocCollection.getCollectionPath("c2"), null, null); + zkClient.setData(DocCollection.getCollectionPath("c2"), data); // get the most up-to-date state reader.forceUpdateCollection("c2"); @@ -500,9 +500,7 @@ public void testSingleExternalCollectionCompressedState() throws Exception { writer.writePendingUpdates(); byte[] data = - zkClient - .getZooKeeper() - .getData(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", null, null); + zkClient.getData(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", null, null); Map map = (Map) Utils.fromJSON(data); assertNotNull(map.get("c1")); } @@ -537,8 +535,9 @@ public void testSingleExternalCollectionCompressedState() throws Exception { byte[] data = zkClient - .getZooKeeper() - .getData(ZkStateReader.COLLECTIONS_ZKNODE + "/c2/state.json", null, null); + .getCuratorFramework() + .getData() + .forPath(ZkStateReader.COLLECTIONS_ZKNODE + "/c2/state.json"); assertTrue(compressor.isCompressedBytes(data)); Map map = (Map) Utils.fromJSON(compressor.decompressBytes(data)); assertNotNull(map.get("c2")); diff --git a/solr/core/src/test/org/apache/solr/handler/TestConfigReload.java b/solr/core/src/test/org/apache/solr/handler/TestConfigReload.java index 36ce1c08377..ab806d58829 100644 --- a/solr/core/src/test/org/apache/solr/handler/TestConfigReload.java +++ b/solr/core/src/test/org/apache/solr/handler/TestConfigReload.java @@ -77,15 +77,15 @@ private void checkConfReload(SolrZkClient client, String resPath, String name, S Stat stat = new Stat(); byte[] data = null; try { - data = client.getData(resPath, null, stat, true); + data = client.getData(resPath, null, stat); } catch (KeeperException.NoNodeException e) { data = "{}".getBytes(StandardCharsets.UTF_8); log.info("creating_node {}", resPath); - client.create(resPath, data, CreateMode.PERSISTENT, true); + client.create(resPath, data, CreateMode.PERSISTENT); } long startTime = System.nanoTime(); - Stat newStat = client.setData(resPath, data, true); - client.setData("/configs/conf1", new byte[] {1}, true); + Stat newStat = client.setData(resPath, data); + client.setData("/configs/conf1", new byte[] {1}); assertTrue(newStat.getVersion() > stat.getVersion()); if (log.isInfoEnabled()) { log.info("new_version {}", newStat.getVersion()); diff --git a/solr/core/src/test/org/apache/solr/handler/admin/ZookeeperReadAPITest.java b/solr/core/src/test/org/apache/solr/handler/admin/ZookeeperReadAPITest.java index 109e27d64d9..ee4cf40ed34 100644 --- a/solr/core/src/test/org/apache/solr/handler/admin/ZookeeperReadAPITest.java +++ b/solr/core/src/test/org/apache/solr/handler/admin/ZookeeperReadAPITest.java @@ -86,9 +86,7 @@ public void testZkread() throws Exception { bytes[i] = (byte) random().nextInt(128); } try { - cluster - .getZkClient() - .create("/configs/_default/testdata", bytes, CreateMode.PERSISTENT, true); + cluster.getZkClient().create("/configs/_default/testdata", bytes, CreateMode.PERSISTENT); Utils.executeGET( client.getHttpClient(), basezk + "/configs/_default/testdata", @@ -101,7 +99,7 @@ public void testZkread() throws Exception { return null; }); } finally { - cluster.getZkClient().delete("/configs/_default/testdata", -1, true); + cluster.getZkClient().delete("/configs/_default/testdata", -1); } } } diff --git a/solr/core/src/test/org/apache/solr/handler/designer/TestSchemaDesignerAPI.java b/solr/core/src/test/org/apache/solr/handler/designer/TestSchemaDesignerAPI.java index 57d5a6b47a8..42b25847d15 100644 --- a/solr/core/src/test/org/apache/solr/handler/designer/TestSchemaDesignerAPI.java +++ b/solr/core/src/test/org/apache/solr/handler/designer/TestSchemaDesignerAPI.java @@ -126,7 +126,7 @@ public void testTSV() throws Exception { String mutableId = getMutableId(configSet); assertFalse(cc.getZkController().getClusterState().hasCollection(mutableId)); SolrZkClient zkClient = cc.getZkController().getZkClient(); - assertFalse(zkClient.exists("/configs/" + mutableId, true)); + assertFalse(zkClient.exists("/configs/" + mutableId)); } @Test @@ -681,7 +681,7 @@ public void testBasicUserWorkflow() throws Exception { String mutableId = getMutableId(configSet); assertFalse(cc.getZkController().getClusterState().hasCollection(mutableId)); SolrZkClient zkClient = cc.getZkController().getZkClient(); - assertFalse(zkClient.exists("/configs/" + mutableId, true)); + assertFalse(zkClient.exists("/configs/" + mutableId)); SolrQuery query = new SolrQuery("*:*"); query.setRows(0); diff --git a/solr/core/src/test/org/apache/solr/handler/designer/TestSchemaDesignerConfigSetHelper.java b/solr/core/src/test/org/apache/solr/handler/designer/TestSchemaDesignerConfigSetHelper.java index 979ecd9ef0b..bcb51f4217d 100644 --- a/solr/core/src/test/org/apache/solr/handler/designer/TestSchemaDesignerConfigSetHelper.java +++ b/solr/core/src/test/org/apache/solr/handler/designer/TestSchemaDesignerConfigSetHelper.java @@ -180,8 +180,7 @@ public void testEnableDisableOptions() throws Exception { assertTrue( cluster .getZkClient() - .exists( - SchemaDesignerAPI.getConfigSetZkPath(mutableId, "lang/stopwords_en.txt"), true)); + .exists(SchemaDesignerAPI.getConfigSetZkPath(mutableId, "lang/stopwords_en.txt"))); assertNotNull(schema.getFieldTypeByName("text_fr")); assertNotNull(schema.getFieldOrNull("*_txt_fr")); assertNull(schema.getFieldOrNull("*_txt_ga")); @@ -204,8 +203,7 @@ public void testEnableDisableOptions() throws Exception { assertTrue( cluster .getZkClient() - .exists( - SchemaDesignerAPI.getConfigSetZkPath(mutableId, "lang/stopwords_en.txt"), true)); + .exists(SchemaDesignerAPI.getConfigSetZkPath(mutableId, "lang/stopwords_en.txt"))); assertNotNull(schema.getFieldTypeByName("text_fr")); assertNotNull(schema.getFieldOrNull("*_txt_fr")); assertNull(schema.getFieldOrNull("*_txt_ga")); diff --git a/solr/core/src/test/org/apache/solr/pkg/TestPackages.java b/solr/core/src/test/org/apache/solr/pkg/TestPackages.java index 3e8fea806e5..7c92be25e5a 100644 --- a/solr/core/src/test/org/apache/solr/pkg/TestPackages.java +++ b/solr/core/src/test/org/apache/solr/pkg/TestPackages.java @@ -623,7 +623,7 @@ public void testAPI() throws Exception { new MapWriterMap( (Map) Utils.fromJSON( - cluster.getZkClient().getData(SOLR_PKGS_PATH, null, new Stat(), true))), + cluster.getZkClient().getData(SOLR_PKGS_PATH, null, new Stat()))), Map.of(":packages:test_pkg[0]:version", "0.12", ":packages:test_pkg[0]:files[0]", FILE2)); // post a new jar with a proper signature @@ -647,7 +647,7 @@ public void testAPI() throws Exception { new MapWriterMap( (Map) Utils.fromJSON( - cluster.getZkClient().getData(SOLR_PKGS_PATH, null, new Stat(), true))), + cluster.getZkClient().getData(SOLR_PKGS_PATH, null, new Stat()))), Map.of(":packages:test_pkg[1]:version", "0.13", ":packages:test_pkg[1]:files[0]", FILE3)); // Now we will just delete one version @@ -673,7 +673,7 @@ public void testAPI() throws Exception { new MapWriterMap( (Map) Utils.fromJSON( - cluster.getZkClient().getData(SOLR_PKGS_PATH, null, new Stat(), true))), + cluster.getZkClient().getData(SOLR_PKGS_PATH, null, new Stat()))), Map.of(":packages:test_pkg[0]:version", "0.13", ":packages:test_pkg[0]:files[0]", FILE3)); // So far we have been verifying the details with ZK directly diff --git a/solr/core/src/test/org/apache/solr/schema/TestCloudManagedSchema.java b/solr/core/src/test/org/apache/solr/schema/TestCloudManagedSchema.java index 5c0f4f49d22..33c0f3e3952 100644 --- a/solr/core/src/test/org/apache/solr/schema/TestCloudManagedSchema.java +++ b/solr/core/src/test/org/apache/solr/schema/TestCloudManagedSchema.java @@ -92,16 +92,16 @@ public void test() throws Exception { private String getFileContentFromZooKeeper(SolrZkClient zkClient, String fileName) throws KeeperException, InterruptedException { - return (new String(zkClient.getData(fileName, null, null, true), StandardCharsets.UTF_8)); + return (new String(zkClient.getData(fileName, null, null), StandardCharsets.UTF_8)); } protected final void assertFileNotInZooKeeper( SolrZkClient zkClient, String parent, String fileName) throws Exception { - List kids = zkClient.getChildren(parent, null, true); + List kids = zkClient.getChildren(parent, null); for (String kid : kids) { if (kid.equalsIgnoreCase(fileName)) { String rawContent = - new String(zkClient.getData(fileName, null, null, true), StandardCharsets.UTF_8); + new String(zkClient.getData(fileName, null, null), StandardCharsets.UTF_8); fail( "File '" + fileName diff --git a/solr/core/src/test/org/apache/solr/schema/TestManagedSchemaThreadSafety.java b/solr/core/src/test/org/apache/solr/schema/TestManagedSchemaThreadSafety.java index bd452178f63..8e84d5e5728 100644 --- a/solr/core/src/test/org/apache/solr/schema/TestManagedSchemaThreadSafety.java +++ b/solr/core/src/test/org/apache/solr/schema/TestManagedSchemaThreadSafety.java @@ -73,11 +73,11 @@ boolean isSlowpoke() { } @Override - public byte[] getData(String path, Watcher watcher, Stat stat, boolean retryOnConnLoss) + public byte[] getData(String path, Watcher watcher, Stat stat) throws KeeperException, InterruptedException { byte[] data; try { - data = super.getData(path, watcher, stat, retryOnConnLoss); + data = super.getData(path, watcher, stat); } catch (NoNodeException e) { if (isSlowpoke()) { // System.out.println("suspending "+Thread.currentThread()+" on " + path); @@ -161,7 +161,7 @@ private ZkController createZkController(SolrZkClient client) public Boolean answer(InvocationOnMock invocation) throws Throwable { String path = (String) invocation.getArguments()[0]; perhapsExpired(); - Boolean exists = client.exists(path, true); + Boolean exists = client.exists(path); perhapsExpired(); return exists; } diff --git a/solr/core/src/test/org/apache/solr/security/BasicAuthIntegrationTest.java b/solr/core/src/test/org/apache/solr/security/BasicAuthIntegrationTest.java index 3599a4e2ebe..12352970d2e 100644 --- a/solr/core/src/test/org/apache/solr/security/BasicAuthIntegrationTest.java +++ b/solr/core/src/test/org/apache/solr/security/BasicAuthIntegrationTest.java @@ -112,7 +112,7 @@ public void testBasicAuth() throws Exception { JettySolrRunner randomJetty = cluster.getRandomJetty(random()); String baseUrl = randomJetty.getBaseUrl().toString(); verifySecurityStatus(cl, baseUrl + authcPrefix, "/errorMessages", null, 20); - zkClient().setData("/security.json", STD_CONF.replace("'", "\"").getBytes(UTF_8), true); + zkClient().setData("/security.json", STD_CONF.replace("'", "\"").getBytes(UTF_8)); verifySecurityStatus( cl, baseUrl + authcPrefix, "authentication/class", "solr.BasicAuthPlugin", 20); diff --git a/solr/core/src/test/org/apache/solr/security/BasicAuthOnSingleNodeTest.java b/solr/core/src/test/org/apache/solr/security/BasicAuthOnSingleNodeTest.java index 8b6708fe825..b5d49a9c55f 100644 --- a/solr/core/src/test/org/apache/solr/security/BasicAuthOnSingleNodeTest.java +++ b/solr/core/src/test/org/apache/solr/security/BasicAuthOnSingleNodeTest.java @@ -80,7 +80,7 @@ public void testDeleteSecurityJsonZnode() throws Exception { // Deleting security.json will disable security - before SOLR-9679 it would instead cause an // exception - cluster.getZkClient().delete("/security.json", -1, false); + cluster.getZkClient().delete("/security.json", -1); int count = 0; boolean done = false; diff --git a/solr/core/src/test/org/apache/solr/security/TestAuthorizationFramework.java b/solr/core/src/test/org/apache/solr/security/TestAuthorizationFramework.java index 3fdda76715d..ee04fcf20ed 100644 --- a/solr/core/src/test/org/apache/solr/security/TestAuthorizationFramework.java +++ b/solr/core/src/test/org/apache/solr/security/TestAuthorizationFramework.java @@ -53,8 +53,7 @@ public void distribSetUp() throws Exception { new ZkStateReader(zkServer.getZkAddress(), TIMEOUT, TIMEOUT)) { zkStateReader .getZkClient() - .create( - ZkStateReader.SOLR_SECURITY_CONF_PATH, SECURITY_JSON, CreateMode.PERSISTENT, true); + .create(ZkStateReader.SOLR_SECURITY_CONF_PATH, SECURITY_JSON, CreateMode.PERSISTENT); } } diff --git a/solr/core/src/test/org/apache/solr/update/processor/TimeRoutedAliasUpdateProcessorTest.java b/solr/core/src/test/org/apache/solr/update/processor/TimeRoutedAliasUpdateProcessorTest.java index 9a781215b8e..efba05bc1ca 100644 --- a/solr/core/src/test/org/apache/solr/update/processor/TimeRoutedAliasUpdateProcessorTest.java +++ b/solr/core/src/test/org/apache/solr/update/processor/TimeRoutedAliasUpdateProcessorTest.java @@ -214,8 +214,7 @@ public void test() throws Exception { + "/" + COLLECTION_PROPS_ZKNODE, null, - null, - true); + null); assertNotNull(data); assertTrue(data.length > 0); @SuppressWarnings("unchecked") @@ -1048,8 +1047,7 @@ public void process(WatchedEvent watchedEvent) { aliasUpdate.countDown(); } }, - stat, - true); + stat); } /** @@ -1272,7 +1270,7 @@ private void manuallyConstructLegacyTRA() throws Exception { } // now grab the zk data, so we can hack in our legacy collections... - byte[] data = zkStateReader.getZkClient().getData("/aliases.json", null, null, true); + byte[] data = zkStateReader.getZkClient().getData("/aliases.json", null, null); // some tidbits for handling zk data here are swiped from Aliases.json Map aliasMap; @@ -1293,7 +1291,7 @@ private void manuallyConstructLegacyTRA() throws Exception { colAliases.put(alias, String.join(",", legacy24, legacy23)); data = Utils.toJSON(aliasMap); - zkStateReader.getZkClient().setData("/aliases.json", data, true); + zkStateReader.getZkClient().setData("/aliases.json", data); zkStateReader.aliasesManager.update(); // make sure we've updated with the data we just sent diff --git a/solr/licenses/curator-client-LICENSE-ASL.txt b/solr/licenses/curator-LICENSE-ASL.txt similarity index 100% rename from solr/licenses/curator-client-LICENSE-ASL.txt rename to solr/licenses/curator-LICENSE-ASL.txt diff --git a/solr/licenses/curator-client-NOTICE.txt b/solr/licenses/curator-NOTICE.txt similarity index 100% rename from solr/licenses/curator-client-NOTICE.txt rename to solr/licenses/curator-NOTICE.txt diff --git a/solr/licenses/curator-framework-LICENSE-ASL.txt b/solr/licenses/curator-framework-LICENSE-ASL.txt deleted file mode 100644 index 7a4a3ea2424..00000000000 --- a/solr/licenses/curator-framework-LICENSE-ASL.txt +++ /dev/null @@ -1,202 +0,0 @@ - - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - - APPENDIX: How to apply the Apache License to your work. - - To apply the Apache License to your work, attach the following - boilerplate notice, with the fields enclosed by brackets "[]" - replaced with your own identifying information. (Don't include - the brackets!) The text should be enclosed in the appropriate - comment syntax for the file format. We also recommend that a - file or class name and description of purpose be included on the - same "printed page" as the copyright notice for easier - identification within third-party archives. - - Copyright [yyyy] [name of copyright owner] - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. \ No newline at end of file diff --git a/solr/licenses/curator-framework-NOTICE.txt b/solr/licenses/curator-framework-NOTICE.txt deleted file mode 100644 index f568d0fe32e..00000000000 --- a/solr/licenses/curator-framework-NOTICE.txt +++ /dev/null @@ -1,5 +0,0 @@ -Apache Curator -Copyright 2013-2014 The Apache Software Foundation - -This product includes software developed at -The Apache Software Foundation (http://www.apache.org/). \ No newline at end of file diff --git a/solr/licenses/curator-recipes-LICENSE-ASL.txt b/solr/licenses/curator-recipes-LICENSE-ASL.txt deleted file mode 100644 index 7a4a3ea2424..00000000000 --- a/solr/licenses/curator-recipes-LICENSE-ASL.txt +++ /dev/null @@ -1,202 +0,0 @@ - - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - - APPENDIX: How to apply the Apache License to your work. - - To apply the Apache License to your work, attach the following - boilerplate notice, with the fields enclosed by brackets "[]" - replaced with your own identifying information. (Don't include - the brackets!) The text should be enclosed in the appropriate - comment syntax for the file format. We also recommend that a - file or class name and description of purpose be included on the - same "printed page" as the copyright notice for easier - identification within third-party archives. - - Copyright [yyyy] [name of copyright owner] - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. \ No newline at end of file diff --git a/solr/licenses/curator-recipes-NOTICE.txt b/solr/licenses/curator-recipes-NOTICE.txt deleted file mode 100644 index f568d0fe32e..00000000000 --- a/solr/licenses/curator-recipes-NOTICE.txt +++ /dev/null @@ -1,5 +0,0 @@ -Apache Curator -Copyright 2013-2014 The Apache Software Foundation - -This product includes software developed at -The Apache Software Foundation (http://www.apache.org/). \ No newline at end of file diff --git a/solr/licenses/curator-test-5.5.0.jar.sha1 b/solr/licenses/curator-test-5.5.0.jar.sha1 new file mode 100644 index 00000000000..5f377502d11 --- /dev/null +++ b/solr/licenses/curator-test-5.5.0.jar.sha1 @@ -0,0 +1 @@ +065586d87700aa29855e6aa566b210eadd1bb38d diff --git a/solr/modules/hadoop-auth/build.gradle b/solr/modules/hadoop-auth/build.gradle index 3bf7bfab75f..3aec2cfd644 100644 --- a/solr/modules/hadoop-auth/build.gradle +++ b/solr/modules/hadoop-auth/build.gradle @@ -50,14 +50,15 @@ dependencies { implementation('org.apache.zookeeper:zookeeper', { exclude group: "org.apache.yetus", module: "audience-annotations" }) - implementation ('org.apache.zookeeper:zookeeper-jute') { - exclude group: 'org.apache.yetus', module: 'audience-annotations' - } // required for instantiating a Zookeeper server (for embedding ZK or running tests) runtimeOnly 'org.xerial.snappy:snappy-java' - implementation 'org.apache.curator:curator-client' - implementation 'org.apache.curator:curator-framework' - runtimeOnly 'org.apache.curator:curator-recipes' + + implementation('org.apache.curator:curator-framework', { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + }) + runtimeOnly('org.apache.curator:curator-recipes', { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + }) // Hadoop auth framework implementation 'org.apache.hadoop:hadoop-annotations' @@ -105,6 +106,9 @@ dependencies { testImplementation('org.apache.zookeeper:zookeeper', { exclude group: "org.apache.yetus", module: "audience-annotations" }) + testImplementation ('org.apache.zookeeper:zookeeper-jute') { + exclude group: 'org.apache.yetus', module: 'audience-annotations' + } // required for instantiating a Zookeeper server in tests or embedded testRuntimeOnly ('org.xerial.snappy:snappy-java') } diff --git a/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/DelegationTokenKerberosFilter.java b/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/DelegationTokenKerberosFilter.java index b0021c889a5..a1c211b05ad 100644 --- a/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/DelegationTokenKerberosFilter.java +++ b/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/DelegationTokenKerberosFilter.java @@ -20,23 +20,15 @@ import static org.apache.hadoop.security.token.delegation.ZKDelegationTokenSecretManager.ZK_DTSM_ZNODE_WORKING_PATH_DEAFULT; import java.io.IOException; -import java.util.ArrayList; import java.util.Enumeration; -import java.util.List; import java.util.Objects; -import java.util.concurrent.ExecutorService; import javax.servlet.FilterChain; import javax.servlet.FilterConfig; import javax.servlet.ServletException; import javax.servlet.ServletRequest; import javax.servlet.ServletResponse; import javax.servlet.http.HttpServletRequest; -import org.apache.curator.RetryPolicy; -import org.apache.curator.framework.AuthInfo; import org.apache.curator.framework.CuratorFramework; -import org.apache.curator.framework.CuratorFrameworkFactory; -import org.apache.curator.framework.api.ACLProvider; -import org.apache.curator.retry.ExponentialBackoffRetry; import org.apache.hadoop.conf.Configuration; import org.apache.hadoop.security.UserGroupInformation; import org.apache.hadoop.security.authentication.server.AuthenticationHandler; @@ -44,13 +36,8 @@ import org.apache.hadoop.security.token.delegation.web.HttpUserGroupInformation; import org.apache.solr.common.cloud.SecurityAwareZkACLProvider; import org.apache.solr.common.cloud.SolrZkClient; -import org.apache.solr.common.cloud.ZkACLProvider; -import org.apache.solr.common.cloud.ZkCredentialsProvider; -import org.apache.solr.common.util.ExecutorUtil; -import org.apache.solr.common.util.SolrNamedThreadFactory; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.data.ACL; /** * This is an authentication filter based on Hadoop's {@link DelegationTokenAuthenticationFilter}. @@ -58,9 +45,6 @@ * reuse the authentication of an end-user or another application. */ public class DelegationTokenKerberosFilter extends DelegationTokenAuthenticationFilter { - private ExecutorService curatorSafeServiceExecutor; - private CuratorFramework curatorFramework; - @Override public void init(FilterConfig conf) throws ServletException { if (conf != null && "zookeeper".equals(conf.getInitParameter("signer.secret.provider"))) { @@ -129,19 +113,6 @@ public void doFilter(ServletRequest servletRequest, ServletResponse servletRespo super.doFilter(request, response, filterChainWrapper); } - @Override - public void destroy() { - super.destroy(); - if (curatorFramework != null) { - curatorFramework.close(); - curatorFramework = null; - } - if (curatorSafeServiceExecutor != null) { - ExecutorUtil.shutdownNowAndAwaitTermination(curatorSafeServiceExecutor); - curatorSafeServiceExecutor = null; - } - } - @Override protected void initializeAuthHandler(String authHandlerClassName, FilterConfig filterConfig) throws ServletException { @@ -183,108 +154,19 @@ private CuratorFramework getCuratorClientInternal(FilterConfig conf, SolrZkClien protected CuratorFramework getCuratorClient(SolrZkClient zkClient) throws InterruptedException, KeeperException { - // should we try to build a RetryPolicy off of the ZkController? - RetryPolicy retryPolicy = new ExponentialBackoffRetry(1000, 3); - if (zkClient == null) { - throw new IllegalArgumentException("zkClient required"); - } - String zkHost = zkClient.getZkServerAddress(); - String zkChroot = zkHost.contains("/") ? zkHost.substring(zkHost.indexOf('/')) : ""; - String zkNamespace = zkChroot + SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH; - zkNamespace = zkNamespace.startsWith("/") ? zkNamespace.substring(1) : zkNamespace; - String zkConnectionString = - zkHost.contains("/") ? zkHost.substring(0, zkHost.indexOf('/')) : zkHost; - SolrZkToCuratorCredentialsACLs curatorToSolrZk = new SolrZkToCuratorCredentialsACLs(zkClient); - final int connectionTimeoutMs = 30000; // this value is currently hard coded, see SOLR-7561. - // Create /security znode upfront. Without this, the curator framework creates this directory // path // without the appropriate ACL configuration. This issue is possibly related to HADOOP-11973 try { - zkClient.makePath( - SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH, CreateMode.PERSISTENT, true); - } catch (KeeperException.NodeExistsException ignore) { + zkClient.makePath(SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH, CreateMode.PERSISTENT); + } catch (KeeperException.NodeExistsException ex) { + // ignore? } - curatorSafeServiceExecutor = - ExecutorUtil.newMDCAwareSingleThreadExecutor( - new SolrNamedThreadFactory("delegationtokenkerberosfilter-curator-safeService")); - curatorFramework = - CuratorFrameworkFactory.builder() - .namespace(zkNamespace) - .connectString(zkConnectionString) - .retryPolicy(retryPolicy) - .aclProvider(curatorToSolrZk.getACLProvider()) - .authorization(curatorToSolrZk.getAuthInfos()) - .sessionTimeoutMs(zkClient.getZkClientTimeout()) - .connectionTimeoutMs(connectionTimeoutMs) - .runSafeService(curatorSafeServiceExecutor) - .build(); - curatorFramework.start(); - - return curatorFramework; - } - - /** Convert Solr Zk Credentials/ACLs to Curator versions */ - protected static class SolrZkToCuratorCredentialsACLs { - private final String zkChroot; - private final ACLProvider aclProvider; - private final List authInfos; - - public SolrZkToCuratorCredentialsACLs(SolrZkClient zkClient) { - this.aclProvider = createACLProvider(zkClient); - this.authInfos = createAuthInfo(zkClient); - String zkHost = zkClient.getZkServerAddress(); - this.zkChroot = zkHost.contains("/") ? zkHost.substring(zkHost.indexOf('/')) : null; - } + // Note - Curator complains if the namespace starts with / + String namespace = zkClient.getAbsolutePath(SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH); + namespace = namespace.startsWith("/") ? namespace.substring(1) : namespace; - public ACLProvider getACLProvider() { - return aclProvider; - } - - public List getAuthInfos() { - return authInfos; - } - - private ACLProvider createACLProvider(SolrZkClient zkClient) { - final ZkACLProvider zkACLProvider = zkClient.getZkACLProvider(); - return new ACLProvider() { - @Override - public List getDefaultAcl() { - return zkACLProvider.getACLsToAdd(null); - } - - @Override - public List getAclForPath(String path) { - List acls = null; - - // The logic in SecurityAwareZkACLProvider does not work when - // the Solr zkPath is chrooted (e.g. /solr instead of /). This - // due to the fact that the getACLsToAdd(..) callback provides - // an absolute path (instead of relative path to the chroot) and - // the string comparison in SecurityAwareZkACLProvider fails. - if (zkACLProvider instanceof SecurityAwareZkACLProvider && zkChroot != null) { - acls = zkACLProvider.getACLsToAdd(path.replace(zkChroot, "")); - } else { - acls = zkACLProvider.getACLsToAdd(path); - } - - return acls; - } - }; - } - - private List createAuthInfo(SolrZkClient zkClient) { - List ret = new ArrayList<>(); - - // In theory the credentials to add could change here if zookeeper hasn't been initialized - ZkCredentialsProvider credentialsProvider = - zkClient.getZkClientConnectionStrategy().getZkCredentialsToAddAutomatically(); - for (ZkCredentialsProvider.ZkCredentials zkCredentials : - credentialsProvider.getCredentials()) { - ret.add(new AuthInfo(zkCredentials.getScheme(), zkCredentials.getAuth())); - } - return ret; - } + return zkClient.getCuratorFramework().usingNamespace(namespace); } } diff --git a/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/HadoopAuthFilter.java b/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/HadoopAuthFilter.java index f462ad7e682..9a5dcff772d 100644 --- a/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/HadoopAuthFilter.java +++ b/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/HadoopAuthFilter.java @@ -20,35 +20,22 @@ import static org.apache.hadoop.security.token.delegation.ZKDelegationTokenSecretManager.ZK_DTSM_ZNODE_WORKING_PATH_DEAFULT; import java.io.IOException; -import java.util.ArrayList; -import java.util.List; import java.util.Objects; -import java.util.concurrent.ExecutorService; import javax.servlet.FilterChain; import javax.servlet.FilterConfig; import javax.servlet.ServletException; import javax.servlet.ServletRequest; import javax.servlet.ServletResponse; import javax.servlet.http.HttpServletRequest; -import org.apache.curator.RetryPolicy; -import org.apache.curator.framework.AuthInfo; import org.apache.curator.framework.CuratorFramework; -import org.apache.curator.framework.CuratorFrameworkFactory; -import org.apache.curator.framework.api.ACLProvider; -import org.apache.curator.retry.ExponentialBackoffRetry; import org.apache.hadoop.security.UserGroupInformation; import org.apache.hadoop.security.authentication.server.AuthenticationHandler; import org.apache.hadoop.security.token.delegation.web.DelegationTokenAuthenticationFilter; import org.apache.hadoop.security.token.delegation.web.HttpUserGroupInformation; import org.apache.solr.common.cloud.SecurityAwareZkACLProvider; import org.apache.solr.common.cloud.SolrZkClient; -import org.apache.solr.common.cloud.ZkACLProvider; -import org.apache.solr.common.cloud.ZkCredentialsProvider; -import org.apache.solr.common.util.ExecutorUtil; -import org.apache.solr.common.util.SolrNamedThreadFactory; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.data.ACL; /** * This is an authentication filter based on Hadoop's {@link DelegationTokenAuthenticationFilter}. @@ -60,9 +47,6 @@ public class HadoopAuthFilter extends DelegationTokenAuthenticationFilter { */ static final String DELEGATION_TOKEN_ZK_CLIENT = "solr.kerberos.delegation.token.zk.client"; - private ExecutorService curatorSafeServiceExecutor; - private CuratorFramework curatorFramework; - @Override public void init(FilterConfig conf) throws ServletException { if (conf != null && "zookeeper".equals(conf.getInitParameter("signer.secret.provider"))) { @@ -111,14 +95,6 @@ public void doFilter(ServletRequest servletRequest, ServletResponse servletRespo @Override public void destroy() { super.destroy(); - if (curatorFramework != null) { - curatorFramework.close(); - curatorFramework = null; - } - if (curatorSafeServiceExecutor != null) { - ExecutorUtil.shutdownNowAndAwaitTermination(curatorSafeServiceExecutor); - curatorSafeServiceExecutor = null; - } } @Override @@ -161,109 +137,20 @@ private CuratorFramework getCuratorClientInternal(FilterConfig conf, SolrZkClien } protected CuratorFramework getCuratorClient(SolrZkClient zkClient) - throws KeeperException, InterruptedException { - // should we try to build a RetryPolicy off of the ZkController? - RetryPolicy retryPolicy = new ExponentialBackoffRetry(1000, 3); - if (zkClient == null) { - throw new IllegalArgumentException("zkClient required"); - } - String zkHost = zkClient.getZkServerAddress(); - String zkChroot = zkHost.contains("/") ? zkHost.substring(zkHost.indexOf('/')) : ""; - String zkNamespace = zkChroot + SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH; - zkNamespace = zkNamespace.startsWith("/") ? zkNamespace.substring(1) : zkNamespace; - String zkConnectionString = - zkHost.contains("/") ? zkHost.substring(0, zkHost.indexOf('/')) : zkHost; - SolrZkToCuratorCredentialsACLs curatorToSolrZk = new SolrZkToCuratorCredentialsACLs(zkClient); - final int connectionTimeoutMs = 30000; // this value is currently hard coded, see SOLR-7561. - + throws InterruptedException, KeeperException { // Create /security znode upfront. Without this, the curator framework creates this directory // path // without the appropriate ACL configuration. This issue is possibly related to HADOOP-11973 try { - zkClient.makePath( - SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH, CreateMode.PERSISTENT, true); - } catch (KeeperException.NodeExistsException ignore) { + zkClient.makePath(SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH, CreateMode.PERSISTENT); + } catch (KeeperException.NodeExistsException ex) { + // ignore? } - curatorSafeServiceExecutor = - ExecutorUtil.newMDCAwareSingleThreadExecutor( - new SolrNamedThreadFactory("hadoopauthfilter-curator-safeService")); - curatorFramework = - CuratorFrameworkFactory.builder() - .namespace(zkNamespace) - .connectString(zkConnectionString) - .retryPolicy(retryPolicy) - .aclProvider(curatorToSolrZk.getACLProvider()) - .authorization(curatorToSolrZk.getAuthInfos()) - .sessionTimeoutMs(zkClient.getZkClientTimeout()) - .connectionTimeoutMs(connectionTimeoutMs) - .runSafeService(curatorSafeServiceExecutor) - .build(); - curatorFramework.start(); + // Note - Curator complains if the namespace starts with / + String namespace = zkClient.getAbsolutePath(SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH); + namespace = namespace.startsWith("/") ? namespace.substring(1) : namespace; - return curatorFramework; - } - - /** Convert Solr Zk Credentials/ACLs to Curator versions */ - protected static class SolrZkToCuratorCredentialsACLs { - private final String zkChroot; - private final ACLProvider aclProvider; - private final List authInfos; - - public SolrZkToCuratorCredentialsACLs(SolrZkClient zkClient) { - this.aclProvider = createACLProvider(zkClient); - this.authInfos = createAuthInfo(zkClient); - String zkHost = zkClient.getZkServerAddress(); - this.zkChroot = zkHost.contains("/") ? zkHost.substring(zkHost.indexOf('/')) : null; - } - - public ACLProvider getACLProvider() { - return aclProvider; - } - - public List getAuthInfos() { - return authInfos; - } - - private ACLProvider createACLProvider(SolrZkClient zkClient) { - final ZkACLProvider zkACLProvider = zkClient.getZkACLProvider(); - return new ACLProvider() { - @Override - public List getDefaultAcl() { - return zkACLProvider.getACLsToAdd(null); - } - - @Override - public List getAclForPath(String path) { - List acls = null; - - // The logic in SecurityAwareZkACLProvider does not work when - // the Solr zkPath is chrooted (e.g. /solr instead of /). This - // due to the fact that the getACLsToAdd(..) callback provides - // an absolute path (instead of relative path to the chroot) and - // the string comparison in SecurityAwareZkACLProvider fails. - if (zkACLProvider instanceof SecurityAwareZkACLProvider && zkChroot != null) { - acls = zkACLProvider.getACLsToAdd(path.replace(zkChroot, "")); - } else { - acls = zkACLProvider.getACLsToAdd(path); - } - - return acls; - } - }; - } - - private List createAuthInfo(SolrZkClient zkClient) { - List ret = new ArrayList<>(); - - // In theory the credentials to add could change here if zookeeper hasn't been initialized - ZkCredentialsProvider credentialsProvider = - zkClient.getZkClientConnectionStrategy().getZkCredentialsToAddAutomatically(); - for (ZkCredentialsProvider.ZkCredentials zkCredentials : - credentialsProvider.getCredentials()) { - ret.add(new AuthInfo(zkCredentials.getScheme(), zkCredentials.getAuth())); - } - return ret; - } + return zkClient.getCuratorFramework().usingNamespace(namespace); } } diff --git a/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/HadoopAuthPlugin.java b/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/HadoopAuthPlugin.java index 3e9d904d6f9..f48d36d6d18 100644 --- a/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/HadoopAuthPlugin.java +++ b/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/HadoopAuthPlugin.java @@ -35,6 +35,7 @@ import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.apache.hadoop.security.authentication.server.AuthenticationFilter; +import org.apache.hadoop.security.authentication.util.ZKSignerSecretProvider; import org.apache.hadoop.security.token.delegation.web.DelegationTokenAuthenticationHandler; import org.apache.solr.client.solrj.impl.Krb5HttpClientBuilder; import org.apache.solr.cloud.ZkController; @@ -189,6 +190,7 @@ protected FilterConfig getInitFilterConfig(Map pluginConfig) { ZkController controller = coreContainer.getZkController(); if (controller != null) { servletContext.setAttribute(DELEGATION_TOKEN_ZK_CLIENT, controller.getZkClient()); + params.put(ZKSignerSecretProvider.DISCONNECT_FROM_ZOOKEEPER_ON_SHUTDOWN, "false"); } FilterConfig conf = diff --git a/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/KerberosPlugin.java b/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/KerberosPlugin.java index 34729db1f1d..45aa467ba00 100644 --- a/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/KerberosPlugin.java +++ b/solr/modules/hadoop-auth/src/java/org/apache/solr/security/hadoop/KerberosPlugin.java @@ -32,6 +32,7 @@ import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.apache.hadoop.security.authentication.util.KerberosName; +import org.apache.hadoop.security.authentication.util.ZKSignerSecretProvider; import org.apache.hadoop.security.token.delegation.web.DelegationTokenAuthenticationHandler; import org.apache.http.HttpRequest; import org.apache.http.protocol.HttpContext; @@ -157,6 +158,8 @@ protected FilterConfig getInitFilterConfig( "/token"); // ensure krb5 is setup properly before running curator getHttpClientBuilder(SolrHttpClientBuilder.create()); + + params.put(ZKSignerSecretProvider.DISCONNECT_FROM_ZOOKEEPER_ON_SHUTDOWN, "false"); } } else { log.info( diff --git a/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/SaslZkACLProviderTest.java b/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/SaslZkACLProviderTest.java index 0dbfee03cb5..c06d8ecd420 100644 --- a/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/SaslZkACLProviderTest.java +++ b/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/SaslZkACLProviderTest.java @@ -24,6 +24,7 @@ import java.nio.charset.StandardCharsets; import java.nio.file.Path; import java.util.concurrent.TimeUnit; +import org.apache.curator.framework.api.ACLProvider; import org.apache.lucene.tests.util.QuickPatchThreadsFilter; import org.apache.lucene.util.Constants; import org.apache.solr.SolrIgnoredThreadsFilter; @@ -96,7 +97,7 @@ public void setUp() throws Exception { new SolrZkClientWithACLs(zkServer.getZkHost(), AbstractZkTestCase.TIMEOUT)) { ZooKeeperSaslClient saslClient = zkClient.getZooKeeper().getSaslClient(); assumeFalse("Could not set up ZK with SASL", saslClient.isFailed()); - zkClient.makePath("/solr", false, true); + zkClient.makePath("/solr", false); } catch (KeeperException e) { // This fails on Linux but passes on Windows and MacOS. Why? assumeNoException("Could not set up ZK chroot, see SOLR-15366.", e); @@ -113,17 +114,13 @@ protected void setupZNodes() throws Exception { new SolrZkClientWithACLs(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT); try { zkClient.create( - "/protectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); + "/protectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.makePath( - "/protectedMakePathNode", - "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); + "/protectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.create( SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH, "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); + CreateMode.PERSISTENT); } finally { zkClient.close(); } @@ -131,15 +128,9 @@ protected void setupZNodes() throws Exception { zkClient = new SolrZkClientNoACLs(zkServer.getZkAddress(), AbstractZkTestCase.TIMEOUT); try { zkClient.create( - "/unprotectedCreateNode", - "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); + "/unprotectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.makePath( - "/unprotectedMakePathNode", - "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); + "/unprotectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); } finally { zkClient.close(); } @@ -188,7 +179,7 @@ public SolrZkClientWithACLs(String zkServerAddress, int zkClientTimeout) { } @Override - public ZkACLProvider createZkACLProvider() { + public ZkACLProvider createACLProvider() { return new SaslZkACLProvider(); } } @@ -204,7 +195,7 @@ public SolrZkClientNoACLs(String zkServerAddress, int zkClientTimeout) { } @Override - public ZkACLProvider createZkACLProvider() { + public ACLProvider createACLProvider() { return new DefaultZkACLProvider(); } } diff --git a/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestDelegationWithHadoopAuth.java b/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestDelegationWithHadoopAuth.java index 0fd49a52314..60fc0e4e145 100644 --- a/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestDelegationWithHadoopAuth.java +++ b/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestDelegationWithHadoopAuth.java @@ -360,8 +360,8 @@ public void testZNodePaths() throws Exception { .withUrl(cluster.getZkServer().getZkAddress()) .withTimeout(1000, TimeUnit.MILLISECONDS) .build()) { - assertTrue(zkClient.exists("/security/zkdtsm", true)); - assertTrue(zkClient.exists("/security/token", true)); + assertTrue(zkClient.exists("/security/zkdtsm")); + assertTrue(zkClient.exists("/security/token")); } } diff --git a/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestImpersonationWithHadoopAuth.java b/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestImpersonationWithHadoopAuth.java index 6a1d484c917..2adb385ff04 100644 --- a/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestImpersonationWithHadoopAuth.java +++ b/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestImpersonationWithHadoopAuth.java @@ -53,8 +53,7 @@ public static void setupClass() throws Exception { InetAddress loopback = InetAddress.getLoopbackAddress(); Path securityJsonPath = TEST_PATH().resolve("security").resolve("hadoop_simple_auth_with_delegation.json"); - String securityJson = - new String(Files.readAllBytes(securityJsonPath), Charset.defaultCharset()); + String securityJson = Files.readString(securityJsonPath, Charset.defaultCharset()); Map securityConfig = (Map) Utils.fromJSONString(securityJson); Map authConfig = (Map) securityConfig.get("authentication"); diff --git a/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestSolrCloudWithDelegationTokens.java b/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestSolrCloudWithDelegationTokens.java index 859857eed1b..1a99d543af5 100644 --- a/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestSolrCloudWithDelegationTokens.java +++ b/solr/modules/hadoop-auth/src/test/org/apache/solr/security/hadoop/TestSolrCloudWithDelegationTokens.java @@ -77,10 +77,6 @@ public static void startup() throws Exception { @AfterClass public static void shutdown() throws Exception { - if (miniCluster != null) { - miniCluster.shutdown(); - miniCluster = null; - } if (null != solrClientPrimary) { solrClientPrimary.close(); solrClientPrimary = null; @@ -89,6 +85,11 @@ public static void shutdown() throws Exception { solrClientSecondary.close(); solrClientSecondary = null; } + + if (miniCluster != null) { + miniCluster.shutdown(); + miniCluster = null; + } System.clearProperty("authenticationPlugin"); System.clearProperty(KerberosPlugin.DELEGATION_TOKEN_ENABLED); System.clearProperty("solr.kerberos.cookie.domain"); @@ -398,8 +399,8 @@ public void testZNodePaths() throws Exception { .withUrl(miniCluster.getZkServer().getZkAddress()) .withTimeout(1000, TimeUnit.MILLISECONDS) .build()) { - assertTrue(zkClient.exists("/security/zkdtsm", true)); - assertTrue(zkClient.exists("/security/token", true)); + assertTrue(zkClient.exists("/security/zkdtsm")); + assertTrue(zkClient.exists("/security/token")); } } diff --git a/solr/modules/hdfs/src/test/org/apache/solr/hdfs/cloud/api/collections/TestHdfsCloudBackupRestore.java b/solr/modules/hdfs/src/test/org/apache/solr/hdfs/cloud/api/collections/TestHdfsCloudBackupRestore.java index 9cb6c9ec25a..b1616c20b6f 100644 --- a/solr/modules/hdfs/src/test/org/apache/solr/hdfs/cloud/api/collections/TestHdfsCloudBackupRestore.java +++ b/solr/modules/hdfs/src/test/org/apache/solr/hdfs/cloud/api/collections/TestHdfsCloudBackupRestore.java @@ -160,8 +160,7 @@ public static void setupClass() throws Exception { + "confFaulty" + Path.SEPARATOR + "solrconfig.xml", - -1, - true); + -1); } @AfterClass diff --git a/solr/modules/jwt-auth/src/test/org/apache/solr/security/jwt/JWTAuthPluginIntegrationTest.java b/solr/modules/jwt-auth/src/test/org/apache/solr/security/jwt/JWTAuthPluginIntegrationTest.java index c2613d8550c..1fea4d8319d 100644 --- a/solr/modules/jwt-auth/src/test/org/apache/solr/security/jwt/JWTAuthPluginIntegrationTest.java +++ b/solr/modules/jwt-auth/src/test/org/apache/solr/security/jwt/JWTAuthPluginIntegrationTest.java @@ -303,7 +303,7 @@ private MiniSolrCloudCluster configureClusterMockOauth( .withDefaultClusterProperty("useLegacyReplicaAssignment", "false") .build(); String securityJson = createMockOAuthSecurityJson(pemFilePath); - myCluster.zkSetData("/security.json", securityJson.getBytes(Charset.defaultCharset()), true); + myCluster.zkSetData("/security.json", securityJson.getBytes(Charset.defaultCharset())); RTimer timer = new RTimer(); do { // Wait timeoutMs time for the security.json change to take effect Thread.sleep(200); diff --git a/solr/solrj-zookeeper/build.gradle b/solr/solrj-zookeeper/build.gradle index 1ac5febdb06..0ddc632759a 100644 --- a/solr/solrj-zookeeper/build.gradle +++ b/solr/solrj-zookeeper/build.gradle @@ -32,6 +32,13 @@ dependencies { implementation project(':solr:solrj') + api('org.apache.curator:curator-client', { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + }) + api('org.apache.curator:curator-framework', { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + }) + // declare dependencies we use even though already declared by solrj-core implementation 'org.slf4j:slf4j-api' implementation 'org.apache.httpcomponents:httpclient' diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/cloud/DistribStateManager.java b/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/cloud/DistribStateManager.java index 3ec636de1a8..c558debc62d 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/cloud/DistribStateManager.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/cloud/DistribStateManager.java @@ -24,13 +24,13 @@ import java.util.List; import java.util.Map; import java.util.NoSuchElementException; +import org.apache.curator.framework.api.transaction.CuratorTransactionResult; import org.apache.solr.common.SolrCloseable; import org.apache.solr.common.cloud.DocCollection; import org.apache.solr.common.cloud.PerReplicaStates; +import org.apache.solr.common.cloud.SolrZkClient; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.Op; -import org.apache.zookeeper.OpResult; import org.apache.zookeeper.Watcher; /** This interface represents a distributed state repository. */ @@ -85,7 +85,7 @@ void setData(String path, byte[] data, int version) throws BadVersionException, NoSuchElementException, IOException, KeeperException, InterruptedException; - List multi(final Iterable ops) + List multi(final List ops) throws BadVersionException, NoSuchElementException, AlreadyExistsException, IOException, KeeperException, InterruptedException; diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/impl/ZkClientClusterStateProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/impl/ZkClientClusterStateProvider.java index 075c1e4d3de..4e74981a661 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/impl/ZkClientClusterStateProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/impl/ZkClientClusterStateProvider.java @@ -100,7 +100,7 @@ public static ClusterState createFromJsonSupportingLegacyConfigName( try { // read configName from collections/collection node String path = ZkStateReader.COLLECTIONS_ZKNODE + "/" + coll; - byte[] data = zkClient.getData(path, null, null, true); + byte[] data = zkClient.getData(path, null, null); if (data != null && data.length > 0) { ZkNodeProps configProp = ZkNodeProps.load(data); String configName = configProp.getStr(ZkStateReader.CONFIGNAME_PROP); diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/impl/ZkDistribStateManager.java b/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/impl/ZkDistribStateManager.java index e5a987c38d9..15d3ebc2651 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/impl/ZkDistribStateManager.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/client/solrj/impl/ZkDistribStateManager.java @@ -22,6 +22,7 @@ import java.util.List; import java.util.Map; import java.util.NoSuchElementException; +import org.apache.curator.framework.api.transaction.CuratorTransactionResult; import org.apache.solr.client.solrj.cloud.AlreadyExistsException; import org.apache.solr.client.solrj.cloud.BadVersionException; import org.apache.solr.client.solrj.cloud.DistribStateManager; @@ -34,8 +35,6 @@ import org.apache.solr.common.util.Utils; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.Op; -import org.apache.zookeeper.OpResult; import org.apache.zookeeper.Watcher; import org.apache.zookeeper.data.Stat; @@ -67,7 +66,7 @@ public Map getJson(String path) @Override public boolean hasData(String path) throws IOException, KeeperException, InterruptedException { try { - return zkClient.exists(path, true); + return zkClient.exists(path); } catch (InterruptedException e) { Thread.currentThread().interrupt(); throw new AlreadyClosedException(); @@ -78,7 +77,7 @@ public boolean hasData(String path) throws IOException, KeeperException, Interru public List listData(String path, Watcher watcher) throws NoSuchElementException, IOException, KeeperException, InterruptedException { try { - return zkClient.getChildren(path, watcher, true); + return zkClient.getChildren(path, watcher); } catch (KeeperException.NoNodeException e) { throw new NoSuchElementException(path); } catch (InterruptedException e) { @@ -98,7 +97,7 @@ public VersionedData getData(String path, Watcher watcher) throws NoSuchElementException, IOException, KeeperException, InterruptedException { Stat stat = new Stat(); try { - byte[] bytes = zkClient.getData(path, watcher, stat, true); + byte[] bytes = zkClient.getData(path, watcher, stat); return new VersionedData( stat.getVersion(), bytes, @@ -116,7 +115,7 @@ public VersionedData getData(String path, Watcher watcher) public void makePath(String path) throws AlreadyExistsException, IOException, KeeperException, InterruptedException { try { - zkClient.makePath(path, true); + zkClient.makePath(path); } catch (KeeperException.NodeExistsException e) { throw new AlreadyExistsException(path); } catch (InterruptedException e) { @@ -129,7 +128,7 @@ public void makePath(String path) public void makePath(String path, byte[] data, CreateMode createMode, boolean failOnExists) throws AlreadyExistsException, IOException, KeeperException, InterruptedException { try { - zkClient.makePath(path, data, createMode, null, failOnExists, true); + zkClient.makePath(path, data, createMode, null, failOnExists); } catch (KeeperException.NodeExistsException e) { throw new AlreadyExistsException(path); } catch (InterruptedException e) { @@ -143,7 +142,7 @@ public String createData(String path, byte[] data, CreateMode mode) throws NoSuchElementException, AlreadyExistsException, IOException, KeeperException, InterruptedException { try { - return zkClient.create(path, data, mode, true); + return zkClient.create(path, data, mode); } catch (KeeperException.NoNodeException e) { throw new NoSuchElementException(path); } catch (KeeperException.NodeExistsException e) { @@ -159,7 +158,7 @@ public void removeData(String path, int version) throws NoSuchElementException, BadVersionException, NotEmptyException, IOException, KeeperException, InterruptedException { try { - zkClient.delete(path, version, true); + zkClient.delete(path, version); } catch (KeeperException.NoNodeException e) { throw new NoSuchElementException(path); } catch (KeeperException.NotEmptyException e) { @@ -177,7 +176,7 @@ public void setData(String path, byte[] data, int version) throws BadVersionException, NoSuchElementException, IOException, KeeperException, InterruptedException { try { - zkClient.setData(path, data, version, true); + zkClient.setData(path, data, version); } catch (KeeperException.NoNodeException e) { throw new NoSuchElementException(path); } catch (KeeperException.BadVersionException e) { @@ -189,11 +188,11 @@ public void setData(String path, byte[] data, int version) } @Override - public List multi(Iterable ops) + public List multi(List ops) throws BadVersionException, AlreadyExistsException, NoSuchElementException, IOException, KeeperException, InterruptedException { try { - return zkClient.multi(ops, true); + return zkClient.multi(ops); } catch (KeeperException.NoNodeException e) { throw new NoSuchElementException(ops.toString()); } catch (KeeperException.NodeExistsException e) { diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/LazySolrCluster.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/LazySolrCluster.java index 811a0b4e2e8..6baac9554d0 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/LazySolrCluster.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/LazySolrCluster.java @@ -265,7 +265,7 @@ public String config() { byte[] d = zkStateReader .getZkClient() - .getData(DocCollection.getCollectionPathRoot(coll.getName()), null, null, true); + .getData(DocCollection.getCollectionPathRoot(coll.getName()), null, null); if (d == null || d.length == 0) return null; Map m = (Map) Utils.fromJSON(d); confName = (String) m.get("configName"); diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/SimpleZkMap.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/SimpleZkMap.java index 39051da857c..5848831fd76 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/SimpleZkMap.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/SimpleZkMap.java @@ -54,7 +54,7 @@ public Resource get(String key) { @Override public void abortableForEach(BiFunction fun) { try { - recursiveRead("", zkStateReader.getZkClient().getChildren(basePath, null, true), fun); + recursiveRead("", zkStateReader.getZkClient().getChildren(basePath, null), fun); } catch (KeeperException | InterruptedException e) { throwZkExp(e); } @@ -84,8 +84,7 @@ public String name() { @Override public void get(Consumer consumer) throws SolrException { try { - byte[] data = - zkStateReader.getZkClient().getData(basePath + "/" + path, null, null, true); + byte[] data = zkStateReader.getZkClient().getData(basePath + "/" + path, null, null); if (data != null && data.length > 0) { consumer.read(new ByteArrayInputStream(data)); } else { @@ -109,7 +108,7 @@ private boolean recursiveRead( String relativePath = parent.isEmpty() ? child : parent + "/" + child; if (!fun.apply(relativePath, readZkNode(relativePath))) return false; List l1 = - zkStateReader.getZkClient().getChildren(basePath + "/" + relativePath, null, true); + zkStateReader.getZkClient().getChildren(basePath + "/" + relativePath, null); if (l1 != null && !l1.isEmpty()) { withKids.put(relativePath, l1); } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/BeforeReconnect.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/BeforeReconnect.java index 928e606c920..6ef59f3149f 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/BeforeReconnect.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/BeforeReconnect.java @@ -16,6 +16,17 @@ */ package org.apache.solr.common.cloud; -public interface BeforeReconnect { +import org.apache.curator.framework.CuratorFramework; +import org.apache.curator.framework.state.ConnectionState; +import org.apache.curator.framework.state.ConnectionStateListener; + +public interface BeforeReconnect extends ConnectionStateListener { public void command(); + + @Override + default void stateChanged(CuratorFramework client, ConnectionState newState) { + if (newState == ConnectionState.LOST) { + command(); + } + } } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ClusterProperties.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ClusterProperties.java index 84e5cf462e4..9373d8825ae 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ClusterProperties.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ClusterProperties.java @@ -97,7 +97,7 @@ public Map getClusterProperties() throws IOException { try { Map properties = (Map) - Utils.fromJSON(client.getData(ZkStateReader.CLUSTER_PROPS, null, new Stat(), true)); + Utils.fromJSON(client.getData(ZkStateReader.CLUSTER_PROPS, null, new Stat())); return convertCollectionDefaultsToNestedFormat(properties); } catch (KeeperException.NoNodeException e) { return Collections.emptyMap(); @@ -197,23 +197,21 @@ public void setClusterProperty(String propertyName, Object propertyValue) throws for (; ; ) { Stat s = new Stat(); try { - if (client.exists(ZkStateReader.CLUSTER_PROPS, true)) { + if (client.exists(ZkStateReader.CLUSTER_PROPS)) { @SuppressWarnings({"rawtypes"}) Map properties = - (Map) Utils.fromJSON(client.getData(ZkStateReader.CLUSTER_PROPS, null, s, true)); + (Map) Utils.fromJSON(client.getData(ZkStateReader.CLUSTER_PROPS, null, s)); if (propertyValue == null) { // Don't update ZK unless absolutely necessary. if (properties.get(propertyName) != null) { properties.remove(propertyName); - client.setData( - ZkStateReader.CLUSTER_PROPS, Utils.toJSON(properties), s.getVersion(), true); + client.setData(ZkStateReader.CLUSTER_PROPS, Utils.toJSON(properties), s.getVersion()); } } else { // Don't update ZK unless absolutely necessary. if (!propertyValue.equals(properties.get(propertyName))) { properties.put(propertyName, propertyValue); - client.setData( - ZkStateReader.CLUSTER_PROPS, Utils.toJSON(properties), s.getVersion(), true); + client.setData(ZkStateReader.CLUSTER_PROPS, Utils.toJSON(properties), s.getVersion()); } } } else { @@ -221,7 +219,7 @@ public void setClusterProperty(String propertyName, Object propertyValue) throws Map properties = new LinkedHashMap(); properties.put(propertyName, propertyValue); client.makePath( - ZkStateReader.CLUSTER_PROPS, Utils.toJSON(properties), CreateMode.PERSISTENT, true); + ZkStateReader.CLUSTER_PROPS, Utils.toJSON(properties), CreateMode.PERSISTENT); } } catch (KeeperException.BadVersionException | KeeperException.NodeExistsException e) { // race condition diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/CollectionProperties.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/CollectionProperties.java index e036ac76217..25b13086267 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/CollectionProperties.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/CollectionProperties.java @@ -67,8 +67,7 @@ public Map getCollectionProperties(String collection) throws IOE try { return (Map) Utils.fromJSON( - client.getData( - ZkStateReader.getCollectionPropsPath(collection), null, new Stat(), true)); + client.getData(ZkStateReader.getCollectionPropsPath(collection), null, new Stat())); } catch (KeeperException.NoNodeException e) { return Collections.emptyMap(); } catch (KeeperException | InterruptedException e) { @@ -94,25 +93,25 @@ public void setCollectionProperty(String collection, String propertyName, String while (true) { Stat s = new Stat(); try { - if (client.exists(znodePath, true)) { + if (client.exists(znodePath)) { Map properties = - (Map) Utils.fromJSON(client.getData(znodePath, null, s, true)); + (Map) Utils.fromJSON(client.getData(znodePath, null, s)); if (propertyValue == null) { if (properties.remove(propertyName) != null) { // Don't update ZK unless absolutely necessary. - client.setData(znodePath, Utils.toJSON(properties), s.getVersion(), true); + client.setData(znodePath, Utils.toJSON(properties), s.getVersion()); } } else { if (!propertyValue.equals( properties.put( propertyName, propertyValue))) { // Don't update ZK unless absolutely necessary. - client.setData(znodePath, Utils.toJSON(properties), s.getVersion(), true); + client.setData(znodePath, Utils.toJSON(properties), s.getVersion()); } } } else { Map properties = new LinkedHashMap<>(); properties.put(propertyName, propertyValue); - client.create(znodePath, Utils.toJSON(properties), CreateMode.PERSISTENT, true); + client.create(znodePath, Utils.toJSON(properties), CreateMode.PERSISTENT); } } catch (KeeperException.BadVersionException | KeeperException.NodeExistsException e) { // race condition diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ConnectionManager.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ConnectionManager.java deleted file mode 100644 index ba527b1eef8..00000000000 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ConnectionManager.java +++ /dev/null @@ -1,318 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.solr.common.cloud; - -import static org.apache.zookeeper.Watcher.Event.KeeperState.AuthFailed; -import static org.apache.zookeeper.Watcher.Event.KeeperState.Disconnected; -import static org.apache.zookeeper.Watcher.Event.KeeperState.Expired; - -import java.lang.invoke.MethodHandles; -import java.util.concurrent.TimeUnit; -import java.util.concurrent.TimeoutException; -import org.apache.solr.common.SolrException; -import org.apache.zookeeper.WatchedEvent; -import org.apache.zookeeper.Watcher; -import org.apache.zookeeper.Watcher.Event.KeeperState; -import org.apache.zookeeper.ZooKeeper; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -public class ConnectionManager implements Watcher { - private static final Logger log = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass()); - - private final String name; - - private volatile boolean connected = false; - - private final ZkClientConnectionStrategy connectionStrategy; - - private final String zkServerAddress; - - private final SolrZkClient client; - - private final OnReconnect onReconnect; - private final BeforeReconnect beforeReconnect; - - private volatile boolean isClosed = false; - - // Track the likely expired state - private static class LikelyExpiredState { - private static LikelyExpiredState NOT_EXPIRED = - new LikelyExpiredState(StateType.NOT_EXPIRED, 0); - private static LikelyExpiredState EXPIRED = new LikelyExpiredState(StateType.EXPIRED, 0); - - public enum StateType { - NOT_EXPIRED, // definitely not expired - EXPIRED, // definitely expired - TRACKING_TIME // not sure, tracking time of last disconnect - } - - private StateType stateType; - private long lastDisconnectTime; - - public LikelyExpiredState(StateType stateType, long lastDisconnectTime) { - this.stateType = stateType; - this.lastDisconnectTime = lastDisconnectTime; - } - - public boolean isLikelyExpired(long timeToExpire) { - return stateType == StateType.EXPIRED - || (stateType == StateType.TRACKING_TIME - && (System.nanoTime() - lastDisconnectTime - > TimeUnit.NANOSECONDS.convert(timeToExpire, TimeUnit.MILLISECONDS))); - } - } - - public interface IsClosed { - boolean isClosed(); - } - - private volatile LikelyExpiredState likelyExpiredState = LikelyExpiredState.EXPIRED; - - private IsClosed isClosedCheck; - - public ConnectionManager( - String name, - SolrZkClient client, - String zkServerAddress, - ZkClientConnectionStrategy strat, - OnReconnect onConnect, - BeforeReconnect beforeReconnect, - IsClosed isClosed) { - this.name = name; - this.client = client; - this.connectionStrategy = strat; - this.zkServerAddress = zkServerAddress; - this.onReconnect = onConnect; - this.beforeReconnect = beforeReconnect; - this.isClosedCheck = isClosed; - } - - private synchronized void connected() { - connected = true; - likelyExpiredState = LikelyExpiredState.NOT_EXPIRED; - notifyAll(); - } - - private synchronized void disconnected() { - connected = false; - // record the time we expired unless we are already likely expired - if (!likelyExpiredState.isLikelyExpired(0)) { - likelyExpiredState = - new LikelyExpiredState(LikelyExpiredState.StateType.TRACKING_TIME, System.nanoTime()); - } - notifyAll(); - } - - @Override - public void process(WatchedEvent event) { - if (event.getState() == AuthFailed - || event.getState() == Disconnected - || event.getState() == Expired) { - log.warn( - "Watcher {} name: {} got event {} path: {} type: {}", - this, - name, - event, - event.getPath(), - event.getType()); - } else { - if (log.isDebugEnabled()) { - log.debug( - "Watcher {} name: {} got event {} path: {} type: {}", - this, - name, - event, - event.getPath(), - event.getType()); - } - } - - if (isClosed()) { - log.debug("Client->ZooKeeper status change trigger but we are already closed"); - return; - } - - KeeperState state = event.getState(); - - if (state == KeeperState.SyncConnected) { - log.info("zkClient has connected"); - connected(); - connectionStrategy.connected(); - } else if (state == Expired) { - if (isClosed()) { - return; - } - // we don't call disconnected here, because we know we are expired - connected = false; - likelyExpiredState = LikelyExpiredState.EXPIRED; - - log.warn( - "Our previous ZooKeeper session was expired. Attempting to reconnect to recover relationship with ZooKeeper..."); - - if (beforeReconnect != null) { - try { - beforeReconnect.command(); - } catch (Exception e) { - log.warn("Exception running beforeReconnect command", e); - } - } - - do { - // This loop will break if a valid connection is made. If a connection is not made then it - // will repeat and try again to create a new connection. - try { - connectionStrategy.reconnect( - zkServerAddress, - client.getZkClientTimeout(), - this, - new ZkClientConnectionStrategy.ZkUpdate() { - @Override - public void update(ZooKeeper keeper) { - try { - waitForConnected(Long.MAX_VALUE); - - try { - client.updateKeeper(keeper); - } catch (InterruptedException e) { - closeKeeper(keeper); - Thread.currentThread().interrupt(); - // we must have been asked to stop - throw new RuntimeException(e); - } - - if (onReconnect != null) { - onReconnect.command(); - } - - } catch (Exception e1) { - // if there was a problem creating the new SolrZooKeeper - // or if we cannot run our reconnect command, close the keeper - // our retry loop will try to create one again - closeKeeper(keeper); - throw new RuntimeException(e1); - } - } - - private void closeKeeper(ZooKeeper keeper) { - try { - keeper.close(); - } catch (InterruptedException e) { - // Restore the interrupted status - Thread.currentThread().interrupt(); - log.error("", e); - throw new ZooKeeperException(SolrException.ErrorCode.SERVER_ERROR, "", e); - } - } - }); - - break; - - } catch (Exception e) { - log.error("Could not connect due to error, sleeping for 1s and trying again", e); - waitSleep(1000); - } - - } while (!isClosed()); - log.info("zkClient Connected: {}", connected); - } else if (state == KeeperState.Disconnected) { - log.warn("zkClient has disconnected"); - disconnected(); - connectionStrategy.disconnected(); - } else if (state == KeeperState.AuthFailed) { - log.warn("zkClient received AuthFailed"); - } - } - - public synchronized boolean isConnectedAndNotClosed() { - return !isClosed() && connected; - } - - public synchronized boolean isConnected() { - return connected; - } - - // we use a volatile rather than sync - // to avoid possible deadlock on shutdown - public void close() { - this.isClosed = true; - this.likelyExpiredState = LikelyExpiredState.EXPIRED; - } - - private boolean isClosed() { - return isClosed || isClosedCheck.isClosed(); - } - - public boolean isLikelyExpired() { - return isClosed() - || likelyExpiredState.isLikelyExpired((long) (client.getZkClientTimeout() * 0.90)); - } - - public synchronized void waitSleep(long waitFor) { - try { - wait(waitFor); - } catch (InterruptedException e) { - Thread.currentThread().interrupt(); - } - } - - /** - * Wait for an established zookeeper connection - * - * @param waitForConnection time to wait, in ms - */ - public synchronized void waitForConnected(long waitForConnection) throws TimeoutException { - log.info("Waiting up to {}ms for client to connect to ZooKeeper", waitForConnection); - long expire = - System.nanoTime() + TimeUnit.NANOSECONDS.convert(waitForConnection, TimeUnit.MILLISECONDS); - long left = 1; - while (!connected && left > 0) { - if (isClosed()) { - break; - } - try { - wait(500); - } catch (InterruptedException e) { - Thread.currentThread().interrupt(); - break; - } - left = expire - System.nanoTime(); - } - if (!connected) { - throw new TimeoutException( - "Could not connect to ZooKeeper " - + zkServerAddress - + " within " - + waitForConnection - + " ms"); - } - log.info("Client is connected to ZooKeeper"); - } - - public synchronized void waitForDisconnected(long timeout) - throws InterruptedException, TimeoutException { - long expire = System.nanoTime() + TimeUnit.NANOSECONDS.convert(timeout, TimeUnit.MILLISECONDS); - long left = timeout; - while (connected && left > 0) { - wait(left); - left = expire - System.nanoTime(); - } - if (connected) { - throw new TimeoutException("Did not disconnect"); - } - } -} diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultConnectionStrategy.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultConnectionStrategy.java deleted file mode 100644 index 42d8cbe31e9..00000000000 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultConnectionStrategy.java +++ /dev/null @@ -1,74 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.solr.common.cloud; - -import java.io.IOException; -import java.lang.invoke.MethodHandles; -import java.util.concurrent.TimeoutException; -import org.apache.solr.common.AlreadyClosedException; -import org.apache.zookeeper.Watcher; -import org.apache.zookeeper.ZooKeeper; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -/** TODO: improve backoff retry impl */ -public class DefaultConnectionStrategy extends ZkClientConnectionStrategy { - - private static final Logger log = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass()); - - @Override - public void connect(String serverAddress, int timeout, Watcher watcher, ZkUpdate updater) - throws IOException, InterruptedException, TimeoutException { - ZooKeeper zk = createZooKeeper(serverAddress, timeout, watcher); - boolean success = false; - try { - updater.update(zk); - success = true; - } finally { - if (!success) { - zk.close(); - } - } - } - - @Override - public void reconnect( - final String serverAddress, - final int zkClientTimeout, - final Watcher watcher, - final ZkUpdate updater) - throws IOException, InterruptedException, TimeoutException { - log.warn("Connection expired - starting a new one..."); - ZooKeeper zk = createZooKeeper(serverAddress, zkClientTimeout, watcher); - boolean success = false; - try { - updater.update(zk); - success = true; - log.info("Reconnected to ZooKeeper"); - } catch (AlreadyClosedException e) { - - } finally { - if (!success) { - try { - zk.close(); - } catch (InterruptedException e) { - Thread.currentThread().interrupt(); - } - } - } - } -} diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultZkACLProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultZkACLProvider.java index 5b43414da9d..2582d01a0b9 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultZkACLProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultZkACLProvider.java @@ -22,7 +22,15 @@ public class DefaultZkACLProvider implements ZkACLProvider { - private List globalACLsToAdd; + private volatile List globalACLsToAdd; + + public DefaultZkACLProvider() { + this(null); + } + + public DefaultZkACLProvider(List globalACLsToAdd) { + this.globalACLsToAdd = globalACLsToAdd; + } @Override public List getACLsToAdd(String zNodePath) { @@ -35,6 +43,28 @@ public List getACLsToAdd(String zNodePath) { return globalACLsToAdd; } + @Override + public List getAclForPath(String zNodePath) { + // In default (simple) implementation use the same set of ACLs for all znodes + if (globalACLsToAdd == null) { + synchronized (this) { + if (globalACLsToAdd == null) globalACLsToAdd = createGlobalACLsToAdd(); + } + } + return globalACLsToAdd; + } + + @Override + public List getDefaultAcl() { + // In default (simple) implementation use the same set of ACLs for all znodes + if (globalACLsToAdd == null) { + synchronized (this) { + if (globalACLsToAdd == null) globalACLsToAdd = createGlobalACLsToAdd(); + } + } + return globalACLsToAdd; + } + protected List createGlobalACLsToAdd() { return ZooDefs.Ids.OPEN_ACL_UNSAFE; } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultZkCredentialsProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultZkCredentialsProvider.java index e855052f6a6..cfdd2098f94 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultZkCredentialsProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DefaultZkCredentialsProvider.java @@ -17,19 +17,30 @@ package org.apache.solr.common.cloud; import java.util.ArrayList; -import java.util.Collection; +import java.util.List; +import org.apache.curator.framework.AuthInfo; public class DefaultZkCredentialsProvider implements ZkCredentialsProvider { - private Collection zkCredentials; + private volatile List zkCredentials; protected ZkCredentialsInjector zkCredentialsInjector; public DefaultZkCredentialsProvider() { - this(new DefaultZkCredentialsInjector()); + this(new DefaultZkCredentialsInjector(), null); + } + + public DefaultZkCredentialsProvider(List zkCredentials) { + this(new DefaultZkCredentialsInjector(), zkCredentials); } public DefaultZkCredentialsProvider(ZkCredentialsInjector zkCredentialsInjector) { + this(zkCredentialsInjector, null); + } + + public DefaultZkCredentialsProvider( + ZkCredentialsInjector zkCredentialsInjector, List zkCredentials) { this.zkCredentialsInjector = zkCredentialsInjector; + this.zkCredentials = zkCredentials; } @Override @@ -38,7 +49,7 @@ public void setZkCredentialsInjector(ZkCredentialsInjector zkCredentialsInjector } @Override - public Collection getCredentials() { + public List getCredentials() { if (zkCredentials == null) { synchronized (this) { if (zkCredentials == null) zkCredentials = createCredentials(); @@ -47,7 +58,7 @@ public Collection getCredentials() { return zkCredentials; } - protected Collection createCredentials() { + protected List createCredentials() { return new ArrayList<>(); } } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DigestZkACLProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DigestZkACLProvider.java index 314990ff278..6b6edaafc85 100755 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DigestZkACLProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DigestZkACLProvider.java @@ -39,7 +39,9 @@ public class DigestZkACLProvider extends SecurityAwareZkACLProvider { private static final Logger log = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass()); /** Called by reflective instantiation */ - public DigestZkACLProvider() {} + public DigestZkACLProvider() { + super(); + } public DigestZkACLProvider(ZkCredentialsInjector zkCredentialsInjector) { super(zkCredentialsInjector); diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DigestZkCredentialsProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DigestZkCredentialsProvider.java index cfe30286dc9..6eeefc6c106 100755 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DigestZkCredentialsProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/DigestZkCredentialsProvider.java @@ -19,8 +19,8 @@ import java.lang.invoke.MethodHandles; import java.nio.charset.StandardCharsets; import java.util.ArrayList; -import java.util.Collection; import java.util.List; +import org.apache.curator.framework.AuthInfo; import org.apache.solr.common.util.StrUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -34,15 +34,26 @@ public class DigestZkCredentialsProvider extends DefaultZkCredentialsProvider { private static final Logger log = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass()); /** Called by reflective instantiation */ - public DigestZkCredentialsProvider() {} + public DigestZkCredentialsProvider() { + super(); + } public DigestZkCredentialsProvider(ZkCredentialsInjector zkCredentialsInjector) { super(zkCredentialsInjector); } + public DigestZkCredentialsProvider(List zkCredentials) { + super(new DefaultZkCredentialsInjector(), zkCredentials); + } + + public DigestZkCredentialsProvider( + ZkCredentialsInjector zkCredentialsInjector, List zkCredentials) { + super(zkCredentialsInjector, zkCredentials); + } + @Override - protected Collection createCredentials() { - List result = new ArrayList<>(1); + protected List createCredentials() { + List result = new ArrayList<>(1); List zkCredentials = zkCredentialsInjector.getZkCredentials(); log.debug("createCredentials using zkCredentials: {}", zkCredentials); @@ -52,7 +63,7 @@ protected Collection createCredentials() { if (StrUtils.isNotNullOrEmpty(zkCredential.getUsername()) && StrUtils.isNotNullOrEmpty(zkCredential.getPassword())) { result.add( - new ZkCredentials( + new AuthInfo( "digest", (zkCredential.getUsername() + ":" + zkCredential.getPassword()) .getBytes(StandardCharsets.UTF_8))); diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/TestConnectionStrategy.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/OnDisconnect.java similarity index 54% rename from solr/test-framework/src/java/org/apache/solr/cloud/TestConnectionStrategy.java rename to solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/OnDisconnect.java index 88d94faaa85..f33013c5185 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/TestConnectionStrategy.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/OnDisconnect.java @@ -14,22 +14,19 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -package org.apache.solr.cloud; +package org.apache.solr.common.cloud; -import java.io.IOException; -import org.apache.solr.common.cloud.DefaultConnectionStrategy; -import org.apache.zookeeper.TestableZooKeeper; -import org.apache.zookeeper.Watcher; -import org.apache.zookeeper.ZooKeeper; +import org.apache.curator.framework.CuratorFramework; +import org.apache.curator.framework.state.ConnectionState; +import org.apache.curator.framework.state.ConnectionStateListener; + +public interface OnDisconnect extends ConnectionStateListener { + public void command(); -/** - * Connection strategy that creates instances of {@link TestableZooKeeper} instead of plain {@link - * ZooKeeper} objects. Useful for adding pause and disconnect events. - */ -public class TestConnectionStrategy extends DefaultConnectionStrategy { @Override - protected ZooKeeper newZooKeeperInstance( - String serverAddress, int zkClientTimeout, Watcher watcher) throws IOException { - return new TestableZooKeeper(serverAddress, zkClientTimeout, watcher); + default void stateChanged(CuratorFramework client, ConnectionState newState) { + if (newState == ConnectionState.LOST) { + command(); + } } } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/OnReconnect.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/OnReconnect.java index 19acfda4f6a..1863d797938 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/OnReconnect.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/OnReconnect.java @@ -16,7 +16,10 @@ */ package org.apache.solr.common.cloud; -import org.apache.zookeeper.KeeperException.SessionExpiredException; +import java.util.concurrent.atomic.AtomicBoolean; +import org.apache.curator.framework.CuratorFramework; +import org.apache.curator.framework.state.ConnectionState; +import org.apache.curator.framework.state.ConnectionStateListener; /** * Implementations are expected to implement a correct hashCode and equals method needed to uniquely @@ -25,6 +28,19 @@ * org.apache.solr.cloud.ZkController#removeOnReconnectListener(OnReconnect) when it no longer needs * to be notified of ZK reconnection events. */ -public interface OnReconnect { - void command() throws SessionExpiredException; +public interface OnReconnect extends ConnectionStateListener { + void command(); + + AtomicBoolean sessionEnded = new AtomicBoolean(false); + + @Override + default void stateChanged(CuratorFramework client, ConnectionState newState) { + if (ConnectionState.RECONNECTED.equals(newState)) { + if (sessionEnded.getAndSet(false)) { + command(); + } + } else if (ConnectionState.LOST == newState) { + sessionEnded.set(true); + } + } } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/PerReplicaStatesOps.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/PerReplicaStatesOps.java index dd0b14fd3e1..2194defcdde 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/PerReplicaStatesOps.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/PerReplicaStatesOps.java @@ -30,7 +30,6 @@ import org.apache.solr.common.util.CommonTestInjection; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.Op; import org.apache.zookeeper.data.Stat; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -60,12 +59,12 @@ public static PerReplicaStates fetch( assert CommonTestInjection.injectBreakpoint( PerReplicaStatesOps.class.getName() + "/beforePrsFetch"); if (current != null) { - Stat stat = zkClient.exists(current.path, null, true); + Stat stat = zkClient.exists(current.path, null); if (stat == null) return new PerReplicaStates(path, 0, Collections.emptyList()); if (current.cversion == stat.getCversion()) return current; // not modifiedZkStateReaderTest } Stat stat = new Stat(); - List children = zkClient.getChildren(path, null, stat, true); + List children = zkClient.getChildren(path, null, stat); return new PerReplicaStates(path, stat.getCversion(), Collections.unmodifiableList(children)); } catch (KeeperException.NoNodeException e) { throw new PrsZkNodeNotFoundException( @@ -104,20 +103,19 @@ private void persist( log.debug("Per-replica state being persisted for : '{}', ops: {}", znode, operations); } - List ops = new ArrayList<>(operations.size()); + List ops = new ArrayList<>(operations.size()); for (PerReplicaStates.Operation op : operations) { // the state of the replica is being updated String path = znode + "/" + op.state.asString; ops.add( op.typ == PerReplicaStates.Operation.Type.ADD - ? Op.create( - path, null, zkClient.getZkACLProvider().getACLsToAdd(path), CreateMode.PERSISTENT) - : Op.delete(path, -1)); + ? zkOp -> zkOp.create().withMode(CreateMode.PERSISTENT).forPath(path, null) + : zkOp -> zkOp.delete().withVersion(-1).forPath(path)); } try { - zkClient.multi(ops, true); + zkClient.multi(ops); } catch (KeeperException e) { - log.error("Multi-op exception: {}", zkClient.getChildren(znode, null, true)); + log.error("Multi-op exception: {}", zkClient.getChildren(znode, null)); throw e; } } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SaslZkACLProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SaslZkACLProvider.java index 2fbfbdd2ef8..ca2ba3bfe0a 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SaslZkACLProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SaslZkACLProvider.java @@ -17,7 +17,6 @@ package org.apache.solr.common.cloud; import java.util.Arrays; -import java.util.Collections; import java.util.List; import org.apache.zookeeper.ZooDefs; import org.apache.zookeeper.data.ACL; @@ -43,6 +42,7 @@ protected List createNonSecurityACLsToAdd() { @Override protected List createSecurityACLsToAdd() { - return Collections.singletonList(new ACL(ZooDefs.Perms.ALL, new Id("sasl", superUser))); + // Must be Arrays.asList(), Zookeeper does not allow for immutable list types for ACLs + return Arrays.asList(new ACL(ZooDefs.Perms.ALL, new Id("sasl", superUser))); } } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SecurityAwareZkACLProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SecurityAwareZkACLProvider.java index 1868f53308a..e0a42c79ebb 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SecurityAwareZkACLProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SecurityAwareZkACLProvider.java @@ -17,6 +17,7 @@ package org.apache.solr.common.cloud; import java.util.List; +import org.apache.curator.utils.ZKPaths; import org.apache.zookeeper.data.ACL; /** @@ -26,16 +27,52 @@ public abstract class SecurityAwareZkACLProvider implements ZkACLProvider { public static final String SECURITY_ZNODE_PATH = "/security"; - private List nonSecurityACLsToAdd; - private List securityACLsToAdd; + private volatile List nonSecurityACLsToAdd; + private volatile List securityACLsToAdd; + + private final String securityConfPath; + private final String securityZNodePath; + private final String securityZNodePathDir; + protected ZkCredentialsInjector zkCredentialsInjector; public SecurityAwareZkACLProvider() { this(new DefaultZkCredentialsInjector()); } + public SecurityAwareZkACLProvider(String chroot) { + this(new DefaultZkCredentialsInjector(), chroot); + } + public SecurityAwareZkACLProvider(ZkCredentialsInjector zkCredentialsInjector) { + this(zkCredentialsInjector, null); + } + + public SecurityAwareZkACLProvider(ZkCredentialsInjector zkCredentialsInjector, String chroot) { this.zkCredentialsInjector = zkCredentialsInjector; + if (chroot != null) { + this.securityConfPath = ZKPaths.makePath(chroot, ZkStateReader.SOLR_SECURITY_CONF_PATH); + this.securityZNodePath = ZKPaths.makePath(chroot, SECURITY_ZNODE_PATH); + this.securityZNodePathDir = securityZNodePath + "/"; + } else { + this.securityConfPath = null; + this.securityZNodePath = null; + this.securityZNodePathDir = null; + } + } + + public SecurityAwareZkACLProvider withChroot(String chroot) { + return new SecurityAwareZkACLProvider(chroot) { + @Override + protected List createNonSecurityACLsToAdd() { + return SecurityAwareZkACLProvider.this.createNonSecurityACLsToAdd(); + } + + @Override + protected List createSecurityACLsToAdd() { + return SecurityAwareZkACLProvider.this.createSecurityACLsToAdd(); + } + }; } @Override @@ -52,11 +89,16 @@ public final List getACLsToAdd(String zNodePath) { } } + @Override + public final List getDefaultAcl() { + return getNonSecurityACLsToAdd(); + } + protected boolean isSecurityZNodePath(String zNodePath) { return zNodePath != null - && (zNodePath.equals(ZkStateReader.SOLR_SECURITY_CONF_PATH) - || zNodePath.equals(SECURITY_ZNODE_PATH) - || zNodePath.startsWith(SECURITY_ZNODE_PATH + "/")); + && (zNodePath.equals(securityConfPath) + || zNodePath.equals(securityZNodePath) + || (securityZNodePathDir != null && zNodePath.startsWith(securityZNodePathDir))); } /** diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SecurityNodeWatcher.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SecurityNodeWatcher.java index 487fa6b427b..0a35bad37e5 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SecurityNodeWatcher.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SecurityNodeWatcher.java @@ -71,12 +71,9 @@ public void process(WatchedEvent event) { new SolrZkClient.NodeData(new Stat(), "{}".getBytes(StandardCharsets.UTF_8)); if (Event.EventType.NodeDeleted.equals(event.getType())) { // Node deleted, just recreate watch without attempting a read - SOLR-9679 - zkStateReader.getZkClient().exists(ZkStateReader.SOLR_SECURITY_CONF_PATH, this, true); + zkStateReader.getZkClient().exists(ZkStateReader.SOLR_SECURITY_CONF_PATH, this); } else { - data = - zkStateReader - .getZkClient() - .getNode(ZkStateReader.SOLR_SECURITY_CONF_PATH, this, true); + data = zkStateReader.getZkClient().getNode(ZkStateReader.SOLR_SECURITY_CONF_PATH, this); } try { callback.call(data); @@ -97,7 +94,7 @@ public void process(WatchedEvent event) { } void register() throws InterruptedException, KeeperException { - zkStateReader.getZkClient().exists(ZkStateReader.SOLR_SECURITY_CONF_PATH, this, true); + zkStateReader.getZkClient().exists(ZkStateReader.SOLR_SECURITY_CONF_PATH, this); securityData = getSecurityProps(true); } @@ -108,9 +105,9 @@ ZkStateReader.ConfigData getSecurityProps(boolean getFresh) { return new ZkStateReader.ConfigData(securityData.data, securityData.version); } try { - if (zkStateReader.getZkClient().exists(ZkStateReader.SOLR_SECURITY_CONF_PATH, true)) { + if (zkStateReader.getZkClient().exists(ZkStateReader.SOLR_SECURITY_CONF_PATH)) { SolrZkClient.NodeData d = - zkStateReader.getZkClient().getNode(ZkStateReader.SOLR_SECURITY_CONF_PATH, null, true); + zkStateReader.getZkClient().getNode(ZkStateReader.SOLR_SECURITY_CONF_PATH, null); return d != null && d.data.length > 0 ? new ZkStateReader.ConfigData( (Map) Utils.fromJSON(d.data), d.stat.getVersion()) diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SolrZkClient.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SolrZkClient.java index ddbd70d375f..c87be19e421 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SolrZkClient.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/SolrZkClient.java @@ -23,24 +23,37 @@ import java.nio.charset.StandardCharsets; import java.nio.file.Files; import java.nio.file.Path; +import java.util.Arrays; import java.util.List; import java.util.Locale; import java.util.concurrent.ExecutorService; import java.util.concurrent.RejectedExecutionException; import java.util.concurrent.TimeUnit; +import java.util.concurrent.TimeoutException; import java.util.concurrent.atomic.LongAdder; import java.util.function.BiFunction; import java.util.function.Function; import java.util.function.Predicate; import java.util.regex.Pattern; +import java.util.stream.Collectors; +import org.apache.curator.RetryPolicy; +import org.apache.curator.ensemble.fixed.FixedEnsembleProvider; +import org.apache.curator.framework.CuratorFramework; +import org.apache.curator.framework.CuratorFrameworkFactory; +import org.apache.curator.framework.api.ACLProvider; +import org.apache.curator.framework.api.transaction.CuratorOp; +import org.apache.curator.framework.api.transaction.CuratorTransactionResult; +import org.apache.curator.framework.api.transaction.TransactionOp; +import org.apache.curator.retry.ExponentialBackoffRetry; +import org.apache.curator.utils.ZKPaths; import org.apache.solr.client.solrj.SolrServerException; import org.apache.solr.client.solrj.impl.SolrZkClientTimeout; import org.apache.solr.common.MapWriter; import org.apache.solr.common.SolrException; import org.apache.solr.common.annotation.JsonProperty; -import org.apache.solr.common.cloud.ConnectionManager.IsClosed; import org.apache.solr.common.util.Compressor; import org.apache.solr.common.util.ExecutorUtil; +import org.apache.solr.common.util.IOUtils; import org.apache.solr.common.util.ObjectReleaseTracker; import org.apache.solr.common.util.ReflectMapWriter; import org.apache.solr.common.util.SolrNamedThreadFactory; @@ -48,17 +61,13 @@ import org.apache.solr.common.util.ZLibCompressor; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.KeeperException.NoAuthException; import org.apache.zookeeper.KeeperException.NoNodeException; -import org.apache.zookeeper.KeeperException.NodeExistsException; -import org.apache.zookeeper.Op; -import org.apache.zookeeper.OpResult; import org.apache.zookeeper.WatchedEvent; import org.apache.zookeeper.Watcher; -import org.apache.zookeeper.ZooDefs; import org.apache.zookeeper.ZooKeeper; import org.apache.zookeeper.data.ACL; import org.apache.zookeeper.data.Stat; +import org.apache.zookeeper.server.quorum.flexible.QuorumVerifier; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -73,11 +82,8 @@ public class SolrZkClient implements Closeable { private static final Logger log = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass()); - private ConnectionManager connManager; - - private volatile ZooKeeper keeper; - - private ZkCmdExecutor zkCmdExecutor; + private ExecutorService curatorSafeServiceExecutor; + CuratorFramework client; private final ZkMetrics metrics = new ZkMetrics(); @@ -89,14 +95,13 @@ public MapWriter getMetrics() { private final ExecutorService zkCallbackExecutor = ExecutorUtil.newMDCAwareCachedThreadPool(new SolrNamedThreadFactory("zkCallback")); - private final ExecutorService zkConnManagerCallbackExecutor = + private final ExecutorService zkConnectionListenerCallbackExecutor = ExecutorUtil.newMDCAwareSingleThreadExecutor( - new SolrNamedThreadFactory("zkConnectionManagerCallback")); + new SolrNamedThreadFactory("zkConnectionListenerCallback")); private volatile boolean isClosed = false; - private ZkClientConnectionStrategy zkClientConnectionStrategy; private int zkClientTimeout; - private ZkACLProvider zkACLProvider; + private ACLProvider aclProvider; private ZkCredentialsInjector zkCredentialsInjector; private String zkServerAddress; private SolrClassLoader solrClassLoader; @@ -112,10 +117,10 @@ public SolrZkClient(Builder builder) { builder.zkServerAddress, builder.zkClientTimeout, builder.zkClientConnectTimeout, - builder.connectionStrategy, + builder.zkCredentialsProvider, + builder.aclProvider, builder.onReconnect, builder.beforeReconnect, - builder.zkACLProvider, builder.higherLevelIsClosed, builder.compressor, builder.solrClassLoader); @@ -125,10 +130,10 @@ private SolrZkClient( String zkServerAddress, int zkClientTimeout, int clientConnectTimeout, - ZkClientConnectionStrategy strat, + ZkCredentialsProvider zkCredentialsProvider, + ACLProvider aclProvider, final OnReconnect onReconnect, BeforeReconnect beforeReconnect, - ZkACLProvider zkACLProvider, IsClosed higherLevelIsClosed, Compressor compressor, SolrClassLoader solrClassLoader) { @@ -138,82 +143,82 @@ private SolrZkClient( return; } this.zkServerAddress = zkServerAddress; - this.higherLevelIsClosed = higherLevelIsClosed; - if (strat == null) { - String connectionStrategy = System.getProperty("solr.zookeeper.connectionStrategy"); - strat = - ZkClientConnectionStrategy.forName(connectionStrategy, new DefaultConnectionStrategy()); + String chroot, zkHost; + int chrootIndex = zkServerAddress.indexOf('/'); + if (chrootIndex == -1) { + zkHost = zkServerAddress; + chroot = null; + } else if (chrootIndex == zkServerAddress.length() - 1) { + zkHost = zkServerAddress.substring(0, zkServerAddress.length() - 1); + chroot = null; + } else { + zkHost = zkServerAddress.substring(0, chrootIndex); + chroot = zkServerAddress.substring(chrootIndex + 1); } - this.zkClientConnectionStrategy = strat; - this.solrClassLoader = solrClassLoader; - if (!strat.hasZkCredentialsToAddAutomatically()) { + this.higherLevelIsClosed = higherLevelIsClosed; + + if (zkCredentialsProvider == null) { zkCredentialsInjector = createZkCredentialsInjector(); - ZkCredentialsProvider zkCredentialsToAddAutomatically = - createZkCredentialsToAddAutomatically(); - strat.setZkCredentialsToAddAutomatically(zkCredentialsToAddAutomatically); + zkCredentialsProvider = createZkCredentialsToAddAutomatically(); + } + if (aclProvider == null) { + aclProvider = createACLProvider(); + } + if (chroot != null && aclProvider instanceof SecurityAwareZkACLProvider) { + this.aclProvider = ((SecurityAwareZkACLProvider) aclProvider).withChroot(chroot); + } else { + this.aclProvider = aclProvider; } this.zkClientTimeout = zkClientTimeout; - // we must retry at least as long as the session timeout - zkCmdExecutor = new ZkCmdExecutor(zkClientTimeout, SolrZkClient.this::isClosed); - connManager = - new ConnectionManager( - "ZooKeeperConnection Watcher:" + zkServerAddress, - this, - zkServerAddress, - strat, - onReconnect, - beforeReconnect, - SolrZkClient.this::isClosed); - try { - strat.connect( - zkServerAddress, - zkClientTimeout, - wrapWatcher(connManager), - zooKeeper -> { - ZooKeeper oldKeeper = keeper; - keeper = zooKeeper; - try { - closeKeeper(oldKeeper); - } finally { - if (isClosed) { - // we may have been closed - closeKeeper(SolrZkClient.this.keeper); - } - } - }); - } catch (Exception e) { - connManager.close(); - if (keeper != null) { - try { - keeper.close(); - } catch (InterruptedException e1) { - Thread.currentThread().interrupt(); - } - } - throw new SolrException(SolrException.ErrorCode.SERVER_ERROR, e); + curatorSafeServiceExecutor = + ExecutorUtil.newMDCAwareSingleThreadExecutor( + new SolrNamedThreadFactory("curator-safeService")); + + RetryPolicy retryPolicy = new ExponentialBackoffRetry(1000, 3); + var clientBuilder = + CuratorFrameworkFactory.builder() + .ensembleProvider(new FixedEnsembleProvider(zkHost)) + .namespace(chroot) + .sessionTimeoutMs(zkClientTimeout) + .connectionTimeoutMs(clientConnectTimeout) + .aclProvider(this.aclProvider) + .authorization(zkCredentialsProvider.getCredentials()) + .retryPolicy(retryPolicy) + .runSafeService(curatorSafeServiceExecutor); + + client = clientBuilder.build(); + if (onReconnect != null) { + client + .getConnectionStateListenable() + .addListener(onReconnect, zkConnectionListenerCallbackExecutor); } - + if (beforeReconnect != null) { + client + .getConnectionStateListenable() + .addListener(beforeReconnect, zkConnectionListenerCallbackExecutor); + } + client.start(); try { - connManager.waitForConnected(clientConnectTimeout); + if (!client.blockUntilConnected(clientConnectTimeout, TimeUnit.MILLISECONDS)) { + throw new TimeoutException( + String.format( + Locale.ROOT, + "Timeout while waiting for Zookeeper Client to connect: %d ms", + clientConnectTimeout)); + } + ; } catch (Exception e) { - connManager.close(); - try { - keeper.close(); - } catch (InterruptedException e1) { + if (e instanceof InterruptedException) { Thread.currentThread().interrupt(); } - zkConnManagerCallbackExecutor.shutdown(); + client.close(); throw new SolrException(SolrException.ErrorCode.SERVER_ERROR, e); } + assert ObjectReleaseTracker.track(this); - if (zkACLProvider == null) { - this.zkACLProvider = createZkACLProvider(); - } else { - this.zkACLProvider = zkACLProvider; - } if (compressor == null) { this.compressor = new ZLibCompressor(); @@ -222,12 +227,8 @@ private SolrZkClient( } } - public ConnectionManager getConnectionManager() { - return connManager; - } - - public ZkClientConnectionStrategy getZkClientConnectionStrategy() { - return zkClientConnectionStrategy; + public CuratorFramework getCuratorFramework() { + return client; } public static final String ZK_CRED_PROVIDER_CLASS_NAME_VM_PARAM_NAME = "zkCredentialsProvider"; @@ -261,7 +262,7 @@ protected ZkCredentialsProvider createZkCredentialsToAddAutomatically() { public static final String ZK_ACL_PROVIDER_CLASS_NAME_VM_PARAM_NAME = "zkACLProvider"; - protected ZkACLProvider createZkACLProvider() { + protected ACLProvider createACLProvider() { String zkACLProviderClassName = System.getProperty(ZK_ACL_PROVIDER_CLASS_NAME_VM_PARAM_NAME); if (StrUtils.isNotNullOrEmpty(zkACLProviderClassName)) { try { @@ -324,29 +325,21 @@ protected ZkCredentialsInjector createZkCredentialsInjector() { /** Returns true if client is connected */ public boolean isConnected() { - return keeper != null && keeper.getState() == ZooKeeper.States.CONNECTED; + return client.getZookeeperClient().isConnected(); } - public void delete(final String path, final int version, boolean retryOnConnLoss) + public void delete(final String path, final int version) throws InterruptedException, KeeperException { - if (retryOnConnLoss) { - zkCmdExecutor.retryOperation( - () -> { - keeper.delete(path, version); - return null; - }); - } else { - keeper.delete(path, version); - } + runWithCorrectThrows( + "deleting znode", () -> client.delete().withVersion(version).forPath(path)); metrics.deletes.increment(); } /** * Wraps the watcher so that it doesn't fire off ZK's event queue. In order to guarantee that a * watch object will only be triggered once for a given notification, users need to wrap their - * watcher using this method before calling {@link #exists(String, org.apache.zookeeper.Watcher, - * boolean)} or {@link #getData(String, org.apache.zookeeper.Watcher, - * org.apache.zookeeper.data.Stat, boolean)}. + * watcher using this method before calling {@link #exists(String, Watcher)} or {@link + * #getData(String, Watcher, Stat)}. */ public Watcher wrapWatcher(final Watcher watcher) { if (watcher == null || watcher instanceof ProcessWatchWithExecutor) return watcher; @@ -367,40 +360,31 @@ public Watcher wrapWatcher(final Watcher watcher) { * @throws InterruptedException If the server transaction is interrupted. * @throws IllegalArgumentException if an invalid path is specified */ - public Stat exists(final String path, final Watcher watcher, boolean retryOnConnLoss) + public Stat exists(final String path, final Watcher watcher) throws KeeperException, InterruptedException { - Stat result = null; - if (retryOnConnLoss) { - result = zkCmdExecutor.retryOperation(() -> keeper.exists(path, wrapWatcher(watcher))); - } else { - result = keeper.exists(path, wrapWatcher(watcher)); - } + Stat result = + runWithCorrectThrows( + "checking exists", + () -> client.checkExists().usingWatcher(wrapWatcher(watcher)).forPath(path)); metrics.existsChecks.increment(); return result; } /** Returns true if path exists */ - public Boolean exists(final String path, boolean retryOnConnLoss) - throws KeeperException, InterruptedException { - Boolean result = null; - if (retryOnConnLoss) { - result = zkCmdExecutor.retryOperation(() -> keeper.exists(path, null) != null); - } else { - result = keeper.exists(path, null) != null; - } + public Boolean exists(final String path) throws KeeperException, InterruptedException { + Boolean result = + runWithCorrectThrows("checking exists", () -> client.checkExists().forPath(path) != null); metrics.existsChecks.increment(); return result; } /** Returns children of the node at the path */ - public List getChildren(final String path, final Watcher watcher, boolean retryOnConnLoss) + public List getChildren(final String path, final Watcher watcher) throws KeeperException, InterruptedException { - List result = null; - if (retryOnConnLoss) { - return zkCmdExecutor.retryOperation(() -> keeper.getChildren(path, wrapWatcher(watcher))); - } else { - result = keeper.getChildren(path, wrapWatcher(watcher)); - } + List result = + runWithCorrectThrows( + "getting children", + () -> client.getChildren().usingWatcher(wrapWatcher(watcher)).forPath(path)); metrics.childFetches.increment(); if (result != null) { @@ -410,16 +394,18 @@ public List getChildren(final String path, final Watcher watcher, boolea } /** Returns children of the node at the path */ - public List getChildren( - final String path, final Watcher watcher, Stat stat, boolean retryOnConnLoss) + public List getChildren(final String path, final Watcher watcher, Stat stat) throws KeeperException, InterruptedException { - List result = null; - if (retryOnConnLoss) { - result = - zkCmdExecutor.retryOperation(() -> keeper.getChildren(path, wrapWatcher(watcher), stat)); - } else { - result = keeper.getChildren(path, wrapWatcher(watcher), stat); - } + List result = + runWithCorrectThrows( + "getting children", + () -> + client + .getChildren() + .storingStatIn(stat) + .usingWatcher(wrapWatcher(watcher)) + .forPath(path)); + metrics.childFetches.increment(); if (result != null) { metrics.cumulativeChildrenFetched.add(result.size()); @@ -428,15 +414,17 @@ public List getChildren( } /** Returns node's data */ - public byte[] getData( - final String path, final Watcher watcher, final Stat stat, boolean retryOnConnLoss) + public byte[] getData(final String path, final Watcher watcher, final Stat stat) throws KeeperException, InterruptedException { - byte[] result = null; - if (retryOnConnLoss) { - result = zkCmdExecutor.retryOperation(() -> keeper.getData(path, wrapWatcher(watcher), stat)); - } else { - result = keeper.getData(path, wrapWatcher(watcher), stat); - } + byte[] result = + runWithCorrectThrows( + "getting data", + () -> + client + .getData() + .storingStatIn(stat) + .usingWatcher(wrapWatcher(watcher)) + .forPath(path)); if (compressor.isCompressedBytes(result)) { log.debug("Zookeeper data at path {} is compressed", path); try { @@ -456,22 +444,18 @@ public byte[] getData( return result; } - public NodeData getNode(final String path, Watcher watcher, boolean retryOnConnLoss) + public NodeData getNode(final String path, Watcher watcher) throws KeeperException, InterruptedException { Stat stat = new Stat(); - return new NodeData(stat, getData(path, watcher, stat, retryOnConnLoss)); + return new NodeData(stat, getData(path, watcher, stat)); } /** Returns node's state */ - public Stat setData( - final String path, final byte data[], final int version, boolean retryOnConnLoss) + public Stat setData(final String path, final byte data[], final int version) throws KeeperException, InterruptedException { - Stat result = null; - if (retryOnConnLoss) { - result = zkCmdExecutor.retryOperation(() -> keeper.setData(path, data, version)); - } else { - result = keeper.setData(path, data, version); - } + Stat result = + runWithCorrectThrows( + "setting data", () -> client.setData().withVersion(version).forPath(path, data)); metrics.writes.increment(); if (data != null) { metrics.bytesWritten.add(data.length); @@ -491,14 +475,14 @@ public void atomicUpdate(String path, BiFunction editor) byte[] zkData = null; Stat s = new Stat(); try { - if (exists(path, true)) { - zkData = getData(path, null, s, true); + if (exists(path)) { + zkData = getData(path, null, s); modified = editor.apply(s, zkData); if (modified == null) { // no change , no need to persist return; } - setData(path, modified, s.getVersion(), true); + setData(path, modified, s.getVersion()); break; } else { modified = editor.apply(s, null); @@ -506,7 +490,7 @@ public void atomicUpdate(String path, BiFunction editor) // no change , no need to persist return; } - create(path, modified, CreateMode.PERSISTENT, true); + create(path, modified, CreateMode.PERSISTENT); break; } } catch (KeeperException.BadVersionException | KeeperException.NodeExistsException e) { @@ -516,18 +500,11 @@ public void atomicUpdate(String path, BiFunction editor) } /** Returns path of created node */ - public String create( - final String path, final byte[] data, final CreateMode createMode, boolean retryOnConnLoss) + public String create(final String path, final byte[] data, final CreateMode createMode) throws KeeperException, InterruptedException { - String result = null; - if (retryOnConnLoss) { - result = - zkCmdExecutor.retryOperation( - () -> keeper.create(path, data, zkACLProvider.getACLsToAdd(path), createMode)); - } else { - List acls = zkACLProvider.getACLsToAdd(path); - result = keeper.create(path, data, acls, createMode); - } + String result = + runWithCorrectThrows( + "creating znode", () -> client.create().withMode(createMode).forPath(path, data)); metrics.writes.increment(); if (data != null) { metrics.bytesWritten.add(data.length); @@ -541,36 +518,28 @@ public String create( *

e.g. If path=/solr/group/node and none of the nodes, solr, group, node exist, * each will be created. */ - public void makePath(String path, boolean retryOnConnLoss) - throws KeeperException, InterruptedException { - makePath(path, null, CreateMode.PERSISTENT, retryOnConnLoss); + public void makePath(String path) throws KeeperException, InterruptedException { + makePath(path, null, CreateMode.PERSISTENT); } - public void makePath(String path, boolean failOnExists, boolean retryOnConnLoss) + public void makePath(String path, boolean failOnExists) throws KeeperException, InterruptedException { - makePath(path, null, CreateMode.PERSISTENT, null, failOnExists, retryOnConnLoss, 0); + makePath(path, null, CreateMode.PERSISTENT, null, failOnExists, 0); } - public void makePath(String path, Path data, boolean failOnExists, boolean retryOnConnLoss) + public void makePath(String path, Path data, boolean failOnExists) throws IOException, KeeperException, InterruptedException { - makePath( - path, - Files.readAllBytes(data), - CreateMode.PERSISTENT, - null, - failOnExists, - retryOnConnLoss, - 0); + makePath(path, Files.readAllBytes(data), CreateMode.PERSISTENT, null, failOnExists, 0); } - public void makePath(String path, Path data, boolean retryOnConnLoss) + public void makePath(String path, Path data) throws IOException, KeeperException, InterruptedException { - makePath(path, Files.readAllBytes(data), retryOnConnLoss); + makePath(path, Files.readAllBytes(data)); } - public void makePath(String path, CreateMode createMode, boolean retryOnConnLoss) + public void makePath(String path, CreateMode createMode) throws KeeperException, InterruptedException { - makePath(path, null, createMode, retryOnConnLoss); + makePath(path, null, createMode); } /** @@ -578,9 +547,8 @@ public void makePath(String path, CreateMode createMode, boolean retryOnConnLoss * * @param data to set on the last zkNode */ - public void makePath(String path, byte[] data, boolean retryOnConnLoss) - throws KeeperException, InterruptedException { - makePath(path, data, CreateMode.PERSISTENT, retryOnConnLoss); + public void makePath(String path, byte[] data) throws KeeperException, InterruptedException { + makePath(path, data, CreateMode.PERSISTENT); } /** @@ -591,9 +559,14 @@ public void makePath(String path, byte[] data, boolean retryOnConnLoss) * * @param data to set on the last zkNode */ - public void makePath(String path, byte[] data, CreateMode createMode, boolean retryOnConnLoss) + public void makePath(String path, byte[] data, CreateMode createMode) + throws KeeperException, InterruptedException { + makePath(path, data, createMode, null); + } + + public void makePath(String zkPath, CreateMode createMode, Watcher watcher) throws KeeperException, InterruptedException { - makePath(path, data, createMode, null, retryOnConnLoss); + makePath(zkPath, null, createMode, watcher, true, 0); } /** @@ -604,10 +577,9 @@ public void makePath(String path, byte[] data, CreateMode createMode, boolean re * * @param data to set on the last zkNode */ - public void makePath( - String path, byte[] data, CreateMode createMode, Watcher watcher, boolean retryOnConnLoss) + public void makePath(String path, byte[] data, CreateMode createMode, Watcher watcher) throws KeeperException, InterruptedException { - makePath(path, data, createMode, watcher, true, retryOnConnLoss, 0); + makePath(path, data, createMode, watcher, true, 0); } /** @@ -619,14 +591,9 @@ public void makePath( * @param data to set on the last zkNode */ public void makePath( - String path, - byte[] data, - CreateMode createMode, - Watcher watcher, - boolean failOnExists, - boolean retryOnConnLoss) + String path, byte[] data, CreateMode createMode, Watcher watcher, boolean failOnExists) throws KeeperException, InterruptedException { - makePath(path, data, createMode, watcher, failOnExists, retryOnConnLoss, 0); + makePath(path, data, createMode, watcher, failOnExists, 0); } /** @@ -637,9 +604,6 @@ public void makePath( * *

skipPathParts will force the call to fail if the first skipPathParts do not exist already. * - *

Note: retryOnConnLoss is only respected for the final node - nodes before that are always - * retried on connection loss. - * *

Note: if failOnExists == false then we will always overwrite the existing data with the * given data */ @@ -649,86 +613,130 @@ public void makePath( CreateMode createMode, Watcher watcher, boolean failOnExists, - boolean retryOnConnLoss, int skipPathParts) throws KeeperException, InterruptedException { log.debug("makePath: {}", path); + var createBuilder = client.create(); + if (!failOnExists) { + createBuilder.orSetData(); + } metrics.writes.increment(); if (data != null) { metrics.bytesWritten.add(data.length); } - boolean retry = true; if (path.startsWith("/")) { - path = path.substring(1, path.length()); + path = path.substring(1); } - String[] paths = path.split("/"); - StringBuilder sbPath = new StringBuilder(); - for (int i = 0; i < paths.length; i++) { - String pathPiece = paths[i]; - sbPath.append("/").append(pathPiece); - if (i < skipPathParts) { - continue; + if (skipPathParts > 0) { + String[] paths = path.split("/"); + StringBuilder sbPath = new StringBuilder(); + for (int i = 0; i < paths.length; i++) { + if (i == skipPathParts) { + break; + } + String pathPiece = paths[i]; + sbPath.append("/").append(pathPiece); } - byte[] bytes = null; - final String currentPath = sbPath.toString(); - - CreateMode mode = CreateMode.PERSISTENT; - if (i == paths.length - 1) { - mode = createMode; - bytes = data; - if (!retryOnConnLoss) retry = false; + String skipPathPartsPath = sbPath.toString(); + final String finalSkipPathPartsPath; + if (!skipPathPartsPath.startsWith("/")) { + finalSkipPathPartsPath = "/" + skipPathPartsPath; + } else { + finalSkipPathPartsPath = skipPathPartsPath; } - try { - if (retry) { - final CreateMode finalMode = mode; - final byte[] finalBytes = bytes; - zkCmdExecutor.retryOperation( - () -> { - keeper.create( - currentPath, finalBytes, zkACLProvider.getACLsToAdd(currentPath), finalMode); - return null; - }); - } else { - keeper.create(currentPath, bytes, zkACLProvider.getACLsToAdd(currentPath), mode); - } - } catch (NoAuthException e) { - // in auth cases, we may not have permission for an earlier part of a path, which is fine - if (i == paths.length - 1 || !exists(currentPath, retryOnConnLoss)) { + Stat exists = + runWithCorrectThrows( + "checking skipPathParts exists", + () -> client.checkExists().forPath(finalSkipPathPartsPath)); + if (exists == null) { + throw new KeeperException.NoNodeException(finalSkipPathPartsPath + " didn't already exist"); + } + } - throw e; - } - } catch (NodeExistsException e) { - if (log.isDebugEnabled()) { - log.debug("Node exists: {}", e.getPath()); - } + final String finalPath; + if (!path.startsWith("/")) { + finalPath = "/" + path; + } else { + finalPath = path; + } + runWithCorrectThrows( + "making path", + () -> { + createBuilder.creatingParentsIfNeeded().withMode(createMode).forPath(finalPath, data); + return client.checkExists().usingWatcher(wrapWatcher(watcher)).forPath(finalPath); + }); + } - if (!failOnExists && i == paths.length - 1) { - // TODO: version ? for now, don't worry about race - setData(currentPath, data, -1, retryOnConnLoss); - // set new watch - exists(currentPath, watcher, retryOnConnLoss); - return; - } + /** + * Create a node if it does not exist + * + * @param path the path at which to create the znode + */ + public void ensureExists(final String path) throws KeeperException, InterruptedException { + ensureExists(path, null); + } - // ignore unless it's the last node in the path - if (i == paths.length - 1) { - throw e; - } - } - } + /** + * Create a node if it does not exist + * + * @param path the path at which to create the znode + * @param data the optional data to set on the znode + */ + public void ensureExists(final String path, final byte[] data) + throws KeeperException, InterruptedException { + ensureExists(path, data, CreateMode.PERSISTENT); } - public void makePath( - String zkPath, CreateMode createMode, Watcher watcher, boolean retryOnConnLoss) + /** + * Create a node if it does not exist + * + * @param path the path at which to create the znode + * @param data the optional data to set on the znode + * @param createMode the mode with which to create the znode + */ + public void ensureExists(final String path, final byte[] data, CreateMode createMode) throws KeeperException, InterruptedException { - makePath(zkPath, null, createMode, watcher, retryOnConnLoss); + ensureExists(path, data, createMode, 0); } - /** Write data to ZooKeeper. */ - public Stat setData(String path, byte[] data, boolean retryOnConnLoss) + /** + * Create a node if it does not exist + * + * @param path the path at which to create the znode + * @param data the optional data to set on the znode + * @param createMode the mode with which to create the znode + * @param skipPathParts how many path elements to skip + */ + public void ensureExists( + final String path, final byte[] data, CreateMode createMode, int skipPathParts) throws KeeperException, InterruptedException { - return setData(path, data, -1, retryOnConnLoss); + if (exists(path)) { + return; + } + try { + if (skipPathParts > 0) { + int endingIndex = 0; + for (int i = 0; i < skipPathParts && endingIndex >= 0; i++) { + endingIndex = path.indexOf('/', endingIndex + 1); + } + if (endingIndex == -1 || endingIndex == path.length() - 1) { + throw new KeeperException.NoNodeException(path); + } + String startingPath = path.substring(0, endingIndex); + if (!exists(startingPath)) { + throw new KeeperException.NoNodeException(startingPath); + } + } + makePath(path, data, createMode, null, true, skipPathParts); + } catch (KeeperException.NodeExistsException ignored) { + // it's okay if another beats us creating the node + } + } + + /** Write data to ZooKeeper. */ + public Stat setData(String path, byte[] data) throws KeeperException, InterruptedException { + return setData(path, data, -1); } /** @@ -737,22 +745,47 @@ public Stat setData(String path, byte[] data, boolean retryOnConnLoss) * @param path path to upload file to e.g. /solr/conf/solrconfig.xml * @param data a filepath to read data from */ - public Stat setData(String path, Path data, boolean retryOnConnLoss) + public Stat setData(String path, Path data) throws IOException, KeeperException, InterruptedException { if (log.isDebugEnabled()) { log.debug("Write to ZooKeeper: {} to {}", data.toAbsolutePath(), path); } - return setData(path, Files.readAllBytes(data), retryOnConnLoss); + return setData(path, Files.readAllBytes(data)); } - public List multi(final Iterable ops, boolean retryOnConnLoss) - throws InterruptedException, KeeperException { - List result = null; - if (retryOnConnLoss) { - result = zkCmdExecutor.retryOperation(() -> keeper.multi(ops)); - } else { - result = keeper.multi(ops); + @FunctionalInterface + public interface CuratorOpBuilder { + CuratorOp build(TransactionOp startingOp) throws Exception; + + default CuratorOp buildWithoutThrows(TransactionOp startingOp) { + try { + return build(startingOp); + } catch (RuntimeException e) { + throw e; + } catch (Exception e) { + throw new RuntimeException(e); + } } + } + + public List multi(CuratorOpBuilder... ops) + throws InterruptedException, KeeperException { + return multi(Arrays.asList(ops)); + } + + public List multi(final List ops) + throws InterruptedException, KeeperException { + List result = + runWithCorrectThrows( + "executing multi-transaction", + () -> + client + .transaction() + .forOperations( + ops.stream() + .map(op -> op.buildWithoutThrows(client.transactionOp())) + .collect(Collectors.toList()))); + metrics.multiOps.increment(); if (result != null) { metrics.cumulativeMultiOps.add(result.size()); @@ -763,14 +796,12 @@ public List multi(final Iterable ops, boolean retryOnConnLoss) /** Fills string with printout of current ZooKeeper layout. */ public void printLayout(String path, int indent, StringBuilder string) throws KeeperException, InterruptedException { - byte[] data = getData(path, null, null, true); - List children = getChildren(path, null, true); + byte[] data = getData(path, null, null); + List children = getChildren(path, null); StringBuilder dent = new StringBuilder(); - for (int i = 0; i < indent; i++) { - dent.append(" "); - } + dent.append(" ".repeat(Math.max(0, indent))); string.append(dent).append(path).append(" (").append(children.size()).append(")").append(NEWL); - if (data != null) { + if (data != null && data.length > 0) { String dataString = new String(data, StandardCharsets.UTF_8); if (!path.endsWith(".txt") && !path.endsWith(".xml")) { string @@ -809,8 +840,8 @@ public void close() { try { closeCallbackExecutor(); } finally { - connManager.close(); - closeKeeper(keeper); + IOUtils.closeQuietly(client); + ExecutorUtil.shutdownNowAndAwaitTermination(curatorSafeServiceExecutor); } assert ObjectReleaseTracker.release(this); } @@ -819,32 +850,28 @@ public boolean isClosed() { return isClosed || (higherLevelIsClosed != null && higherLevelIsClosed.isClosed()); } - /** Allows package private classes to update volatile ZooKeeper. */ - void updateKeeper(ZooKeeper keeper) throws InterruptedException { - ZooKeeper oldKeeper = this.keeper; - this.keeper = keeper; - if (oldKeeper != null) { - oldKeeper.close(); - } - // we might have been closed already - if (isClosed) this.keeper.close(); + public ZooKeeper getZooKeeper() throws Exception { + return client.getZookeeperClient().getZooKeeper(); } - public ZooKeeper getZooKeeper() { - return keeper; + public long getZkSessionId() { + if (isConnected()) { + try { + return client.getZookeeperClient().getZooKeeper().getSessionId(); + } catch (Exception ignored) { + } + } + return -1; } - private void closeKeeper(ZooKeeper keeper) { - if (keeper != null) { + public int getZkSessionTimeout() { + if (isConnected()) { try { - keeper.close(); - } catch (InterruptedException e) { - // Restore the interrupted status - Thread.currentThread().interrupt(); - log.error("", e); - throw new ZooKeeperException(SolrException.ErrorCode.SERVER_ERROR, "", e); + return client.getZookeeperClient().getZooKeeper().getSessionTimeout(); + } catch (Exception ignored) { } } + return 0; } private void closeCallbackExecutor() { @@ -855,7 +882,7 @@ private void closeCallbackExecutor() { } try { - ExecutorUtil.shutdownAndAwaitTermination(zkConnManagerCallbackExecutor); + ExecutorUtil.shutdownAndAwaitTermination(zkConnectionListenerCallbackExecutor); } catch (Exception e) { log.error("Error shutting down zkConnManagerCallbackExecutor", e); } @@ -888,6 +915,20 @@ public String getZkServerAddress() { return zkServerAddress; } + /** + * @return the address of the zookeeper cluster + */ + public String getChroot() { + return client.getNamespace(); + } + + /** + * @return the address of the zookeeper cluster + */ + public String getAbsolutePath(String path) { + return ZKPaths.fixForNamespace(getChroot(), path); + } + /** * Gets the raw config node /zookeeper/config as returned by server. Response may look like * @@ -902,37 +943,25 @@ public String getZkServerAddress() { * string */ public String getConfig() { - try { - Stat stat = new Stat(); - keeper.sync(ZooDefs.CONFIG_NODE, null, null); - byte[] data = keeper.getConfig(false, stat); - if (data == null || data.length == 0) { - return ""; - } - return new String(data, StandardCharsets.UTF_8); - } catch (NoNodeException nne) { + QuorumVerifier currentConfig = client.getCurrentConfig(); + if (currentConfig == null) { log.debug("Zookeeper does not have the /zookeeper/config znode, assuming old ZK version"); return ""; - } catch (KeeperException | InterruptedException ex) { - throw new SolrException( - SolrException.ErrorCode.SERVER_ERROR, "Failed to get config from zookeeper", ex); + } else { + return currentConfig.toString(); } } - public ZkACLProvider getZkACLProvider() { - return zkACLProvider; + public ACLProvider getZkACLProvider() { + return aclProvider; } /** * @return the ACLs on a single node in ZooKeeper. */ - public List getACL(String path, Stat stat, boolean retryOnConnLoss) - throws KeeperException, InterruptedException { - if (retryOnConnLoss) { - return zkCmdExecutor.retryOperation(() -> keeper.getACL(path, stat)); - } else { - return keeper.getACL(path, stat); - } + public List getACL(String path, Stat stat) throws KeeperException, InterruptedException { + return runWithCorrectThrows( + "getting acls", () -> client.getACL().storingStatIn(stat).forPath(path)); } /** @@ -940,16 +969,11 @@ public List getACL(String path, Stat stat, boolean retryOnConnLoss) * * @param path path to set ACL on e.g. /solr/conf/solrconfig.xml * @param acls a list of {@link ACL}s to be applied - * @param retryOnConnLoss true if the command should be retried on connection loss * @return the stat of the node */ - public Stat setACL(String path, List acls, boolean retryOnConnLoss) - throws InterruptedException, KeeperException { - if (retryOnConnLoss) { - return zkCmdExecutor.retryOperation(() -> keeper.setACL(path, acls, -1)); - } else { - return keeper.setACL(path, acls, -1); - } + public Stat setACL(String path, List acls) throws InterruptedException, KeeperException { + return runWithCorrectThrows( + "setting acls", () -> client.setACL().withVersion(-1).withACL(acls).forPath(path)); } /** @@ -964,14 +988,33 @@ public void updateACLs(final String root) throws KeeperException, InterruptedExc ZkMaintenanceUtils.VISIT_ORDER.VISIT_POST, path -> { try { - setACL(path, getZkACLProvider().getACLsToAdd(path), true); - log.debug("Updated ACL on {}", path); + runWithCorrectThrows( + "updating acls", () -> client.setACL().withACL(null).forPath(path)); } catch (NoNodeException ignored) { // If a node was deleted, don't bother trying to set ACLs on it. } }); } + @FunctionalInterface + protected interface SupplierWithException { + T get() throws Exception; + } + + protected T runWithCorrectThrows(String action, SupplierWithException func) + throws KeeperException, InterruptedException { + try { + return func.get(); + } catch (KeeperException | RuntimeException e) { + throw e; + } catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw e; + } catch (Exception e) { + throw new RuntimeException("Exception occurred while " + action, e); + } + } + // Some pass-throughs to allow less code disruption to other classes that use SolrZkClient. public void clean(String path) throws InterruptedException, KeeperException { ZkMaintenanceUtils.clean(this, path); @@ -1019,6 +1062,11 @@ public void downloadFromZK(String zkPath, Path dir) throws IOException { ZkMaintenanceUtils.downloadFromZK(this, zkPath, dir); } + @FunctionalInterface + public interface IsClosed { + boolean isClosed(); + } + /** * Watcher wrapper that ensures that heavy implementations of process do not interfere with our * ability to react to other watches, but also ensures that two wrappers containing equal watches @@ -1038,15 +1086,7 @@ private final class ProcessWatchWithExecutor implements Watcher { // see below f public void process(final WatchedEvent event) { log.debug("Submitting job to respond to event {}", event); try { - if (watcher instanceof ConnectionManager) { - zkConnManagerCallbackExecutor.submit(() -> watcher.process(event)); - } else { - zkCallbackExecutor.submit( - () -> { - metrics.watchesFired.increment(); - watcher.process(event); - }); - } + zkCallbackExecutor.submit(() -> watcher.process(event)); } catch (RejectedExecutionException e) { // If not a graceful shutdown if (!isClosed()) { @@ -1130,8 +1170,8 @@ public static class Builder { public int zkClientConnectTimeout = SolrZkClientTimeout.DEFAULT_ZK_CONNECT_TIMEOUT; public OnReconnect onReconnect; public BeforeReconnect beforeReconnect; - public ZkClientConnectionStrategy connectionStrategy; - public ZkACLProvider zkACLProvider; + public ZkCredentialsProvider zkCredentialsProvider; + public ACLProvider aclProvider; public IsClosed higherLevelIsClosed; public SolrClassLoader solrClassLoader; @@ -1169,18 +1209,18 @@ public Builder withReconnectListener(OnReconnect onReconnect) { return this; } - public Builder withConnStrategy(ZkClientConnectionStrategy strat) { - this.connectionStrategy = strat; + public Builder withBeforeConnect(BeforeReconnect beforeReconnect) { + this.beforeReconnect = beforeReconnect; return this; } - public Builder withBeforeConnect(BeforeReconnect beforeReconnect) { - this.beforeReconnect = beforeReconnect; + public Builder withZkCredentialsProvider(ZkCredentialsProvider zkCredentialsProvider) { + this.zkCredentialsProvider = zkCredentialsProvider; return this; } - public Builder withAclProvider(ZkACLProvider zkACLProvider) { - this.zkACLProvider = zkACLProvider; + public Builder withAclProvider(ACLProvider aclProvider) { + this.aclProvider = aclProvider; return this; } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/VMParamsSingleSetCredentialsDigestZkCredentialsProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/VMParamsSingleSetCredentialsDigestZkCredentialsProvider.java index 0674a088616..05c3d88d199 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/VMParamsSingleSetCredentialsDigestZkCredentialsProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/VMParamsSingleSetCredentialsDigestZkCredentialsProvider.java @@ -16,7 +16,8 @@ */ package org.apache.solr.common.cloud; -import java.util.Collection; +import java.util.List; +import org.apache.curator.framework.AuthInfo; /** * Deprecated in favor of a combination of {@link DigestZkCredentialsProvider} and {@link @@ -64,7 +65,7 @@ public void setZkCredentialsInjector(ZkCredentialsInjector zkCredentialsInjector } @Override - protected Collection createCredentials() { + protected List createCredentials() { return digestZkCredentialsProvider.createCredentials(); } } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkACLProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkACLProvider.java index 9c1fab51766..4364d0ba236 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkACLProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkACLProvider.java @@ -17,12 +17,18 @@ package org.apache.solr.common.cloud; import java.util.List; +import org.apache.curator.framework.api.ACLProvider; import org.apache.zookeeper.data.ACL; -public interface ZkACLProvider { +public interface ZkACLProvider extends ACLProvider { List getACLsToAdd(String zNodePath); + @Override + default List getAclForPath(String zNodePath) { + return getACLsToAdd(zNodePath); + } + /** * @param zkCredentialsInjector The ZkCredentialsInjector that injects ZK credentials */ diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkClientConnectionStrategy.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkClientConnectionStrategy.java deleted file mode 100644 index 8102606a59b..00000000000 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkClientConnectionStrategy.java +++ /dev/null @@ -1,155 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.solr.common.cloud; - -import java.io.IOException; -import java.lang.invoke.MethodHandles; -import java.util.ArrayList; -import java.util.List; -import java.util.concurrent.TimeoutException; -import org.apache.solr.common.cloud.ZkCredentialsProvider.ZkCredentials; -import org.apache.zookeeper.Watcher; -import org.apache.zookeeper.ZooKeeper; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -/** */ -public abstract class ZkClientConnectionStrategy { - private static final Logger log = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass()); - - private volatile ZkCredentialsProvider zkCredentialsToAddAutomatically; - private volatile boolean zkCredentialsToAddAutomaticallyUsed; - - private List disconnectedListeners = new ArrayList<>(); - private List connectedListeners = new ArrayList<>(); - - public abstract void connect( - String zkServerAddress, int zkClientTimeout, Watcher watcher, ZkUpdate updater) - throws IOException, InterruptedException, TimeoutException; - - public abstract void reconnect( - String serverAddress, int zkClientTimeout, Watcher watcher, ZkUpdate updater) - throws IOException, InterruptedException, TimeoutException; - - public ZkClientConnectionStrategy() { - zkCredentialsToAddAutomaticallyUsed = false; - } - - public synchronized void disconnected() { - for (DisconnectedListener listener : disconnectedListeners) { - try { - listener.disconnected(); - } catch (Exception e) { - log.error("Exception on disconnected for listener: {}", listener, e); - } - } - } - - public synchronized void connected() { - for (ConnectedListener listener : connectedListeners) { - try { - listener.connected(); - } catch (Exception e) { - log.error("Exception on connected for listener: {}", listener, e); - } - } - } - - public interface DisconnectedListener { - void disconnected(); - } - - public interface ConnectedListener { - void connected(); - } - - public synchronized void addDisconnectedListener(DisconnectedListener listener) { - disconnectedListeners.add(listener); - } - - public synchronized void removeDisconnectedListener(DisconnectedListener listener) { - disconnectedListeners.remove(listener); - } - - public synchronized void addConnectedListener(ConnectedListener listener) { - connectedListeners.add(listener); - } - - public interface ZkUpdate { - void update(ZooKeeper zooKeeper) throws InterruptedException, TimeoutException, IOException; - } - - public void setZkCredentialsToAddAutomatically( - ZkCredentialsProvider zkCredentialsToAddAutomatically) { - if (zkCredentialsToAddAutomaticallyUsed || (zkCredentialsToAddAutomatically == null)) - throw new RuntimeException( - "Cannot change zkCredentialsToAddAutomatically after it has been (connect or reconnect was called) used or to null"); - this.zkCredentialsToAddAutomatically = zkCredentialsToAddAutomatically; - } - - public boolean hasZkCredentialsToAddAutomatically() { - return zkCredentialsToAddAutomatically != null; - } - - public ZkCredentialsProvider getZkCredentialsToAddAutomatically() { - return zkCredentialsToAddAutomatically; - } - - protected ZooKeeper createZooKeeper( - final String serverAddress, final int zkClientTimeout, final Watcher watcher) - throws IOException { - ZooKeeper result = newZooKeeperInstance(serverAddress, zkClientTimeout, watcher); - - zkCredentialsToAddAutomaticallyUsed = true; - for (ZkCredentials zkCredentials : zkCredentialsToAddAutomatically.getCredentials()) { - result.addAuthInfo(zkCredentials.getScheme(), zkCredentials.getAuth()); - } - - return result; - } - - // Override for testing - protected ZooKeeper newZooKeeperInstance( - final String serverAddress, final int zkClientTimeout, final Watcher watcher) - throws IOException { - return new ZooKeeper(serverAddress, zkClientTimeout, watcher); - } - - /** - * Instantiate a new connection strategy for the given class name - * - * @param name the name of the strategy to use - * @return the strategy instance, or null if it could not be loaded - */ - public static ZkClientConnectionStrategy forName(String name, ZkClientConnectionStrategy def) { - log.debug("Attempting to load zk connection strategy '{}'", name); - if (name == null) { - return def; - } - - try { - // TODO should this use SolrResourceLoader? - return Class.forName(name) - .asSubclass(ZkClientConnectionStrategy.class) - .getConstructor() - .newInstance(); - } catch (Exception e) { - log.warn("Exception when loading '{}' ZK connection strategy.", name, e); - return def; - } - } -} diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkCmdExecutor.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkCmdExecutor.java deleted file mode 100644 index 01924b3c044..00000000000 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkCmdExecutor.java +++ /dev/null @@ -1,103 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.solr.common.cloud; - -import java.lang.invoke.MethodHandles; -import org.apache.solr.common.AlreadyClosedException; -import org.apache.solr.common.cloud.ConnectionManager.IsClosed; -import org.apache.zookeeper.KeeperException; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -public class ZkCmdExecutor { - private static final Logger log = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass()); - - private long retryDelay = 1500L; // 1 second would match timeout, so 500 ms over for padding - private int retryCount; - private double timeouts; - private IsClosed isClosed; - - public ZkCmdExecutor(int timeoutms) { - this(timeoutms, null); - } - - /** - * TODO: At this point, this should probably take a SolrZkClient in its constructor. - * - * @param timeoutms the client timeout for the ZooKeeper clients that will be used with this - * class. - */ - public ZkCmdExecutor(int timeoutms, IsClosed isClosed) { - timeouts = timeoutms / 1000.0; - this.retryCount = Math.round(0.5f * ((float) Math.sqrt(8.0f * timeouts + 1.0f) - 1.0f)) + 1; - this.isClosed = isClosed; - } - - public long getRetryDelay() { - return retryDelay; - } - - public void setRetryDelay(long retryDelay) { - this.retryDelay = retryDelay; - } - - /** Perform the given operation, retrying if the connection fails */ - public T retryOperation(ZkOperation operation) - throws KeeperException, InterruptedException { - KeeperException exception = null; - for (int i = 0; i < retryCount; i++) { - try { - if (log.isTraceEnabled()) { - log.trace("Begin zookeeper operation {}, attempt={}", operation, i); - } - if (i > 0 && isClosed()) { - throw new AlreadyClosedException(); - } - return operation.execute(); - } catch (KeeperException.ConnectionLossException e) { - if (exception == null) { - exception = e; - } - if (Thread.currentThread().isInterrupted()) { - Thread.currentThread().interrupt(); - throw new InterruptedException(); - } - if (i != retryCount - 1) { - retryDelay(i); - } - } finally { - if (log.isTraceEnabled()) { - log.trace("End zookeeper operation {}", operation); - } - } - } - throw exception; - } - - private boolean isClosed() { - return isClosed != null && isClosed.isClosed(); - } - - /** - * Performs a retry delay if this is not the first attempt - * - * @param attemptCount the number of the attempts performed so far - */ - protected void retryDelay(int attemptCount) throws InterruptedException { - Thread.sleep((attemptCount + 1) * retryDelay); - } -} diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkCredentialsProvider.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkCredentialsProvider.java index 8614ce6880c..24091258593 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkCredentialsProvider.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkCredentialsProvider.java @@ -16,30 +16,11 @@ */ package org.apache.solr.common.cloud; -import java.util.Collection; +import java.util.List; +import org.apache.curator.framework.AuthInfo; public interface ZkCredentialsProvider { - - class ZkCredentials { - String scheme; - byte[] auth; - - public ZkCredentials(String scheme, byte[] auth) { - super(); - this.scheme = scheme; - this.auth = auth; - } - - public String getScheme() { - return scheme; - } - - public byte[] getAuth() { - return auth; - } - } - - Collection getCredentials(); + List getCredentials(); void setZkCredentialsInjector(ZkCredentialsInjector zkCredentialsInjector); } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkMaintenanceUtils.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkMaintenanceUtils.java index 34d770c7a12..658281dd09c 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkMaintenanceUtils.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkMaintenanceUtils.java @@ -85,7 +85,7 @@ public static String listZnode(SolrZkClient zkClient, String path, Boolean recur StringBuilder sb = new StringBuilder(); if (recurse == false) { - for (String node : zkClient.getChildren(root, null, true)) { + for (String node : zkClient.getChildren(root, null)) { if (node.equals("zookeeper") == false) { sb.append(node).append(System.lineSeparator()); } @@ -139,7 +139,7 @@ public static void zkTransfer( // Make sure -recurse is specified if the source has children. if (recurse == false) { if (srcIsZk) { - if (zkClient.getChildren(src, null, true).size() != 0) { + if (zkClient.getChildren(src, null).size() != 0) { throw new SolrServerException( "Zookeeper node " + src + " has children and recurse is false"); } @@ -171,7 +171,7 @@ public static void zkTransfer( // Copying individual files from ZK requires special handling since downloadFromZK assumes the // node has children. This is kind of a weak test for the notion of "directory" on Zookeeper. ZK // -> local copy where ZK is a parent node - if (zkClient.getChildren(src, null, true).size() > 0) { + if (zkClient.getChildren(src, null).size() > 0) { downloadFromZK(zkClient, src, Paths.get(dst)); return; } @@ -181,7 +181,7 @@ public static void zkTransfer( if (dst.endsWith(File.separator) == false) dst += File.separator; dst = normalizeDest(src, dst, srcIsZk, dstIsZk); } - byte[] data = zkClient.getData(src, null, null, true); + byte[] data = zkClient.getData(src, null, null); Path filename = Paths.get(dst); Path parentDir = filename.getParent(); if (parentDir != null) { @@ -222,9 +222,9 @@ public static void moveZnode(SolrZkClient zkClient, String src, String dst) String destName = normalizeDest(src, dst, true, true); // Special handling if the source has no children, i.e. copying just a single file. - if (zkClient.getChildren(src, null, true).size() == 0) { - zkClient.makePath(destName, false, true); - zkClient.setData(destName, zkClient.getData(src, null, null, true), true); + if (zkClient.getChildren(src, null).size() == 0) { + zkClient.makePath(destName, false); + zkClient.setData(destName, zkClient.getData(src, null, null)); } else { traverseZkTree(zkClient, src, VISIT_ORDER.VISIT_PRE, new ZkCopier(zkClient, src, destName)); } @@ -241,8 +241,8 @@ public static void moveZnode(SolrZkClient zkClient, String src, String dst) private static void checkAllZnodesThere(SolrZkClient zkClient, String src, String dst) throws KeeperException, InterruptedException, SolrServerException { - for (String node : zkClient.getChildren(src, null, true)) { - if (zkClient.exists(dst + "/" + node, true) == false) { + for (String node : zkClient.getChildren(src, null)) { + if (zkClient.exists(dst + "/" + node) == false) { throw new SolrServerException( "mv command did not move node " + dst + "/" + node + " source left intact"); } @@ -261,7 +261,7 @@ public static void clean(SolrZkClient zkClient, String path) try { if (!znode.equals("/")) { try { - zkClient.delete(znode, -1, true); + zkClient.delete(znode, -1); } catch (KeeperException.NotEmptyException e) { clean(zkClient, znode); } @@ -300,7 +300,7 @@ public static void clean(SolrZkClient zkClient, String path, Predicate f for (String subpath : paths) { if (!subpath.equals("/")) { try { - zkClient.delete(subpath, -1, true); + zkClient.delete(subpath, -1); } catch (KeeperException.NotEmptyException | KeeperException.NoNodeException e) { // expected } @@ -324,11 +324,9 @@ public static void uploadToZK( if (!Files.exists(rootPath)) throw new IOException("Path " + rootPath + " does not exist"); - int partsOffset = - Path.of(zkPath).getNameCount() - rootPath.getNameCount() - 1; // will be negative Files.walkFileTree( rootPath, - new SimpleFileVisitor() { + new SimpleFileVisitor<>() { @Override public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException { @@ -350,24 +348,11 @@ public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) String zkNode = createZkNodeName(zkPath, rootPath, file); try { // if the path exists (and presumably we're uploading data to it) just set its data - if (file.toFile().getName().equals(ZKNODE_DATA_FILE) - && zkClient.exists(zkNode, true)) { - zkClient.setData(zkNode, file, true); - } else if (file == rootPath) { - // We are only uploading a single file, preVisitDirectory was never called - zkClient.makePath(zkNode, file, false, true); + if (file.toFile().getName().equals(ZKNODE_DATA_FILE) && zkClient.exists(zkNode)) { + zkClient.setData(zkNode, file); } else { - // Skip path parts here because they should have been created during - // preVisitDirectory - int pathParts = file.getNameCount() + partsOffset; - zkClient.makePath( - zkNode, - Files.readAllBytes(file), - CreateMode.PERSISTENT, - null, - false, - true, - pathParts); + // We are only uploading a single file, preVisitDirectory was never called + zkClient.makePath(zkNode, file, false); } } catch (KeeperException | InterruptedException e) { throw new IOException( @@ -386,11 +371,9 @@ public FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) try { if (dir.equals(rootPath)) { // Make sure the root path exists, including potential parents - zkClient.makePath(zkNode, true); + zkClient.makePath(zkNode); } else { - // Skip path parts here because they should have been created during previous visits - int pathParts = dir.getNameCount() + partsOffset; - zkClient.makePath(zkNode, null, CreateMode.PERSISTENT, null, true, true, pathParts); + zkClient.makePath(zkNode, true); } } catch (KeeperException.NodeExistsException ignored) { // Using fail-on-exists == false has side effect of makePath attempting to setData on @@ -409,13 +392,13 @@ public FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) private static boolean isEphemeral(SolrZkClient zkClient, String zkPath) throws KeeperException, InterruptedException { - Stat znodeStat = zkClient.exists(zkPath, null, true); + Stat znodeStat = zkClient.exists(zkPath, null); return znodeStat.getEphemeralOwner() != 0; } private static int copyDataDown(SolrZkClient zkClient, String zkPath, Path file) throws IOException, KeeperException, InterruptedException { - byte[] data = zkClient.getData(zkPath, null, null, true); + byte[] data = zkClient.getData(zkPath, null, null); if (data != null && data.length > 0) { // There are apparently basically empty ZNodes. log.info("Writing file {}", file); Files.write(file, data); @@ -427,7 +410,7 @@ private static int copyDataDown(SolrZkClient zkClient, String zkPath, Path file) public static void downloadFromZK(SolrZkClient zkClient, String zkPath, Path file) throws IOException { try { - List children = zkClient.getChildren(zkPath, null, true); + List children = zkClient.getChildren(zkPath, null); // If it has no children, it's a leaf node, write the associated data from the ZNode. // Otherwise, continue recursing, but write the associated data to a special file if any if (children.size() == 0) { @@ -498,7 +481,7 @@ public static void traverseZkTree( } List children; try { - children = zkClient.getChildren(path, null, true); + children = zkClient.getChildren(path, null); } catch (KeeperException.NoNodeException r) { return; } @@ -639,11 +622,11 @@ public static void ensureExists( int skipPathParts) throws KeeperException, InterruptedException { - if (zkClient.exists(path, true)) { + if (zkClient.exists(path)) { return; } try { - zkClient.makePath(path, data, createMode, null, true, true, skipPathParts); + zkClient.makePath(path, data, createMode, null, true, skipPathParts); } catch (NodeExistsException ignored) { // it's okay if another beats us creating the node } @@ -669,8 +652,8 @@ public void visit(String path) throws InterruptedException, KeeperException { String finalDestination = dest; if (path.equals(source) == false) finalDestination += "/" + path.substring(source.length() + 1); - zkClient.makePath(finalDestination, false, true); - zkClient.setData(finalDestination, zkClient.getData(path, null, null, true), true); + zkClient.makePath(finalDestination, false); + zkClient.setData(finalDestination, zkClient.getData(path, null, null)); } } } diff --git a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkStateReader.java b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkStateReader.java index 4879733e7fe..f16360a34be 100644 --- a/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkStateReader.java +++ b/solr/solrj-zookeeper/src/java/org/apache/solr/common/cloud/ZkStateReader.java @@ -574,13 +574,18 @@ public synchronized void createClusterStateWatchersAndUpdate() collectionPropsWatchers.computeIfAbsent(k, PropsWatcher::new).refreshAndWatch(true); }); } catch (KeeperException.NoNodeException nne) { + String noNodePath = nne.getPath(); + if (noNodePath.length() > zkClient.getCuratorFramework().getNamespace().length()) { + noNodePath = + noNodePath.substring(zkClient.getCuratorFramework().getNamespace().length() + 1); + } throw new SolrException( ErrorCode.SERVICE_UNAVAILABLE, "Cannot connect to cluster at " + zkClient.getZkServerAddress() + ": cluster not found/not ready." + " Expected node '" - + nne.getPath() + + noNodePath + "' does not exist."); } } @@ -655,7 +660,7 @@ private void refreshCollectionList(Watcher watcher) throws KeeperException, Inte synchronized (refreshCollectionListLock) { List children = null; try { - children = zkClient.getChildren(COLLECTIONS_ZKNODE, watcher, true); + children = zkClient.getChildren(COLLECTIONS_ZKNODE, watcher); } catch (KeeperException.NoNodeException e) { log.warn("Error fetching collection names: ", e); // fall through @@ -749,7 +754,7 @@ public synchronized DocCollection get(boolean allowCached) { if (cachedDocCollection != null) { Stat freshStats = null; try { - freshStats = zkClient.exists(DocCollection.getCollectionPath(collName), null, true); + freshStats = zkClient.exists(DocCollection.getCollectionPath(collName), null); } catch (Exception e) { } if (freshStats != null @@ -787,7 +792,7 @@ private void refreshLiveNodes(Watcher watcher) throws KeeperException, Interrupt synchronized (refreshLiveNodesLock) { SortedSet newLiveNodes; try { - List nodeList = zkClient.getChildren(LIVE_NODES_ZKNODE, watcher, true); + List nodeList = zkClient.getChildren(LIVE_NODES_ZKNODE, watcher); newLiveNodes = new TreeSet<>(nodeList); } catch (KeeperException.NoNodeException e) { newLiveNodes = emptySortedSet(); @@ -1139,8 +1144,7 @@ private void loadClusterProperties() { while (true) { try { byte[] data = - zkClient.getData( - ZkStateReader.CLUSTER_PROPS, clusterPropertiesWatcher, new Stat(), true); + zkClient.getData(ZkStateReader.CLUSTER_PROPS, clusterPropertiesWatcher, new Stat()); @SuppressWarnings("unchecked") Map properties = (Map) Utils.fromJSON(data); this.clusterProperties = @@ -1156,7 +1160,7 @@ private void loadClusterProperties() { log.debug("Loaded empty cluster properties"); // set an exists watch, and if the node has been created since the last call, // read the data again - if (zkClient.exists(ZkStateReader.CLUSTER_PROPS, clusterPropertiesWatcher, true) == null) + if (zkClient.exists(ZkStateReader.CLUSTER_PROPS, clusterPropertiesWatcher) == null) return; } } @@ -1269,7 +1273,7 @@ private VersionedCollectionProps fetchCollectionProperties(String collection, Wa while (true) { try { Stat stat = new Stat(); - byte[] data = zkClient.getData(znodePath, watcher, stat, true); + byte[] data = zkClient.getData(znodePath, watcher, stat); @SuppressWarnings("unchecked") Map props = (Map) Utils.fromJSON(data); return new VersionedCollectionProps(stat.getVersion(), props); @@ -1281,7 +1285,7 @@ private VersionedCollectionProps fetchCollectionProperties(String collection, Wa } catch (KeeperException.NoNodeException e) { if (watcher != null) { // Leave an exists watch in place in case a collectionprops.json is created later. - Stat exists = zkClient.exists(znodePath, watcher, true); + Stat exists = zkClient.exists(znodePath, watcher); if (exists != null) { // Rare race condition, we tried to fetch the data and couldn't find it, then we found // it exists. Loop and try again. @@ -1388,7 +1392,7 @@ private void refreshAndWatchChildren() throws KeeperException, InterruptedExcept Stat stat = new Stat(); List replicaStates = null; try { - replicaStates = zkClient.getChildren(collectionPath, this, stat, true); + replicaStates = zkClient.getChildren(collectionPath, this, stat); PerReplicaStates newStates = new PerReplicaStates(collectionPath, stat.getCversion(), replicaStates); DocCollection oldState = collectionWatches.getDocCollection(coll); @@ -1603,7 +1607,7 @@ private DocCollection fetchCollectionState(String coll, Watcher watcher) while (true) { try { Stat stat = new Stat(); - byte[] data = zkClient.getData(collectionPath, watcher, stat, true); + byte[] data = zkClient.getData(collectionPath, watcher, stat); // This factory method can detect a missing configName and supply it by reading it from the // old ZK location. @@ -1617,7 +1621,7 @@ private DocCollection fetchCollectionState(String coll, Watcher watcher) } catch (KeeperException.NoNodeException e) { if (watcher != null) { // Leave an exists watch in place in case a state.json is created later. - Stat exists = zkClient.exists(collectionPath, watcher, true); + Stat exists = zkClient.exists(collectionPath, watcher); if (exists != null) { // Rare race condition, we tried to fetch the data and couldn't find it, then we found // it exists. Loop and try again. @@ -1630,7 +1634,7 @@ private DocCollection fetchCollectionState(String coll, Watcher watcher) ZkStateReader.class.getName() + "/exercised", e); // could be a race condition that state.json and PRS entries are deleted between the // state.json fetch and PRS entry fetch - Stat exists = zkClient.exists(collectionPath, watcher, true); + Stat exists = zkClient.exists(collectionPath, watcher); if (exists == null) { log.info( "PRS entry for collection {} not found in ZK. It was probably deleted between state.json read and PRS entry read.", @@ -2137,7 +2141,7 @@ public AliasesManager getAliasesManager() { private void refreshAliases(AliasesManager watcher) throws KeeperException, InterruptedException { synchronized (getUpdateLock()) { constructState(Collections.emptySet()); - zkClient.exists(ALIASES, watcher, true); + zkClient.exists(ALIASES, watcher); } aliasesManager.update(); } @@ -2196,7 +2200,7 @@ public void applyModificationAndExportToZk(UnaryOperator op) { try { try { final Stat stat = - getZkClient().setData(ALIASES, modAliasesJson, curAliases.getZNodeVersion(), true); + getZkClient().setData(ALIASES, modAliasesJson, curAliases.getZNodeVersion()); setIfNewer(new SolrZkClient.NodeData(stat, modAliasesJson)); return; } catch (KeeperException.BadVersionException e) { @@ -2238,8 +2242,9 @@ public boolean update() throws KeeperException, InterruptedException { log.debug("Checking ZK for most up to date Aliases {}", ALIASES); } // Call sync() first to ensure the subsequent read (getData) is up to date. - zkClient.getZooKeeper().sync(ALIASES, null, null); - return setIfNewer(zkClient.getNode(ALIASES, null, true)); + zkClient.runWithCorrectThrows( + "syncing aliases", () -> zkClient.getCuratorFramework().sync().forPath(ALIASES)); + return setIfNewer(zkClient.getNode(ALIASES, null)); } // ZK Watcher interface @@ -2253,7 +2258,7 @@ public void process(WatchedEvent event) { log.debug("Aliases: updating"); // re-register the watch - setIfNewer(zkClient.getNode(ALIASES, this, true)); + setIfNewer(zkClient.getNode(ALIASES, this)); } catch (NoNodeException e) { // /aliases.json will not always exist } catch (KeeperException.ConnectionLossException diff --git a/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/SolrZkClientTest.java b/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/SolrZkClientTest.java index 9d1eacd8950..cb8723c6e68 100644 --- a/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/SolrZkClientTest.java +++ b/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/SolrZkClientTest.java @@ -21,13 +21,15 @@ import java.nio.charset.StandardCharsets; import java.nio.file.Path; import java.security.NoSuchAlgorithmException; -import java.util.Collection; +import java.util.Arrays; import java.util.Collections; import java.util.List; import java.util.Optional; import java.util.concurrent.Semaphore; import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicInteger; +import org.apache.curator.framework.AuthInfo; +import org.apache.curator.framework.api.ACLProvider; import org.apache.solr.client.solrj.impl.CloudSolrClient; import org.apache.solr.client.solrj.request.CollectionAdminRequest; import org.apache.solr.cloud.AbstractZkTestCase; @@ -84,7 +86,7 @@ public void setUp() throws Exception { .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build()) { // Set up chroot - client.makePath("/solr", false, true); + client.makePath("/solr", false); } defaultClient = @@ -92,7 +94,7 @@ public void setUp() throws Exception { .withUrl(zkServer.getZkAddress()) .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build(); - defaultClient.makePath(PATH, true); + defaultClient.makePath(PATH); aclClient = new SolrZkClient( @@ -100,18 +102,17 @@ public void setUp() throws Exception { .withUrl(zkServer.getZkAddress()) .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS)) { @Override - protected ZkACLProvider createZkACLProvider() { - return new DefaultZkACLProvider() { - @Override - protected List createGlobalACLsToAdd() { - try { - Id id = new Id(SCHEME, DigestAuthenticationProvider.generateDigest(AUTH)); - return Collections.singletonList(new ACL(ZooDefs.Perms.ALL, id)); - } catch (NoSuchAlgorithmException e) { - throw new RuntimeException(e); - } - } - }; + protected ACLProvider createACLProvider() { + try { + // Must be Arrays.asList(), Zookeeper does not allow for immutable list types for ACLs + return new DefaultZkACLProvider( + Arrays.asList( + new ACL( + ZooDefs.Perms.ALL, + new Id(SCHEME, DigestAuthenticationProvider.generateDigest(AUTH))))); + } catch (NoSuchAlgorithmException e) { + throw new RuntimeException(e); + } } }; @@ -122,13 +123,9 @@ protected List createGlobalACLsToAdd() { .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS)) { @Override protected ZkCredentialsProvider createZkCredentialsToAddAutomatically() { - return new DefaultZkCredentialsProvider() { - @Override - protected Collection createCredentials() { - return Collections.singleton( - new ZkCredentials(SCHEME, AUTH.getBytes(StandardCharsets.UTF_8))); - } - }; + return new DefaultZkCredentialsProvider( + Collections.singletonList( + new AuthInfo(SCHEME, AUTH.getBytes(StandardCharsets.UTF_8)))); } }; } @@ -219,12 +216,10 @@ public void process(WatchedEvent event) { ZkStateReader.from(solrClient) .getZkClient() - .getData( - "/collections/" + getSaferTestName() + "/collectionprops.json", wrapped1A, null, true); + .getData("/collections/" + getSaferTestName() + "/collectionprops.json", wrapped1A, null); ZkStateReader.from(solrClient) .getZkClient() - .getData( - "/collections/" + getSaferTestName() + "/collectionprops.json", wrapped2A, null, true); + .getData("/collections/" + getSaferTestName() + "/collectionprops.json", wrapped2A, null); CollectionAdminRequest.setCollectionProperty(getSaferTestName(), "baz", "bam") .process(solrClient); @@ -238,12 +233,10 @@ public void process(WatchedEvent event) { ZkStateReader.from(solrClient) .getZkClient() - .getData( - "/collections/" + getSaferTestName() + "/collectionprops.json", wrapped1A, null, true); + .getData("/collections/" + getSaferTestName() + "/collectionprops.json", wrapped1A, null); ZkStateReader.from(solrClient) .getZkClient() - .getData( - "/collections/" + getSaferTestName() + "/collectionprops.json", wrappedB, null, true); + .getData("/collections/" + getSaferTestName() + "/collectionprops.json", wrappedB, null); CollectionAdminRequest.setCollectionProperty(getSaferTestName(), "baz", "bang") .process(solrClient); @@ -260,7 +253,7 @@ public void process(WatchedEvent event) { private static boolean canRead(SolrZkClient zkClient, String path) throws KeeperException, InterruptedException { try { - zkClient.getData(path, null, null, true); + zkClient.getData(path, null, null); return true; } catch (KeeperException.NoAuthException e) { return false; @@ -271,7 +264,7 @@ private static boolean canRead(SolrZkClient zkClient, String path) public void getConfig() { // As the embedded ZK is hardcoded to standalone, there is no way to test actual config data // here - assertEquals("", defaultClient.getConfig()); + assertEquals("version=0", defaultClient.getConfig()); } @Test diff --git a/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestPerReplicaStates.java b/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestPerReplicaStates.java index ab650bdc608..52ee6ff7d7e 100644 --- a/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestPerReplicaStates.java +++ b/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestPerReplicaStates.java @@ -86,12 +86,12 @@ public void testEntries() { public void testReplicaStateOperations() throws Exception { String root = "/testReplicaStateOperations"; - cluster.getZkClient().create(root, null, CreateMode.PERSISTENT, true); + cluster.getZkClient().create(root, null, CreateMode.PERSISTENT); List states = List.of("R1:2:A", "R1:1:A:L", "R1:0:D", "R3:0:A", "R4:13:A"); for (String state : states) { - cluster.getZkClient().create(root + "/" + state, null, CreateMode.PERSISTENT, true); + cluster.getZkClient().create(root + "/" + state, null, CreateMode.PERSISTENT); } ZkStateReader zkStateReader = cluster.getZkStateReader(); @@ -106,7 +106,7 @@ public void testReplicaStateOperations() throws Exception { rs = PerReplicaStatesOps.fetch(root, zkStateReader.getZkClient(), null); assertEquals(4, rs.states.size()); assertTrue(rs.cversion >= 6); - assertEquals(6, cluster.getZkClient().getChildren(root, null, true).size()); + assertEquals(6, cluster.getZkClient().getChildren(root, null).size()); ops = PerReplicaStatesOps.flipState("R1", State.DOWN, rs); assertEquals(4, ops.ops.size()); diff --git a/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestZkConfigSetService.java b/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestZkConfigSetService.java index 5375f62cdeb..50df39f1156 100644 --- a/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestZkConfigSetService.java +++ b/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestZkConfigSetService.java @@ -22,11 +22,12 @@ import java.nio.file.Path; import java.nio.file.Paths; import java.security.NoSuchAlgorithmException; -import java.util.ArrayList; -import java.util.Collection; +import java.util.Arrays; import java.util.List; import java.util.Properties; import java.util.concurrent.TimeUnit; +import org.apache.curator.framework.AuthInfo; +import org.apache.curator.framework.api.ACLProvider; import org.apache.solr.SolrTestCaseJ4; import org.apache.solr.cloud.AbstractZkTestCase; import org.apache.solr.cloud.ZkConfigSetService; @@ -140,7 +141,7 @@ public void testUploadConfig() throws IOException { } @Test - public void testUploadWithACL() throws IOException { + public void testUploadWithACL() throws IOException, NoSuchAlgorithmException { zkServer.ensurePathExists("/acl"); @@ -149,59 +150,36 @@ public void testUploadWithACL() throws IOException { final String writeableUsername = "writeable"; final String writeablePassword = "writeable"; - ZkACLProvider aclProvider = - new DefaultZkACLProvider() { - @Override - protected List createGlobalACLsToAdd() { - try { - List result = new ArrayList<>(); - result.add( - new ACL( - ZooDefs.Perms.ALL, - new Id( - "digest", - DigestAuthenticationProvider.generateDigest( - writeableUsername + ":" + writeablePassword)))); - result.add( - new ACL( - ZooDefs.Perms.READ, - new Id( - "digest", - DigestAuthenticationProvider.generateDigest( - readOnlyUsername + ":" + readOnlyPassword)))); - return result; - } catch (NoSuchAlgorithmException e) { - throw new RuntimeException(e); - } - } - }; - - ZkCredentialsProvider readonly = - new DefaultZkCredentialsProvider() { - @Override - protected Collection createCredentials() { - List credentials = new ArrayList<>(); - credentials.add( - new ZkCredentials( + // Must be Arrays.asList(), Zookeeper does not allow for immutable list types for ACLs + List acls = + Arrays.asList( + new ACL( + ZooDefs.Perms.ALL, + new Id( "digest", - (readOnlyUsername + ":" + readOnlyPassword).getBytes(StandardCharsets.UTF_8))); - return credentials; - } - }; - - ZkCredentialsProvider writeable = - new DefaultZkCredentialsProvider() { - @Override - protected Collection createCredentials() { - List credentials = new ArrayList<>(); - credentials.add( - new ZkCredentials( + DigestAuthenticationProvider.generateDigest( + writeableUsername + ":" + writeablePassword))), + new ACL( + ZooDefs.Perms.READ, + new Id( "digest", - (writeableUsername + ":" + writeablePassword) - .getBytes(StandardCharsets.UTF_8))); - return credentials; - } - }; + DigestAuthenticationProvider.generateDigest( + readOnlyUsername + ":" + readOnlyPassword)))); + ACLProvider aclProvider = new DefaultZkACLProvider(acls); + + List credentials = + List.of( + new AuthInfo( + "digest", + (readOnlyUsername + ":" + readOnlyPassword).getBytes(StandardCharsets.UTF_8))); + ZkCredentialsProvider readonly = new DefaultZkCredentialsProvider(credentials); + + List writeableCredentials = + List.of( + new AuthInfo( + "digest", + (writeableUsername + ":" + writeablePassword).getBytes(StandardCharsets.UTF_8))); + ZkCredentialsProvider writeable = new DefaultZkCredentialsProvider(writeableCredentials); Path configPath = createTempDir("acl-config"); Files.createFile(configPath.resolve("file1")); @@ -250,7 +228,7 @@ public void testBootstrapConf() throws IOException, KeeperException, Interrupted .withUrl(zkServer.getZkHost()) .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build(); - zkClient.makePath("/solr", false, true); + zkClient.makePath("/solr", false); cc.setCoreConfigService(new ZkConfigSetService(zkClient)); assertFalse(cc.getConfigSetService().checkConfigExists("collection1")); ConfigSetService.bootstrapConf(cc); @@ -261,7 +239,7 @@ public void testBootstrapConf() throws IOException, KeeperException, Interrupted static SolrZkClient buildZkClient( String zkAddress, - final ZkACLProvider aclProvider, + final ACLProvider aclProvider, final ZkCredentialsProvider credentialsProvider) { return new SolrZkClient( new SolrZkClient.Builder().withUrl(zkAddress).withTimeout(10000, TimeUnit.MILLISECONDS)) { @@ -271,7 +249,7 @@ protected ZkCredentialsProvider createZkCredentialsToAddAutomatically() { } @Override - protected ZkACLProvider createZkACLProvider() { + protected ACLProvider createACLProvider() { return aclProvider; } }; diff --git a/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestZkMaintenanceUtils.java b/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestZkMaintenanceUtils.java index 89677753f76..bbdd7de8cf3 100644 --- a/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestZkMaintenanceUtils.java +++ b/solr/solrj-zookeeper/src/test/org/apache/solr/common/cloud/TestZkMaintenanceUtils.java @@ -81,18 +81,17 @@ public void testClean() throws KeeperException, InterruptedException, SolrServer String data2 = "myStringData2"; String longData = "myLongStringData"; // create zk nodes that have the same path length - zkClient.create("/myPath", null, CreateMode.PERSISTENT, true); - zkClient.create(path, null, CreateMode.PERSISTENT, true); + zkClient.create("/myPath", null, CreateMode.PERSISTENT); + zkClient.create(path, null, CreateMode.PERSISTENT); zkClient.create( - path + "/file1.txt", data1.getBytes(StandardCharsets.UTF_8), CreateMode.PERSISTENT, true); - zkClient.create(path + "/nothing.txt", null, CreateMode.PERSISTENT, true); + path + "/file1.txt", data1.getBytes(StandardCharsets.UTF_8), CreateMode.PERSISTENT); + zkClient.create(path + "/nothing.txt", null, CreateMode.PERSISTENT); zkClient.create( - path + "/file2.txt", data2.getBytes(StandardCharsets.UTF_8), CreateMode.PERSISTENT, true); + path + "/file2.txt", data2.getBytes(StandardCharsets.UTF_8), CreateMode.PERSISTENT); zkClient.create( path + "/some_longer_file2.txt", longData.getBytes(StandardCharsets.UTF_8), - CreateMode.PERSISTENT, - true); + CreateMode.PERSISTENT); /* RUN */ // delete all nodes that contain "file" @@ -138,9 +137,9 @@ public void testTraverseZkTree() throws Exception { .withUrl(zkServer.getZkHost()) .withTimeout(10000, TimeUnit.MILLISECONDS) .build()) { - zkClient.makePath("/testTraverseZkTree/1/1", true, true); - zkClient.makePath("/testTraverseZkTree/1/2", false, true); - zkClient.makePath("/testTraverseZkTree/2", false, true); + zkClient.makePath("/testTraverseZkTree/1/1", true); + zkClient.makePath("/testTraverseZkTree/1/2", false); + zkClient.makePath("/testTraverseZkTree/2", false); assertEquals( Arrays.asList( "/testTraverseZkTree", @@ -172,7 +171,7 @@ public void testOneByteFile() throws Exception { .build()) { byte[] oneByte = new byte[1]; oneByte[0] = 0x30; - zkClient.makePath("/test1byte/one", oneByte, true); + zkClient.makePath("/test1byte/one", oneByte); Path tmpDest = Paths.get(createTempDir().toFile().getAbsolutePath(), "MustBeOne"); ZkMaintenanceUtils.downloadFromZK(zkClient, "/test1byte/one", tmpDest); diff --git a/solr/solrj/src/test/org/apache/solr/client/solrj/impl/HttpClusterStateSSLTest.java b/solr/solrj/src/test/org/apache/solr/client/solrj/impl/HttpClusterStateSSLTest.java index db385e26b83..79398676f3d 100644 --- a/solr/solrj/src/test/org/apache/solr/client/solrj/impl/HttpClusterStateSSLTest.java +++ b/solr/solrj/src/test/org/apache/solr/client/solrj/impl/HttpClusterStateSSLTest.java @@ -66,9 +66,7 @@ public void testHttpClusterStateWithSSL() throws Exception { // verify the base_url is actually stored with https in it on the server-side byte[] stateJsonBytes = - cluster - .getZkClient() - .getData(DocCollection.getCollectionPath(collectionId), null, null, true); + cluster.getZkClient().getData(DocCollection.getCollectionPath(collectionId), null, null); assertNotNull(stateJsonBytes); Map replicasMap = (Map) diff --git a/solr/solrj/src/test/org/apache/solr/client/solrj/impl/TestCloudSolrClientConnections.java b/solr/solrj/src/test/org/apache/solr/client/solrj/impl/TestCloudSolrClientConnections.java index d678106f873..36ded773992 100644 --- a/solr/solrj/src/test/org/apache/solr/client/solrj/impl/TestCloudSolrClientConnections.java +++ b/solr/solrj/src/test/org/apache/solr/client/solrj/impl/TestCloudSolrClientConnections.java @@ -81,7 +81,7 @@ public void testCloudClientUploads() throws Exception { assertTrue( "List of uploaded configs does not contain 'testconfig'", - cluster.getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + "testconfig", true)); + cluster.getZkClient().exists(ZkStateReader.CONFIGS_ZKNODE + "/" + "testconfig")); } finally { cluster.shutdown(); diff --git a/solr/solrj/src/test/org/apache/solr/common/cloud/PerReplicaStatesIntegrationTest.java b/solr/solrj/src/test/org/apache/solr/common/cloud/PerReplicaStatesIntegrationTest.java index e75100f1a50..aa9b5427c99 100644 --- a/solr/solrj/src/test/org/apache/solr/common/cloud/PerReplicaStatesIntegrationTest.java +++ b/solr/solrj/src/test/org/apache/solr/common/cloud/PerReplicaStatesIntegrationTest.java @@ -306,7 +306,7 @@ public void testZkNodeVersions() throws Exception { Stat stat = null; CollectionAdminRequest.createCollection(NONPRS_COLL, "conf", 10, 1) .process(cluster.getSolrClient()); - stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(NONPRS_COLL), null, true); + stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(NONPRS_COLL), null); log.info(""); // the actual number can vary depending on batching assertTrue(stat.getVersion() >= 2); @@ -315,7 +315,7 @@ public void testZkNodeVersions() throws Exception { CollectionAdminRequest.createCollection(PRS_COLL, "conf", 10, 1) .setPerReplicaState(Boolean.TRUE) .process(cluster.getSolrClient()); - stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(PRS_COLL), null, true); + stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(PRS_COLL), null); // +1 after all replica are added with on state.json write to CreateCollectionCmd.setData() assertEquals(1, stat.getVersion()); // For each replica: @@ -330,7 +330,7 @@ public void testZkNodeVersions() throws Exception { CollectionAdminRequest.addReplicaToShard(PRS_COLL, "shard1") .process(cluster.getSolrClient()); cluster.waitForActiveCollection(PRS_COLL, 10, 11); - stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(PRS_COLL), null, true); + stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(PRS_COLL), null); // For the new replica: // +2 for state.json overseer writes, even though there's no longer PRS updates from // overseer, current code would still do a "TOUCH" on the PRS entry @@ -350,7 +350,7 @@ public void testZkNodeVersions() throws Exception { CollectionAdminRequest.deleteReplica(PRS_COLL, "shard1", addedReplica.getName()) .process(cluster.getSolrClient()); cluster.waitForActiveCollection(PRS_COLL, 10, 10); - stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(PRS_COLL), null, true); + stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(PRS_COLL), null); // For replica deletion // +1 for ZkController#unregister, which delete the PRS entry from data node // overseer, current code would still do a "TOUCH" on the PRS entry @@ -359,7 +359,7 @@ public void testZkNodeVersions() throws Exception { for (JettySolrRunner j : cluster.getJettySolrRunners()) { j.stop(); j.start(true); - stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(PRS_COLL), null, true); + stat = cluster.getZkClient().exists(DocCollection.getCollectionPath(PRS_COLL), null); // ensure restart does not update the state.json, after addReplica/deleteReplica, 2 more // updates hence at version 3 on state.json version assertEquals(3, stat.getVersion()); diff --git a/solr/solrj/src/test/org/apache/solr/common/cloud/SolrZkClientCompressedDataTest.java b/solr/solrj/src/test/org/apache/solr/common/cloud/SolrZkClientCompressedDataTest.java index 82682e5e122..71f95b23c4b 100644 --- a/solr/solrj/src/test/org/apache/solr/common/cloud/SolrZkClientCompressedDataTest.java +++ b/solr/solrj/src/test/org/apache/solr/common/cloud/SolrZkClientCompressedDataTest.java @@ -75,14 +75,11 @@ public void getData() throws Exception { + "\"leader\":\"true\"}}}}}}"; byte[] arr = state.getBytes(StandardCharsets.UTF_8); byte[] compressedData = zLibStateCompression.compressBytes(arr); - ZkACLProvider aclProvider = new DefaultZkACLProvider(); String path = ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json"; - zkClient - .getZooKeeper() - .create(path, compressedData, aclProvider.getACLsToAdd(path), CreateMode.PERSISTENT); + zkClient.create(path, compressedData, CreateMode.PERSISTENT); byte[] data = - zkClient.getData(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", null, null, true); + zkClient.getData(ZkStateReader.COLLECTIONS_ZKNODE + "/c1/state.json", null, null); Map map = (Map) Utils.fromJSON(data); assertEquals(arr.length, data.length); assertNotNull(map.get("c1")); diff --git a/solr/test-framework/build.gradle b/solr/test-framework/build.gradle index cb0ddabf7fa..0798dd83f85 100644 --- a/solr/test-framework/build.gradle +++ b/solr/test-framework/build.gradle @@ -43,6 +43,17 @@ dependencies { var zkExcludes = { exclude group: "org.apache.yetus", module: "audience-annotations" } + api('org.apache.curator:curator-client', { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + }) + api('org.apache.curator:curator-framework', { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + }) + api('org.apache.curator:curator-test') { + exclude group: 'org.apache.zookeeper', module: 'zookeeper' + exclude group: 'com.google.guava', module: 'guava' + exclude group: 'io.dropwizard.metrics', module: 'metrics-core' + } implementation('org.apache.zookeeper:zookeeper', zkExcludes) implementation('org.apache.zookeeper:zookeeper-jute', zkExcludes) diff --git a/solr/test-framework/src/java/org/apache/solr/SolrTestCaseJ4.java b/solr/test-framework/src/java/org/apache/solr/SolrTestCaseJ4.java index 111e2c4580d..d7590f6c257 100644 --- a/solr/test-framework/src/java/org/apache/solr/SolrTestCaseJ4.java +++ b/solr/test-framework/src/java/org/apache/solr/SolrTestCaseJ4.java @@ -94,7 +94,6 @@ import org.apache.solr.client.solrj.util.ClientUtils; import org.apache.solr.cloud.IpTables; import org.apache.solr.cloud.MiniSolrCloudCluster; -import org.apache.solr.cloud.TestConnectionStrategy; import org.apache.solr.common.SolrDocument; import org.apache.solr.common.SolrDocumentList; import org.apache.solr.common.SolrException; @@ -288,7 +287,6 @@ public static void setupTestCases() { System.setProperty("solr.v2RealPath", "true"); System.setProperty("zookeeper.forceSync", "no"); System.setProperty("jetty.testMode", "true"); - System.setProperty("solr.zookeeper.connectionStrategy", TestConnectionStrategy.class.getName()); System.setProperty("enable.update.log", Boolean.toString(usually())); System.setProperty("tests.shardhandler.randomSeed", Long.toString(random().nextLong())); System.setProperty("solr.clustering.enabled", "false"); @@ -878,7 +876,7 @@ public static void deleteCore() { CoreContainer cc = h.getCoreContainer(); if (cc.getNumAllCores() > 0 && cc.isZooKeeperAware()) { try { - cc.getZkController().getZkClient().exists("/", false); + cc.getZkController().getZkClient().exists("/"); } catch (KeeperException e) { log.error("Testing connectivity to ZK by checking for root path failed", e); fail("Trying to tear down a ZK aware core container with ZK not reachable"); diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/AbstractBasicDistributedZk2TestBase.java b/solr/test-framework/src/java/org/apache/solr/cloud/AbstractBasicDistributedZk2TestBase.java index 899efc03dcb..9fc1417cdc4 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/AbstractBasicDistributedZk2TestBase.java +++ b/solr/test-framework/src/java/org/apache/solr/cloud/AbstractBasicDistributedZk2TestBase.java @@ -269,7 +269,7 @@ private void bringDownShardIndexSomeDocsAndRecover() throws Exception { int oldLiveNodes = ZkStateReader.from(cloudClient) .getZkClient() - .getChildren(ZkStateReader.LIVE_NODES_ZKNODE, null, true) + .getChildren(ZkStateReader.LIVE_NODES_ZKNODE, null) .size(); assertEquals(5, oldLiveNodes); diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/AbstractDigestZkACLAndCredentialsProvidersTestBase.java b/solr/test-framework/src/java/org/apache/solr/cloud/AbstractDigestZkACLAndCredentialsProvidersTestBase.java index dbbf308bad1..02935f94b96 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/AbstractDigestZkACLAndCredentialsProvidersTestBase.java +++ b/solr/test-framework/src/java/org/apache/solr/cloud/AbstractDigestZkACLAndCredentialsProvidersTestBase.java @@ -102,7 +102,7 @@ public void setUp() throws Exception { .withConnTimeOut(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build(); - zkClient.makePath("/solr", false, true); + zkClient.makePath("/solr", false); zkClient.close(); zkClient = @@ -111,15 +111,14 @@ public void setUp() throws Exception { .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build(); zkClient.create( - "/protectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); + "/protectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.makePath( - "/protectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); + "/protectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.create( SecurityAwareZkACLProvider.SECURITY_ZNODE_PATH, "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); + CreateMode.PERSISTENT); zkClient.close(); clearSecuritySystemProperties(); @@ -138,12 +137,9 @@ public void setUp() throws Exception { .addAuthInfo( "digest", (ALL_USERNAME + ":" + ALL_PASSWORD).getBytes(StandardCharsets.UTF_8)); zkClient.create( - "/unprotectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT, false); + "/unprotectedCreateNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.makePath( - "/unprotectedMakePathNode", - "content".getBytes(DATA_ENCODING), - CreateMode.PERSISTENT, - false); + "/unprotectedMakePathNode", "content".getBytes(DATA_ENCODING), CreateMode.PERSISTENT); zkClient.close(); setDigestZkSystemProps(); @@ -312,8 +308,8 @@ public void testRepairACL() throws Exception { .getBytes(StandardCharsets.UTF_8)); zkClient.create( - "/security.json", "{}".getBytes(StandardCharsets.UTF_8), CreateMode.PERSISTENT, false); - assertEquals(OPEN_ACL_UNSAFE, zkClient.getACL("/security.json", null, false)); + "/security.json", "{}".getBytes(StandardCharsets.UTF_8), CreateMode.PERSISTENT); + assertEquals(OPEN_ACL_UNSAFE, zkClient.getACL("/security.json", null)); } setSecuritySystemProperties(); @@ -323,7 +319,7 @@ public void testRepairACL() throws Exception { .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build()) { ZkController.createClusterZkNodes(zkClient); - assertNotEquals(OPEN_ACL_UNSAFE, zkClient.getACL("/security.json", null, false)); + assertNotEquals(OPEN_ACL_UNSAFE, zkClient.getACL("/security.json", null)); } useZkCredentialsInjector(ConnectWithReadonlyCredsInjector.class); @@ -334,9 +330,8 @@ public void testRepairACL() throws Exception { .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build()) { NoAuthException e = - assertThrows( - NoAuthException.class, () -> zkClient.getData("/security.json", null, null, false)); - assertEquals("/security.json", e.getPath()); + assertThrows(NoAuthException.class, () -> zkClient.getData("/security.json", null, null)); + assertEquals("/solr/security.json", e.getPath()); } } @@ -401,27 +396,27 @@ protected static void doTest( boolean setData, boolean delete) throws Exception { - doTest(getData, () -> zkClient.getData(path, null, null, false)); - doTest(list, () -> zkClient.getChildren(path, null, false)); + doTest(getData, () -> zkClient.getData(path, null, null)); + doTest(list, () -> zkClient.getChildren(path, null)); doTest( create, () -> { - zkClient.create(path + "/subnode", null, CreateMode.PERSISTENT, false); - zkClient.delete(path + "/subnode", -1, false); + zkClient.create(path + "/subnode", null, CreateMode.PERSISTENT); + zkClient.delete(path + "/subnode", -1); }); doTest( create, () -> { zkClient.makePath(path + "/subnode/subsubnode", false); - zkClient.delete(path + "/subnode/subsubnode", -1, false); - zkClient.delete(path + "/subnode", -1, false); + zkClient.delete(path + "/subnode/subsubnode", -1); + zkClient.delete(path + "/subnode", -1); }); - doTest(setData, () -> zkClient.setData(path, (byte[]) null, false)); + doTest(setData, () -> zkClient.setData(path, (byte[]) null)); // Actually about the ACLs on /solr, but that is protected - doTest(delete, () -> zkClient.delete(path, -1, false)); + doTest(delete, () -> zkClient.delete(path, -1)); } interface ExceptingRunnable { diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/AbstractDistribZkTestBase.java b/solr/test-framework/src/java/org/apache/solr/cloud/AbstractDistribZkTestBase.java index 435a2a931ba..e8b104f9fcf 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/AbstractDistribZkTestBase.java +++ b/solr/test-framework/src/java/org/apache/solr/cloud/AbstractDistribZkTestBase.java @@ -395,6 +395,7 @@ protected void printLayout() throws Exception { protected void restartZk(int pauseMillis) throws Exception { log.info("Restarting ZK with a pause of {}ms in between", pauseMillis); + zkServer.shutdown(); // disconnect enough to test stalling, if things stall, then clientSoTimeout will be hit Thread.sleep(pauseMillis); diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/AbstractFullDistribZkTestBase.java b/solr/test-framework/src/java/org/apache/solr/cloud/AbstractFullDistribZkTestBase.java index e2f2074873d..c0f4ce77a69 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/AbstractFullDistribZkTestBase.java +++ b/solr/test-framework/src/java/org/apache/solr/cloud/AbstractFullDistribZkTestBase.java @@ -262,18 +262,14 @@ public void distribSetUp() throws Exception { .create( ZkStateReader.CLUSTER_PROPS, Utils.toJSON(Collections.singletonMap(URL_SCHEME, HTTPS)), - CreateMode.PERSISTENT, - true); + CreateMode.PERSISTENT); } catch (KeeperException.NodeExistsException e) { ZkNodeProps props = ZkNodeProps.load( - zkStateReader - .getZkClient() - .getData(ZkStateReader.CLUSTER_PROPS, null, null, true)); + zkStateReader.getZkClient().getData(ZkStateReader.CLUSTER_PROPS, null, null)); zkStateReader .getZkClient() - .setData( - ZkStateReader.CLUSTER_PROPS, Utils.toJSON(props.plus(URL_SCHEME, HTTPS)), true); + .setData(ZkStateReader.CLUSTER_PROPS, Utils.toJSON(props.plus(URL_SCHEME, HTTPS))); } } } diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/ChaosMonkey.java b/solr/test-framework/src/java/org/apache/solr/cloud/ChaosMonkey.java index 36bb09e12a4..439e2be77c6 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/ChaosMonkey.java +++ b/solr/test-framework/src/java/org/apache/solr/cloud/ChaosMonkey.java @@ -16,7 +16,6 @@ */ package org.apache.solr.cloud; -import java.io.IOException; import java.lang.invoke.MethodHandles; import java.util.ArrayList; import java.util.List; @@ -29,6 +28,7 @@ import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicInteger; import java.util.regex.Pattern; +import org.apache.curator.test.KillSession; import org.apache.lucene.tests.util.LuceneTestCase; import org.apache.solr.cloud.AbstractFullDistribZkTestBase.CloudJettyRunner; import org.apache.solr.common.cloud.DocCollection; @@ -48,8 +48,6 @@ import org.apache.solr.util.TestInjection; import org.apache.solr.util.TimeOut; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.TestableZooKeeper; -import org.apache.zookeeper.ZooKeeper; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -151,8 +149,9 @@ public void expireSession(final JettySolrRunner jetty) { CoreContainer cores = jetty.getCoreContainer(); if (cores != null) { monkeyLog("expire session for " + jetty.getLocalPort() + " !"); + long sessionId = cores.getZkController().getZkClient().getZkSessionId(); + zkServer.expire(sessionId); causeConnectionLoss(jetty); - zkServer.expire(cores.getZkController().getZkClient().getZooKeeper().getSessionId()); } } @@ -182,21 +181,11 @@ public static void causeConnectionLoss(JettySolrRunner jetty) { if (cores != null) { monkeyLog("Will cause connection loss on " + jetty.getLocalPort()); SolrZkClient zkClient = cores.getZkController().getZkClient(); - causeConnectionLoss(zkClient.getZooKeeper()); - } - } - - public static void causeConnectionLoss(ZooKeeper zooKeeper) { - assert zooKeeper instanceof TestableZooKeeper - : "Can only cause connection loss for TestableZookeeper"; - if (zooKeeper instanceof TestableZooKeeper) { try { - ((TestableZooKeeper) zooKeeper).testableConnloss(); - } catch (IOException ignored) { - // best effort + KillSession.kill(zkClient.getCuratorFramework().getZookeeperClient().getZooKeeper()); + } catch (Exception e) { + log.warn("Exception causing connection loss", e); } - } else { - // TODO what now? } } diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/MiniSolrCloudCluster.java b/solr/test-framework/src/java/org/apache/solr/cloud/MiniSolrCloudCluster.java index 3b8d4e1c774..84ed008a2a1 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/MiniSolrCloudCluster.java +++ b/solr/test-framework/src/java/org/apache/solr/cloud/MiniSolrCloudCluster.java @@ -54,6 +54,7 @@ import java.util.concurrent.atomic.AtomicReference; import java.util.function.Consumer; import javax.servlet.Filter; +import org.apache.curator.test.KillSession; import org.apache.lucene.tests.util.LuceneTestCase; import org.apache.solr.SolrTestCaseJ4; import org.apache.solr.client.solrj.embedded.SSLConfig; @@ -300,17 +301,16 @@ public MiniSolrCloudCluster( .withUrl(zkServer.getZkHost()) .withTimeout(AbstractZkTestCase.TIMEOUT, TimeUnit.MILLISECONDS) .build()) { - if (!zkClient.exists("/solr/solr.xml", true)) { - zkClient.makePath("/solr/solr.xml", solrXml.getBytes(Charset.defaultCharset()), true); + if (!zkClient.exists("/solr/solr.xml")) { + zkClient.makePath("/solr/solr.xml", solrXml.getBytes(Charset.defaultCharset())); if (jettyConfig.sslConfig != null && jettyConfig.sslConfig.isSSLMode()) { zkClient.makePath( "/solr" + ZkStateReader.CLUSTER_PROPS, - "{'urlScheme':'https'}".getBytes(StandardCharsets.UTF_8), - true); + "{'urlScheme':'https'}".getBytes(StandardCharsets.UTF_8)); } if (securityJson.isPresent()) { // configure Solr security zkClient.makePath( - "/solr/security.json", securityJson.get().getBytes(Charset.defaultCharset()), true); + "/solr/security.json", securityJson.get().getBytes(Charset.defaultCharset())); } } } @@ -645,9 +645,7 @@ public void deleteAllConfigSets() throws Exception { // cleanup any property before removing the configset getZkClient() .delete( - ZkConfigSetService.CONFIGS_ZKNODE + "/" + configSet + "/" + DEFAULT_FILENAME, - -1, - true); + ZkConfigSetService.CONFIGS_ZKNODE + "/" + configSet + "/" + DEFAULT_FILENAME, -1); } catch (KeeperException.NoNodeException nne) { } new ConfigSetAdminRequest.Delete().setConfigSetName(configSet).process(solrClient); @@ -736,10 +734,10 @@ public SolrZkClient getZkClient() { * Set data in zk without exposing caller to the ZK API, i.e. tests won't need to include * Zookeeper dependencies */ - public void zkSetData(String path, byte[] data, boolean retryOnConnLoss) + public void zkSetData(String path, byte[] data) throws InterruptedException { try { - getZkClient().setData(path, data, -1, retryOnConnLoss); + getZkClient().setData(path, data, -1); } catch (KeeperException e) { throw new SolrException(ErrorCode.UNKNOWN, "Failed writing to Zookeeper", e); } @@ -806,7 +804,14 @@ public void expireZkSession(JettySolrRunner jetty) { CoreContainer cores = jetty.getCoreContainer(); if (cores != null) { ChaosMonkey.causeConnectionLoss(jetty); - zkServer.expire(cores.getZkController().getZkClient().getZooKeeper().getSessionId()); + SolrZkClient zkClient = cores.getZkController().getZkClient(); + long sessionId = zkClient.getZkSessionId(); + zkServer.expire(sessionId); + try { + KillSession.kill(zkClient.getCuratorFramework().getZookeeperClient().getZooKeeper()); + } catch (Exception e) { + log.error("Exception killing session", e); + } if (log.isInfoEnabled()) { log.info("Expired zookeeper session from node {}", jetty.getBaseUrl()); } diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/MockSolrZkClient.java b/solr/test-framework/src/java/org/apache/solr/cloud/MockSolrZkClient.java index c1c73fb853a..e9bd640d101 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/MockSolrZkClient.java +++ b/solr/test-framework/src/java/org/apache/solr/cloud/MockSolrZkClient.java @@ -29,15 +29,13 @@ public MockSolrZkClient() { } @Override - public Boolean exists(final String path, boolean retryOnConnLoss) - throws KeeperException, InterruptedException { + public Boolean exists(final String path) throws KeeperException, InterruptedException { return false; } @Override - public byte[] getData( - final String path, final Watcher watcher, final Stat stat, boolean retryOnConnLoss) + public byte[] getData(final String path, final Watcher watcher, final Stat stat) throws KeeperException, InterruptedException { return null; } diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/ZkTestServer.java b/solr/test-framework/src/java/org/apache/solr/cloud/ZkTestServer.java index 4a2f97475d0..2cfd01b67a0 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/ZkTestServer.java +++ b/solr/test-framework/src/java/org/apache/solr/cloud/ZkTestServer.java @@ -45,7 +45,6 @@ import org.apache.solr.common.util.Utils; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException; -import org.apache.zookeeper.Op; import org.apache.zookeeper.WatchedEvent; import org.apache.zookeeper.Watcher; import org.apache.zookeeper.ZooDefs; @@ -503,7 +502,7 @@ public void ensurePathExists(String path) throws IOException { .withUrl(getZkHost()) .withTimeout(10000, TimeUnit.MILLISECONDS) .build()) { - client.makePath(path, null, CreateMode.PERSISTENT, null, false, true, 0); + client.makePath(path, null, CreateMode.PERSISTENT, null, false); } catch (InterruptedException | KeeperException e) { log.error("Error checking path {}", path, e); throw new IOException("Error checking path " + path, SolrZkClient.checkInterrupted(e)); @@ -786,7 +785,7 @@ public static void putConfig( if (log.isInfoEnabled()) { log.info("put {} to {}", file.toAbsolutePath(), destPath); } - zkClient.makePath(destPath, file, false, true); + zkClient.makePath(destPath, file, false); } // static to share with distrib test @@ -796,42 +795,26 @@ public void buildZooKeeper(Path solrhome, String config, String schema) throws E props.put("configName", "conf1"); final ZkNodeProps zkProps = new ZkNodeProps(props); - List ops = new ArrayList<>(2); - String path = "/collections"; - ops.add( - Op.create( - path, null, chRootClient.getZkACLProvider().getACLsToAdd(path), CreateMode.PERSISTENT)); - path = "/collections/collection1"; - ops.add( - Op.create( - path, - Utils.toJSON(zkProps), - chRootClient.getZkACLProvider().getACLsToAdd(path), - CreateMode.PERSISTENT)); - path = "/collections/collection1/shards"; - ops.add( - Op.create( - path, null, chRootClient.getZkACLProvider().getACLsToAdd(path), CreateMode.PERSISTENT)); - path = "/collections/control_collection"; - ops.add( - Op.create( - path, - Utils.toJSON(zkProps), - chRootClient.getZkACLProvider().getACLsToAdd(path), - CreateMode.PERSISTENT)); - path = "/collections/control_collection/shards"; - ops.add( - Op.create( - path, null, chRootClient.getZkACLProvider().getACLsToAdd(path), CreateMode.PERSISTENT)); - path = "/configs"; - ops.add( - Op.create( - path, null, chRootClient.getZkACLProvider().getACLsToAdd(path), CreateMode.PERSISTENT)); - path = "/configs/conf1"; - ops.add( - Op.create( - path, null, chRootClient.getZkACLProvider().getACLsToAdd(path), CreateMode.PERSISTENT)); - chRootClient.multi(ops, true); + chRootClient.multi( + op -> op.create().withMode(CreateMode.PERSISTENT).forPath("/collections", null), + op -> + op.create() + .withMode(CreateMode.PERSISTENT) + .forPath("/collections/collection1", Utils.toJSON(zkProps)), + op -> + op.create() + .withMode(CreateMode.PERSISTENT) + .forPath("/collections/collection1/shards", null), + op -> + op.create() + .withMode(CreateMode.PERSISTENT) + .forPath("/collections/control_collection", Utils.toJSON(zkProps)), + op -> + op.create() + .withMode(CreateMode.PERSISTENT) + .forPath("/collections/control_collection/shards", null), + op -> op.create().withMode(CreateMode.PERSISTENT).forPath("/configs", null), + op -> op.create().withMode(CreateMode.PERSISTENT).forPath("/configs/conf1", null)); // for now, always upload the config and schema to the canonical names putConfig("conf1", chRootClient, solrhome, config, "solrconfig.xml"); @@ -849,7 +832,7 @@ public void buildZooKeeper(Path solrhome, String config, String schema) throws E } public void makeSolrZkNode() throws Exception { - rootClient.makePath("/solr", false, true); + rootClient.makePath("/solr", false); } public void tryCleanSolrZkNode() throws Exception { @@ -857,7 +840,7 @@ public void tryCleanSolrZkNode() throws Exception { } void tryCleanPath(String path) throws Exception { - if (rootClient.exists(path, true)) { + if (rootClient.exists(path)) { rootClient.clean(path); } } diff --git a/solr/test-framework/src/java/org/apache/solr/cloud/api/collections/AbstractCollectionsAPIDistributedZkTestBase.java b/solr/test-framework/src/java/org/apache/solr/cloud/api/collections/AbstractCollectionsAPIDistributedZkTestBase.java index a414eb5fdbe..ed51f2ce357 100644 --- a/solr/test-framework/src/java/org/apache/solr/cloud/api/collections/AbstractCollectionsAPIDistributedZkTestBase.java +++ b/solr/test-framework/src/java/org/apache/solr/cloud/api/collections/AbstractCollectionsAPIDistributedZkTestBase.java @@ -115,9 +115,7 @@ public void testCreationAndDeletion() throws Exception { CollectionAdminRequest.listCollections(cluster.getSolrClient()).contains(collectionName)); assertFalse( - cluster - .getZkClient() - .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName, true)); + cluster.getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName)); } @Test @@ -125,7 +123,7 @@ public void deleteCollectionRemovesStaleZkCollectionsNode() throws Exception { String collectionName = "out_of_sync_collection"; // manually create a collections zknode - cluster.getZkClient().makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName, true); + cluster.getZkClient().makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName); CollectionAdminRequest.deleteCollection(collectionName).process(cluster.getSolrClient()); @@ -133,9 +131,7 @@ public void deleteCollectionRemovesStaleZkCollectionsNode() throws Exception { CollectionAdminRequest.listCollections(cluster.getSolrClient()).contains(collectionName)); assertFalse( - cluster - .getZkClient() - .exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName, true)); + cluster.getZkClient().exists(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName)); } @Test @@ -173,7 +169,7 @@ public void deleteCollectionOnlyInZk() throws Exception { final String collectionName = "onlyinzk"; // create the collections node, but nothing else - cluster.getZkClient().makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName, true); + cluster.getZkClient().makePath(ZkStateReader.COLLECTIONS_ZKNODE + "/" + collectionName); // delete via API - should remove collections node CollectionAdminRequest.deleteCollection(collectionName).process(cluster.getSolrClient()); diff --git a/versions.lock b/versions.lock index 6ecfefc94f4..dd3afc7b6fe 100644 --- a/versions.lock +++ b/versions.lock @@ -44,7 +44,7 @@ com.google.cloud:google-cloud-storage:2.27.0 (2 constraints: d71c8a27) com.google.code.gson:gson:2.10.1 (7 constraints: 005f69b0) com.google.errorprone:error_prone_annotations:2.22.0 (11 constraints: 6e891f5a) com.google.guava:failureaccess:1.0.1 (2 constraints: f9199e37) -com.google.guava:guava:32.1.2-jre (26 constraints: 407b586c) +com.google.guava:guava:32.1.2-jre (27 constraints: 498a9992) com.google.guava:guava-parent:32.1.2-jre (1 constraints: b80ba5eb) com.google.guava:listenablefuture:9999.0-empty-to-avoid-conflict-with-guava (2 constraints: 4b35b0a0) com.google.http-client:google-http-client:1.43.3 (11 constraints: 3fbf96b4) @@ -89,7 +89,7 @@ edu.ucar:netcdf4:4.5.5 (1 constraints: 650c0402) edu.ucar:udunits:4.5.5 (1 constraints: 2b06034e) edu.usc.ir:sentiment-analysis-parser:0.1 (1 constraints: fa0b50e9) io.dropwizard.metrics:metrics-annotation:4.2.20 (1 constraints: 30106db0) -io.dropwizard.metrics:metrics-core:4.2.20 (5 constraints: 3344adfc) +io.dropwizard.metrics:metrics-core:4.2.20 (6 constraints: 015254da) io.dropwizard.metrics:metrics-graphite:4.2.20 (1 constraints: 3a05413b) io.dropwizard.metrics:metrics-jetty10:4.2.20 (1 constraints: 3a05413b) io.dropwizard.metrics:metrics-jmx:4.2.20 (1 constraints: 3a05413b) @@ -180,6 +180,7 @@ org.apache.commons:commons-text:1.10.0 (1 constraints: d911adf8) org.apache.curator:curator-client:5.5.0 (2 constraints: e81468a3) org.apache.curator:curator-framework:5.5.0 (2 constraints: 05144b75) org.apache.curator:curator-recipes:5.5.0 (1 constraints: 0c051336) +org.apache.curator:curator-test:5.5.0 (1 constraints: 0c051336) org.apache.hadoop:hadoop-annotations:3.3.6 (1 constraints: 0e050936) org.apache.hadoop:hadoop-auth:3.3.6 (1 constraints: 0e050936) org.apache.hadoop:hadoop-client-api:3.3.6 (3 constraints: 25280861) @@ -256,7 +257,7 @@ org.apache.tika:tika-core:1.28.5 (2 constraints: d8118f11) org.apache.tika:tika-parsers:1.28.5 (1 constraints: 42054a3b) org.apache.tomcat:annotations-api:6.0.53 (1 constraints: 40054e3b) org.apache.xmlbeans:xmlbeans:5.0.3 (2 constraints: 72173075) -org.apache.zookeeper:zookeeper:3.9.1 (2 constraints: 9d13795f) +org.apache.zookeeper:zookeeper:3.9.1 (1 constraints: 0f051636) org.apache.zookeeper:zookeeper-jute:3.9.1 (2 constraints: 9b128823) org.apiguardian:apiguardian-api:1.1.2 (2 constraints: 601bd5a8) org.bitbucket.b_c:jose4j:0.9.3 (1 constraints: 0e050936) @@ -329,12 +330,15 @@ org.jetbrains.kotlin:kotlin-stdlib-common:1.8.22 (3 constraints: 3a2cc871) org.jetbrains.kotlin:kotlin-stdlib-jdk7:1.8.0 (1 constraints: b01019c2) org.jetbrains.kotlin:kotlin-stdlib-jdk8:1.8.0 (4 constraints: dd389ae5) org.junit:junit-bom:5.9.1 (7 constraints: 1974131b) +org.junit.jupiter:junit-jupiter-api:5.9.1 (5 constraints: 5c467228) +org.junit.platform:junit-platform-commons:1.9.1 (3 constraints: ee29f32b) org.locationtech.jts:jts-core:1.19.0 (2 constraints: a31de760) org.locationtech.jts.io:jts-io-common:1.19.0 (1 constraints: 930d513a) org.locationtech.proj4j:proj4j:1.2.2 (1 constraints: 5d0daf2c) org.locationtech.spatial4j:spatial4j:0.8 (1 constraints: 59105498) org.opengis:geoapi:3.0.1 (7 constraints: 1361d046) org.openjdk.jmh:jmh-core:1.37 (1 constraints: df04fc30) +org.opentest4j:opentest4j:1.2.0 (2 constraints: cd205b49) org.osgi:org.osgi.resource:1.0.0 (1 constraints: e60f2999) org.osgi:org.osgi.service.serviceloader:1.0.0 (1 constraints: e60f2999) org.osgi:osgi.annotation:8.1.0 (1 constraints: 0b051636) @@ -354,7 +358,7 @@ org.tallison:metadata-extractor:2.17.1.0 (1 constraints: f00c3b28) org.tallison.xmp:xmpcore-shaded:6.1.10 (1 constraints: 300e8d49) org.threeten:threetenbp:1.6.8 (4 constraints: 2433e267) org.tukaani:xz:1.9 (1 constraints: 030c5be9) -org.xerial.snappy:snappy-java:1.1.10.5 (4 constraints: b538b6ff) +org.xerial.snappy:snappy-java:1.1.10.5 (5 constraints: 8246292b) software.amazon.awssdk:annotations:2.20.155 (20 constraints: 812ebbc3) software.amazon.awssdk:apache-client:2.20.155 (4 constraints: bd2a0d69) software.amazon.awssdk:arns:2.20.155 (2 constraints: 79184eec) @@ -436,16 +440,13 @@ org.hdrhistogram:HdrHistogram:2.1.12 (1 constraints: 520d2029) org.hsqldb:hsqldb:2.7.2 (1 constraints: 0d050c36) org.jetbrains.kotlin:kotlin-reflect:1.8.22 (2 constraints: 6724ece2) org.junit.jupiter:junit-jupiter:5.9.1 (3 constraints: 844699a3) -org.junit.jupiter:junit-jupiter-api:5.9.1 (4 constraints: 8b386434) org.junit.jupiter:junit-jupiter-engine:5.9.1 (2 constraints: 2117d63c) org.junit.jupiter:junit-jupiter-params:5.9.1 (2 constraints: 2117d63c) -org.junit.platform:junit-platform-commons:1.9.1 (3 constraints: ee29f32b) org.junit.platform:junit-platform-engine:1.9.1 (2 constraints: bc19e1f3) org.latencyutils:LatencyUtils:2.0.3 (1 constraints: 210dcd1b) org.mockito:mockito-core:5.5.0 (2 constraints: d61174fd) org.mockito:mockito-subclass:5.5.0 (1 constraints: 0c051336) org.objenesis:objenesis:3.3 (1 constraints: b20a14bd) -org.opentest4j:opentest4j:1.2.0 (2 constraints: cd205b49) org.springframework:spring-aop:5.3.28 (2 constraints: de1e8f9a) org.springframework:spring-beans:5.3.28 (4 constraints: b03ac3c9) org.springframework:spring-context:5.3.28 (2 constraints: 6f1fced2)