@Test
public void replicationWithOutOfOrderPostAndUpdates() throws Throwable {

    // This test verifies that if a replica receives
    // replication requests of POST and PATCH/PUT
    // out-of-order, for persistent services, xenon
    // can still handle it.
    setUp(this.nodeCount);
    this.host.joinNodesAndVerifyConvergence(this.host.getPeerCount());
    this.host.setNodeGroupQuorum(this.nodeCount / 2 + 1);
    waitForReplicatedFactoryServiceAvailable(
            this.host.getPeerServiceUri(ExampleService.FACTORY_LINK),
            ServiceUriPaths.DEFAULT_NODE_SELECTOR);
    waitForReplicationFactoryConvergence();
    ExampleServiceState state = new ExampleServiceState();
    state.name = "testing";
    state.counter = 1L;
    VerificationHost peer = this.host.getPeerHost();
    Map<String, ExampleServiceState> exampleStatesPerSelfLink = new HashMap<>();
    TestContext ctx = this.host.testCreate(this.serviceCount * this.updateCount);
    for (int i = 0; i < this.serviceCount; i++) {
        Operation post = Operation
                .createPost(peer, ExampleService.FACTORY_LINK)
                .setBody(state)
                .setReferer(this.host.getUri())
                .setCompletion((o, e) -> {
                    if (e != null) {
                        ctx.failIteration(e);
                        return;
                    }
                    ExampleServiceState rsp = o.getBody(ExampleServiceState.class);
                    for (int k = 0; k < this.updateCount; k++) {
                        ExampleServiceState update = new ExampleServiceState();
                        state.counter = (long) k;
                        Operation patch = Operation
                                .createPatch(peer, rsp.documentSelfLink)
                                .setBody(update)
                                .setReferer(this.host.getUri())
                                .setCompletion((op, ex) -> {
                                    if (ex != null) {
                                        ctx.failIteration(ex);
                                        return;
                                    }
                                    ExampleServiceState updatedState = op.getBody(ExampleServiceState.class);
                                    exampleStatesPerSelfLink.put(rsp.documentSelfLink, updatedState);
                                    ctx.completeIteration();
                                });
                        this.host.sendRequest(patch);
                    }
                });
        this.host.sendRequest(post);
    }
    ctx.await();
    this.host.waitForReplicatedFactoryChildServiceConvergence(
            getFactoriesPerNodeGroup(ExampleService.FACTORY_LINK),
            exampleStatesPerSelfLink,
            this.exampleStateConvergenceChecker,
            exampleStatesPerSelfLink.size(),
            this.updateCount,
            this.replicationFactor);
}