private List<OpResult> multi(ZooKeeper zk, Iterable<Op> ops) throws KeeperException, InterruptedException { if (useAsync) { final MultiResult res = new MultiResult(); zk.multi(ops, new MultiCallback() { @Override public void processResult(int rc, String path, Object ctx, List<OpResult> opResults) { synchronized (res) { res.rc = rc; res.results = opResults; res.finished = true; res.notifyAll(); } } }, null); synchronized (res) { while (!res.finished) { res.wait(); } } if (KeeperException.Code.OK.intValue() != res.rc) { KeeperException ke = KeeperException.create(KeeperException.Code.get(res.rc)); throw ke; } return res.results; } else { return zk.multi(ops); } }
private List<OpResult> commit(Transaction txn) throws KeeperException, InterruptedException { if (useAsync) { final MultiResult res = new MultiResult(); txn.commit(new MultiCallback() { @Override public void processResult(int rc, String path, Object ctx, List<OpResult> opResults) { synchronized (res) { res.rc = rc; res.results = opResults; res.finished = true; res.notifyAll(); } } }, null); synchronized (res) { while (!res.finished) { res.wait(); } } if (KeeperException.Code.OK.intValue() != res.rc) { KeeperException ke = KeeperException.create(KeeperException.Code.get(res.rc)); throw ke; } return res.results; } else { return txn.commit(); } }
/** * The asynchronous version of multi. * * @see #multi(Iterable) */ public void multi(Iterable<Op> ops, MultiCallback cb, Object ctx) { List<OpResult> results = validatePath(ops); if (results.size() > 0) { cb.processResult(KeeperException.Code.BADARGUMENTS.intValue(), null, ctx, results); return; } multiInternal(generateMultiTransaction(ops), cb, ctx); }
public void commit(MultiCallback cb, Object ctx) { zk.multi(ops, cb, ctx); }
@Test public void TestGetResults() throws Exception { /* Delete of a node folowed by an update of the (now) deleted node */ Iterable<Op> ops = Arrays.asList( Op.create("/multi", new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT), Op.delete("/multi", 0), Op.setData("/multi", "Y".getBytes(), 0), Op.create("/foo", new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT) ); List<OpResult> results = null; if (useAsync) { final MultiResult res = new MultiResult(); zk.multi(ops, new MultiCallback() { @Override public void processResult(int rc, String path, Object ctx, List<OpResult> opResults) { synchronized (res) { res.rc = rc; res.results = opResults; res.finished = true; res.notifyAll(); } } }, null); synchronized (res) { while (!res.finished) { res.wait(); } } Assert.assertFalse("/multi should have been deleted so setData should have failed", KeeperException.Code.OK.intValue() == res.rc); Assert.assertNull(zk.exists("/multi", null)); results = res.results; } else { try { zk.multi(ops); Assert.fail("/multi should have been deleted so setData should have failed"); } catch (KeeperException e) { // '/multi' should never have been created as entire op should fail Assert.assertNull(zk.exists("/multi", null)); results = e.getResults(); } } Assert.assertNotNull(results); for (OpResult r : results) { LOG.info("RESULT==> " + r); if (r instanceof ErrorResult) { ErrorResult er = (ErrorResult) r; LOG.info("ERROR RESULT: " + er + " ERR=>" + KeeperException.Code.get(er.getErr())); } } }
protected void multiInternal(MultiTransactionRecord request, MultiCallback cb, Object ctx) { RequestHeader h = new RequestHeader(); h.setType(ZooDefs.OpCode.multi); MultiResponse response = new MultiResponse(); cnxn.queuePacket(h, new ReplyHeader(), request, response, cb, null, null, ctx, null); }
@Test public void testGetResults() throws Exception { /* Delete of a node folowed by an update of the (now) deleted node */ Iterable<Op> ops = Arrays.asList( Op.create("/multi", new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT), Op.delete("/multi", 0), Op.setData("/multi", "Y".getBytes(), 0), Op.create("/foo", new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT) ); List<OpResult> results = null; if (useAsync) { final MultiResult res = new MultiResult(); zk.multi(ops, new MultiCallback() { @Override public void processResult(int rc, String path, Object ctx, List<OpResult> opResults) { synchronized (res) { res.rc = rc; res.results = opResults; res.finished = true; res.notifyAll(); } } }, null); synchronized (res) { while (!res.finished) { res.wait(); } } Assert.assertFalse("/multi should have been deleted so setData should have failed", KeeperException.Code.OK.intValue() == res.rc); Assert.assertNull(zk.exists("/multi", null)); results = res.results; } else { try { zk.multi(ops); Assert.fail("/multi should have been deleted so setData should have failed"); } catch (KeeperException e) { // '/multi' should never have been created as entire op should fail Assert.assertNull(zk.exists("/multi", null)); results = e.getResults(); } } Assert.assertNotNull(results); for (OpResult r : results) { LOG.info("RESULT==> {}", r); if (r instanceof ErrorResult) { ErrorResult er = (ErrorResult) r; LOG.info("ERROR RESULT: {} ERR=>{}", er, KeeperException.Code.get(er.getErr())); } } }
/** * ZOOKEEPER-1624: PendingChanges of create sequential node request didn't * get rollbacked correctly when multi-op failed. This cause * create sequential node request in subsequent multi-op to failed because * sequential node name generation is incorrect. * * The check is to make sure that each request in multi-op failed with * the correct reason. */ @Test public void testSequentialNodeCreateInAsyncMulti() throws Exception { final int iteration = 4; final List<MultiResult> results = new ArrayList<MultiResult>(); pendingOps.set(iteration); List<Op> ops = Arrays.asList( Op.create("/node-", new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT_SEQUENTIAL), Op.create("/dup", new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT)); for (int i = 0; i < iteration; ++i) { zk.multi(ops, new MultiCallback() { @Override public void processResult(int rc, String path, Object ctx, List<OpResult> opResults) { MultiResult result = new MultiResult(); result.results = opResults; result.rc = rc; results.add(result); finishPendingOps(); } }, null); } waitForPendingOps(CONNECTION_TIMEOUT); // Check that return code of all request are correct assertEquals(KeeperException.Code.OK.intValue(), results.get(0).rc); assertEquals(KeeperException.Code.NODEEXISTS.intValue(), results.get(1).rc); assertEquals(KeeperException.Code.NODEEXISTS.intValue(), results.get(2).rc); assertEquals(KeeperException.Code.NODEEXISTS.intValue(), results.get(3).rc); // Check that the first operation is successful in all request assertTrue(results.get(0).results.get(0) instanceof CreateResult); assertEquals(KeeperException.Code.OK.intValue(), ((ErrorResult) results.get(1).results.get(0)).getErr()); assertEquals(KeeperException.Code.OK.intValue(), ((ErrorResult) results.get(2).results.get(0)).getErr()); assertEquals(KeeperException.Code.OK.intValue(), ((ErrorResult) results.get(3).results.get(0)).getErr()); // Check that the second operation failed after the first request assertEquals(KeeperException.Code.NODEEXISTS.intValue(), ((ErrorResult) results.get(1).results.get(1)).getErr()); assertEquals(KeeperException.Code.NODEEXISTS.intValue(), ((ErrorResult) results.get(2).results.get(1)).getErr()); assertEquals(KeeperException.Code.NODEEXISTS.intValue(), ((ErrorResult) results.get(3).results.get(1)).getErr()); }
@Test public void testGetResults() throws Exception { /* Delete of a node folowed by an update of the (now) deleted node */ Iterable<Op> ops = Arrays.asList( Op.create("/multi", new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT), Op.delete("/multi", 0), Op.setData("/multi", "Y".getBytes(), 0), Op.create("/foo", new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT) ); List<OpResult> results = null; if (useAsync) { final MultiResult res = new MultiResult(); zk.multi(ops, new MultiCallback() { @Override public void processResult(int rc, String path, Object ctx, List<OpResult> opResults) { synchronized (res) { res.rc = rc; res.results = opResults; res.finished = true; res.notifyAll(); } } }, null); synchronized (res) { while (!res.finished) { res.wait(); } } Assert.assertFalse("/multi should have been deleted so setData should have failed", KeeperException.Code.OK.intValue() == res.rc); Assert.assertNull(zk.exists("/multi", null)); results = res.results; } else { try { zk.multi(ops); Assert.fail("/multi should have been deleted so setData should have failed"); } catch (KeeperException e) { // '/multi' should never have been created as entire op should fail Assert.assertNull(zk.exists("/multi", null)); results = e.getResults(); } } Assert.assertNotNull(results); for (OpResult r : results) { LOG.info("RESULT==> " + r); if (r instanceof ErrorResult) { ErrorResult er = (ErrorResult) r; LOG.info("ERROR RESULT: " + er + " ERR=>" + KeeperException.Code.get(er.getErr())); } } }