Repository: cassandra
Updated Branches:
  refs/heads/trunk 795c1f36e -> 471835815


Add additional unit tests for batch behavior, TTLs, Timestamps

Patch by Jeff Jirsa; Reviewed by Jason Brown for CASSANDRA-13846


Project: http://git-wip-us.apache.org/repos/asf/cassandra/repo
Commit: http://git-wip-us.apache.org/repos/asf/cassandra/commit/47183581
Tree: http://git-wip-us.apache.org/repos/asf/cassandra/tree/47183581
Diff: http://git-wip-us.apache.org/repos/asf/cassandra/diff/47183581

Branch: refs/heads/trunk
Commit: 471835815811d4de42474a3e3899a42cb6d969ce
Parents: 795c1f3
Author: Jeff Jirsa <jji...@apple.com>
Authored: Sun Jul 9 16:16:29 2017 -0700
Committer: Jeff Jirsa <jji...@apple.com>
Committed: Mon Sep 11 15:59:44 2017 -0700

----------------------------------------------------------------------
 CHANGES.txt                                     |   1 +
 .../apache/cassandra/batchlog/BatchTest.java    | 107 -------
 .../apache/cassandra/batchlog/BatchlogTest.java | 107 +++++++
 .../cql3/validation/entities/CountersTest.java  |  68 ++++
 .../cql3/validation/entities/TimestampTest.java |  37 +++
 .../cql3/validation/operations/BatchTest.java   | 320 ++++++++++++++++++-
 6 files changed, 528 insertions(+), 112 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cassandra/blob/47183581/CHANGES.txt
----------------------------------------------------------------------
diff --git a/CHANGES.txt b/CHANGES.txt
index 5e9cb72..c688d6d 100644
--- a/CHANGES.txt
+++ b/CHANGES.txt
@@ -1,4 +1,5 @@
 4.0
+ * Add additional unit tests for batch behavior, TTLs, Timestamps 
(CASSANDRA-13846)
  * Add keyspace and table name in schema validation exception (CASSANDRA-13845)
  * Emit metrics whenever we hit tombstone failures and warn thresholds 
(CASSANDRA-13771)
  * Make netty EventLoopGroups daemon threads (CASSANDRA-13837)

http://git-wip-us.apache.org/repos/asf/cassandra/blob/47183581/test/unit/org/apache/cassandra/batchlog/BatchTest.java
----------------------------------------------------------------------
diff --git a/test/unit/org/apache/cassandra/batchlog/BatchTest.java 
b/test/unit/org/apache/cassandra/batchlog/BatchTest.java
deleted file mode 100644
index 8ed1811..0000000
--- a/test/unit/org/apache/cassandra/batchlog/BatchTest.java
+++ /dev/null
@@ -1,107 +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.cassandra.batchlog;
-
-import java.io.IOException;
-import java.nio.ByteBuffer;
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-import java.util.UUID;
-
-import org.junit.BeforeClass;
-import org.junit.Test;
-
-import org.apache.cassandra.SchemaLoader;
-import org.apache.cassandra.schema.TableMetadata;
-import org.apache.cassandra.db.Keyspace;
-import org.apache.cassandra.db.Mutation;
-import org.apache.cassandra.db.RowUpdateBuilder;
-import org.apache.cassandra.db.marshal.BytesType;
-import org.apache.cassandra.exceptions.ConfigurationException;
-import org.apache.cassandra.io.util.DataInputBuffer;
-import org.apache.cassandra.io.util.DataInputPlus;
-import org.apache.cassandra.io.util.DataOutputBuffer;
-import org.apache.cassandra.net.MessagingService;
-import org.apache.cassandra.schema.KeyspaceParams;
-import org.apache.cassandra.utils.FBUtilities;
-import org.apache.cassandra.utils.UUIDGen;
-
-import static org.apache.cassandra.utils.ByteBufferUtil.bytes;
-import static org.junit.Assert.assertEquals;
-
-public class BatchTest
-{
-    private static final String KEYSPACE = "BatchRequestTest";
-    private static final String CF_STANDARD = "Standard";
-
-    @BeforeClass
-    public static void defineSchema() throws ConfigurationException
-    {
-        SchemaLoader.prepareServer();
-        SchemaLoader.createKeyspace(KEYSPACE,
-                                    KeyspaceParams.simple(1),
-                                    SchemaLoader.standardCFMD(KEYSPACE, 
CF_STANDARD, 1, BytesType.instance));
-    }
-
-    @Test
-    public void testSerialization() throws IOException
-    {
-        TableMetadata cfm = 
Keyspace.open(KEYSPACE).getColumnFamilyStore(CF_STANDARD).metadata();
-
-        long now = FBUtilities.timestampMicros();
-        int version = MessagingService.current_version;
-        UUID uuid = UUIDGen.getTimeUUID();
-
-        List<Mutation> mutations = new ArrayList<>(10);
-        for (int i = 0; i < 10; i++)
-        {
-            mutations.add(new RowUpdateBuilder(cfm, 
FBUtilities.timestampMicros(), bytes(i))
-                          .clustering("name" + i)
-                          .add("val", "val" + i)
-                          .build());
-        }
-
-        Batch batch1 = Batch.createLocal(uuid, now, mutations);
-        assertEquals(uuid, batch1.id);
-        assertEquals(now, batch1.creationTime);
-        assertEquals(mutations, batch1.decodedMutations);
-
-        DataOutputBuffer out = new DataOutputBuffer();
-        Batch.serializer.serialize(batch1, out, version);
-
-        assertEquals(out.getLength(), Batch.serializer.serializedSize(batch1, 
version));
-
-        DataInputPlus dis = new DataInputBuffer(out.getData());
-        Batch batch2 = Batch.serializer.deserialize(dis, version);
-
-        assertEquals(batch1.id, batch2.id);
-        assertEquals(batch1.creationTime, batch2.creationTime);
-        assertEquals(batch1.decodedMutations.size(), 
batch2.encodedMutations.size());
-
-        Iterator<Mutation> it1 = batch1.decodedMutations.iterator();
-        Iterator<ByteBuffer> it2 = batch2.encodedMutations.iterator();
-        while (it1.hasNext())
-        {
-            try (DataInputBuffer in = new DataInputBuffer(it2.next().array()))
-            {
-                assertEquals(it1.next().toString(), 
Mutation.serializer.deserialize(in, version).toString());
-            }
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/cassandra/blob/47183581/test/unit/org/apache/cassandra/batchlog/BatchlogTest.java
----------------------------------------------------------------------
diff --git a/test/unit/org/apache/cassandra/batchlog/BatchlogTest.java 
b/test/unit/org/apache/cassandra/batchlog/BatchlogTest.java
new file mode 100644
index 0000000..8fa4afc
--- /dev/null
+++ b/test/unit/org/apache/cassandra/batchlog/BatchlogTest.java
@@ -0,0 +1,107 @@
+/*
+ * 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.cassandra.batchlog;
+
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+import java.util.UUID;
+
+import org.junit.BeforeClass;
+import org.junit.Test;
+
+import org.apache.cassandra.SchemaLoader;
+import org.apache.cassandra.schema.TableMetadata;
+import org.apache.cassandra.db.Keyspace;
+import org.apache.cassandra.db.Mutation;
+import org.apache.cassandra.db.RowUpdateBuilder;
+import org.apache.cassandra.db.marshal.BytesType;
+import org.apache.cassandra.exceptions.ConfigurationException;
+import org.apache.cassandra.io.util.DataInputBuffer;
+import org.apache.cassandra.io.util.DataInputPlus;
+import org.apache.cassandra.io.util.DataOutputBuffer;
+import org.apache.cassandra.net.MessagingService;
+import org.apache.cassandra.schema.KeyspaceParams;
+import org.apache.cassandra.utils.FBUtilities;
+import org.apache.cassandra.utils.UUIDGen;
+
+import static org.apache.cassandra.utils.ByteBufferUtil.bytes;
+import static org.junit.Assert.assertEquals;
+
+public class BatchlogTest
+{
+    private static final String KEYSPACE = "BatchRequestTest";
+    private static final String CF_STANDARD = "Standard";
+
+    @BeforeClass
+    public static void defineSchema() throws ConfigurationException
+    {
+        SchemaLoader.prepareServer();
+        SchemaLoader.createKeyspace(KEYSPACE,
+                                    KeyspaceParams.simple(1),
+                                    SchemaLoader.standardCFMD(KEYSPACE, 
CF_STANDARD, 1, BytesType.instance));
+    }
+
+    @Test
+    public void testSerialization() throws IOException
+    {
+        TableMetadata cfm = 
Keyspace.open(KEYSPACE).getColumnFamilyStore(CF_STANDARD).metadata();
+
+        long now = FBUtilities.timestampMicros();
+        int version = MessagingService.current_version;
+        UUID uuid = UUIDGen.getTimeUUID();
+
+        List<Mutation> mutations = new ArrayList<>(10);
+        for (int i = 0; i < 10; i++)
+        {
+            mutations.add(new RowUpdateBuilder(cfm, 
FBUtilities.timestampMicros(), bytes(i))
+                          .clustering("name" + i)
+                          .add("val", "val" + i)
+                          .build());
+        }
+
+        Batch batch1 = Batch.createLocal(uuid, now, mutations);
+        assertEquals(uuid, batch1.id);
+        assertEquals(now, batch1.creationTime);
+        assertEquals(mutations, batch1.decodedMutations);
+
+        DataOutputBuffer out = new DataOutputBuffer();
+        Batch.serializer.serialize(batch1, out, version);
+
+        assertEquals(out.getLength(), Batch.serializer.serializedSize(batch1, 
version));
+
+        DataInputPlus dis = new DataInputBuffer(out.getData());
+        Batch batch2 = Batch.serializer.deserialize(dis, version);
+
+        assertEquals(batch1.id, batch2.id);
+        assertEquals(batch1.creationTime, batch2.creationTime);
+        assertEquals(batch1.decodedMutations.size(), 
batch2.encodedMutations.size());
+
+        Iterator<Mutation> it1 = batch1.decodedMutations.iterator();
+        Iterator<ByteBuffer> it2 = batch2.encodedMutations.iterator();
+        while (it1.hasNext())
+        {
+            try (DataInputBuffer in = new DataInputBuffer(it2.next().array()))
+            {
+                assertEquals(it1.next().toString(), 
Mutation.serializer.deserialize(in, version).toString());
+            }
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/cassandra/blob/47183581/test/unit/org/apache/cassandra/cql3/validation/entities/CountersTest.java
----------------------------------------------------------------------
diff --git 
a/test/unit/org/apache/cassandra/cql3/validation/entities/CountersTest.java 
b/test/unit/org/apache/cassandra/cql3/validation/entities/CountersTest.java
index 94e1c52..69ad4d3 100644
--- a/test/unit/org/apache/cassandra/cql3/validation/entities/CountersTest.java
+++ b/test/unit/org/apache/cassandra/cql3/validation/entities/CountersTest.java
@@ -238,4 +238,72 @@ public class CountersTest extends CQLTester
             assertRows(execute("SELECT k FROM %s"), row(0));
         }
     }
+
+    /*
+     * Check that a counter batch works as intended
+     */
+    @Test
+    public void testCounterBatch() throws Throwable
+    {
+        createTable("CREATE TABLE %s (userid int, url text, total counter, 
PRIMARY KEY (userid, url)) WITH COMPACT STORAGE");
+
+        // Ensure we handle updates to the same CQL row in the same partition 
properly
+        execute("BEGIN UNLOGGED BATCH " +
+                "UPDATE %1$s SET total = total + 1 WHERE userid = 1 AND url = 
'http://foo.com'; " +
+                "UPDATE %1$s SET total = total + 1 WHERE userid = 1 AND url = 
'http://foo.com'; " +
+                "UPDATE %1$s SET total = total + 1 WHERE userid = 1 AND url = 
'http://foo.com'; " +
+                "APPLY BATCH; ");
+        assertRows(execute("SELECT total FROM %s WHERE userid = 1 AND url = 
'http://foo.com'"),
+                row(3L));
+
+        // Ensure we handle different CQL rows in the same partition properly
+        execute("BEGIN UNLOGGED BATCH " +
+                "UPDATE %1$s SET total = total + 1 WHERE userid = 1 AND url = 
'http://bar.com'; " +
+                "UPDATE %1$s SET total = total + 1 WHERE userid = 1 AND url = 
'http://baz.com'; " +
+                "UPDATE %1$s SET total = total + 1 WHERE userid = 1 AND url = 
'http://bad.com'; " +
+                "APPLY BATCH; ");
+        assertRows(execute("SELECT url, total FROM %s WHERE userid = 1"),
+                row("http://bad.com";, 1L),
+                row("http://bar.com";, 1L),
+                row("http://baz.com";, 1L),
+                row("http://foo.com";, 3L)); // from previous batch
+
+        // Different counters in the same CQL Row
+        createTable("CREATE TABLE %s (userid int, url text, first counter, 
second counter, third counter, PRIMARY KEY (userid, url))");
+        execute("BEGIN UNLOGGED BATCH " +
+                "UPDATE %1$s SET first = first + 1 WHERE userid = 1 AND url = 
'http://foo.com'; " +
+                "UPDATE %1$s SET first = first + 1 WHERE userid = 1 AND url = 
'http://foo.com'; " +
+                "UPDATE %1$s SET second = second + 1 WHERE userid = 1 AND url 
= 'http://foo.com'; " +
+                "APPLY BATCH; ");
+        assertRows(execute("SELECT first, second, third FROM %s WHERE userid = 
1 AND url = 'http://foo.com'"),
+                row(2L, 1L, null));
+
+        // Different counters in different CQL Rows
+        execute("BEGIN UNLOGGED BATCH " +
+                "UPDATE %1$s SET first = first + 1 WHERE userid = 1 AND url = 
'http://bad.com'; " +
+                "UPDATE %1$s SET first = first + 1, second = second + 1 WHERE 
userid = 1 AND url = 'http://bar.com'; " +
+                "UPDATE %1$s SET first = first - 1, second = second - 1 WHERE 
userid = 1 AND url = 'http://bar.com'; " +
+                "UPDATE %1$s SET second = second + 1 WHERE userid = 1 AND url 
= 'http://baz.com'; " +
+                "APPLY BATCH; ");
+        assertRows(execute("SELECT url, first, second, third FROM %s WHERE 
userid = 1"),
+                row("http://bad.com";, 1L, null, null),
+                row("http://bar.com";, 0L, 0L, null),
+                row("http://baz.com";, null, 1L, null),
+                row("http://foo.com";, 2L, 1L, null)); // from previous batch
+
+
+        // Different counters in different partitions
+        execute("BEGIN UNLOGGED BATCH " +
+                "UPDATE %1$s SET first = first + 1 WHERE userid = 2 AND url = 
'http://bad.com'; " +
+                "UPDATE %1$s SET first = first + 1, second = second + 1 WHERE 
userid = 3 AND url = 'http://bar.com'; " +
+                "UPDATE %1$s SET first = first - 1, second = second - 1 WHERE 
userid = 4 AND url = 'http://bar.com'; " +
+                "UPDATE %1$s SET second = second + 1 WHERE userid = 5 AND url 
= 'http://baz.com'; " +
+                "APPLY BATCH; ");
+        assertRowsIgnoringOrder(execute("SELECT userid, url, first, second, 
third FROM %s WHERE userid IN (2, 3, 4, 5)"),
+                row(2, "http://bad.com";, 1L, null, null),
+                row(3, "http://bar.com";, 1L, 1L, null),
+                row(4, "http://bar.com";, -1L, -1L, null),
+                row(5, "http://baz.com";, null, 1L, null));
+
+    }
 }

http://git-wip-us.apache.org/repos/asf/cassandra/blob/47183581/test/unit/org/apache/cassandra/cql3/validation/entities/TimestampTest.java
----------------------------------------------------------------------
diff --git 
a/test/unit/org/apache/cassandra/cql3/validation/entities/TimestampTest.java 
b/test/unit/org/apache/cassandra/cql3/validation/entities/TimestampTest.java
index 985a5e0..ddc402c 100644
--- a/test/unit/org/apache/cassandra/cql3/validation/entities/TimestampTest.java
+++ b/test/unit/org/apache/cassandra/cql3/validation/entities/TimestampTest.java
@@ -182,4 +182,41 @@ public class TimestampTest extends CQLTester
                    row(3, 3, 3, 1L));
     }
 
+    @Test
+    public void testTimestampAndTTLPrepared() throws Throwable
+    {
+
+        createTable("CREATE TABLE %s (k int , c int, i int, PRIMARY KEY (k, 
c))");
+        execute("INSERT INTO %s (k, c, i) VALUES (1, 1, 1) USING TIMESTAMP ? 
AND TTL ?;", 1L,5);
+        execute("INSERT INTO %s (k, c) VALUES (1, 2) USING TIMESTAMP ? AND TTL 
? ;", 1L, 5);
+        execute("INSERT INTO %s (k, c, i) VALUES (1, 3, 1) USING TIMESTAMP ? 
AND TTL ?;", 1L, 5);
+        execute("INSERT INTO %s (k, c) VALUES (2, 2) USING TIMESTAMP ? AND TTL 
?;", 2L, 5);
+        execute("INSERT INTO %s (k, c, i) VALUES (3, 3, 3) USING TIMESTAMP ? 
AND TTL ?;", 1L, 5);
+        assertRows(execute("SELECT k, c, i, writetime(i) FROM %s "),
+                row(1, 1, 1, 1L),
+                row(1, 2, null, null),
+                row(1, 3, 1, 1L),
+                row(2, 2, null, null),
+                row(3, 3, 3, 1L));
+        Thread.sleep(6*1000);
+        assertEmpty(execute("SELECT k, c, i, writetime(i) FROM %s "));
+    }
+
+    @Test
+    public void testTimestampAndTTLUpdatePrepared() throws Throwable
+    {
+
+        createTable("CREATE TABLE %s (k int , c int, i int, PRIMARY KEY (k, 
c))");
+        execute("UPDATE %s USING TIMESTAMP ? AND TTL ? SET i=1 WHERE k=1 AND c 
= 1 ;", 1L, 5);
+        execute("UPDATE %s USING TIMESTAMP ? AND TTL ? SET i=1 WHERE k=1 AND c 
= 3 ;", 1L, 5);
+        execute("UPDATE %s USING TIMESTAMP ? AND TTL ? SET i=1 WHERE k=2 AND c 
= 2 ;", 2L, 5);
+        execute("UPDATE %s USING TIMESTAMP ? AND TTL ? SET i=3 WHERE k=3 AND c 
= 3 ;", 1L, 5);
+        assertRows(execute("SELECT k, c, i, writetime(i) FROM %s "),
+                row(1, 1, 1, 1L),
+                row(1, 3, 1, 1L),
+                row(2, 2, 1, 2L),
+                row(3, 3, 3, 1L));
+        Thread.sleep(6*1000);
+        assertEmpty(execute("SELECT k, c, i, writetime(i) FROM %s "));
+    }
 }

http://git-wip-us.apache.org/repos/asf/cassandra/blob/47183581/test/unit/org/apache/cassandra/cql3/validation/operations/BatchTest.java
----------------------------------------------------------------------
diff --git 
a/test/unit/org/apache/cassandra/cql3/validation/operations/BatchTest.java 
b/test/unit/org/apache/cassandra/cql3/validation/operations/BatchTest.java
index d0bdd15..ae93b6e 100644
--- a/test/unit/org/apache/cassandra/cql3/validation/operations/BatchTest.java
+++ b/test/unit/org/apache/cassandra/cql3/validation/operations/BatchTest.java
@@ -241,7 +241,7 @@ public class BatchTest extends CQLTester
     }
 
     @Test
-    public void testBatchAndConditionalInteraction() throws Throwable
+    public void testBatchTTLConditionalInteraction() throws Throwable
     {
 
         createTable(String.format("CREATE TABLE %s.clustering (\n" +
@@ -256,10 +256,16 @@ public class BatchTest extends CQLTester
         execute("DELETE FROM " + KEYSPACE +".clustering WHERE id=1");
 
         String clusteringInsert = "INSERT INTO " + KEYSPACE + ".clustering(id, 
clustering1, clustering2, clustering3, val) VALUES(%s, %s, %s, %s, %s); ";
+        String clusteringTTLInsert = "INSERT INTO " + KEYSPACE + 
".clustering(id, clustering1, clustering2, clustering3, val) VALUES(%s, %s, %s, 
%s, %s) USING TTL %s; ";
+        String clusteringConditionalInsert = "INSERT INTO " + KEYSPACE + 
".clustering(id, clustering1, clustering2, clustering3, val) VALUES(%s, %s, %s, 
%s, %s) IF NOT EXISTS; ";
+        String clusteringConditionalTTLInsert = "INSERT INTO " + KEYSPACE + 
".clustering(id, clustering1, clustering2, clustering3, val) VALUES(%s, %s, %s, 
%s, %s)  IF NOT EXISTS USING TTL %s; ";
         String clusteringUpdate = "UPDATE " + KEYSPACE + ".clustering SET 
val=%s WHERE id=%s AND clustering1=%s AND clustering2=%s AND clustering3=%s ;";
+        String clusteringTTLUpdate = "UPDATE " + KEYSPACE + ".clustering USING 
TTL %s SET val=%s WHERE id=%s AND clustering1=%s AND clustering2=%s AND 
clustering3=%s ;";
         String clusteringConditionalUpdate = "UPDATE " + KEYSPACE + 
".clustering SET val=%s WHERE id=%s AND clustering1=%s AND clustering2=%s AND 
clustering3=%s IF val=%s ;";
+        String clusteringConditionalTTLUpdate = "UPDATE " + KEYSPACE + 
".clustering USING TTL %s SET val=%s WHERE id=%s AND clustering1=%s AND 
clustering2=%s AND clustering3=%s IF val=%s ;";
         String clusteringDelete = "DELETE FROM " + KEYSPACE + ".clustering 
WHERE id=%s AND clustering1=%s AND clustering2=%s AND clustering3=%s ;";
         String clusteringRangeDelete = "DELETE FROM " + KEYSPACE + 
".clustering WHERE id=%s AND clustering1=%s ;";
+        String clusteringConditionalDelete = "DELETE FROM " + KEYSPACE + 
".clustering WHERE id=%s AND clustering1=%s AND clustering2=%s AND 
clustering3=%s IF val=%s ; ";
 
 
         execute("BEGIN BATCH " + String.format(clusteringInsert, 1, 1, 1, 1, 
1) + " APPLY BATCH");
@@ -300,7 +306,6 @@ public class BatchTest extends CQLTester
         cmd4.append("APPLY BATCH ");
         execute(cmd4.toString());
 
-        System.out.println(execute("SELECT * FROM " + KEYSPACE+".clustering 
WHERE id=1"));
         assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
                 row(1, 1, 1, 2, 234),
                 row(1, 1, 2, 3, 23),
@@ -314,7 +319,6 @@ public class BatchTest extends CQLTester
         cmd5.append("APPLY BATCH ");
         execute(cmd5.toString());
 
-        System.out.println(execute("SELECT * FROM " + KEYSPACE+".clustering 
WHERE id=1"));
         assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
                 row(1, 1, 1, 2, 1234),
                 row(1, 1, 2, 3, 23)
@@ -327,7 +331,6 @@ public class BatchTest extends CQLTester
         cmd6.append("APPLY BATCH ");
         execute(cmd6.toString());
 
-        System.out.println(execute("SELECT * FROM " + KEYSPACE+".clustering 
WHERE id=1"));
         assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
                 row(1, 1, 1, 2, 1),
                 row(1, 1, 2, 3, 23),
@@ -342,12 +345,319 @@ public class BatchTest extends CQLTester
         cmd7.append("APPLY BATCH ");
         execute(cmd7.toString());
 
-        System.out.println(execute("SELECT * FROM " + KEYSPACE+".clustering 
WHERE id=1"));
         assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
                 row(1, 1, 1, 2, 1),
                 row(1, 1, 2, 3, 23),
                 row(1, 3, 4, 5, 345)
         );
+
+        StringBuilder cmd8 = new StringBuilder();
+        cmd8.append("BEGIN BATCH ");
+        cmd8.append(String.format(clusteringConditionalDelete, 1, 3, 4, 5, 
345));
+        cmd8.append(String.format(clusteringRangeDelete, 1, 1));
+        cmd8.append(String.format(clusteringInsert, 1, 2, 3, 4, 5));
+        cmd8.append("APPLY BATCH ");
+        execute(cmd8.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
+                row(1, 2, 3, 4, 5)
+        );
+
+        StringBuilder cmd9 = new StringBuilder();
+        cmd9.append("BEGIN BATCH ");
+        cmd9.append(String.format(clusteringConditionalInsert, 1, 3, 4, 5, 
345));
+        cmd9.append(String.format(clusteringDelete, 1, 2, 3, 4));
+        cmd9.append("APPLY BATCH ");
+        execute(cmd9.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
+                row(1, 3, 4, 5, 345)
+        );
+
+        StringBuilder cmd10 = new StringBuilder();
+        cmd10.append("BEGIN BATCH ");
+        cmd10.append(String.format(clusteringTTLInsert, 1, 2, 3, 4, 5, 5));
+        cmd10.append(String.format(clusteringConditionalTTLUpdate, 10, 5, 1, 
3, 4, 5, 345));
+        cmd10.append("APPLY BATCH ");
+        execute(cmd10.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
+                row(1, 2, 3, 4, 5), // 5 second TTL
+                row(1, 3, 4, 5, 5)  // 10 second TTL
+        );
+
+        Thread.sleep(6000);
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
+                row(1, 3, 4, 5, 5) // now 4 second TTL
+        );
+
+        StringBuilder cmd11 = new StringBuilder();
+        cmd11.append("BEGIN BATCH ");
+        cmd11.append(String.format(clusteringConditionalTTLInsert, 1, 2, 3, 4, 
5, 5));
+        cmd11.append(String.format(clusteringInsert,1, 4, 5, 6, 7));
+        cmd11.append("APPLY BATCH ");
+        execute(cmd11.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
+                row(1, 2, 3, 4, 5), // This one has 5 seconds left
+                row(1, 3, 4, 5, 5), // This one should have 4 seconds left
+                row(1, 4, 5, 6, 7) // This one has no TTL
+        );
+
+        Thread.sleep(6000);
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
+                row(1, 3, 4, 5, null), // We had a row here before from cmd9, 
but we've ttl'd out the value in cmd11
+                row(1, 4, 5, 6, 7)
+        );
+
+        StringBuilder cmd12 = new StringBuilder();
+        cmd12.append("BEGIN BATCH ");
+        cmd12.append(String.format(clusteringConditionalTTLUpdate, 5, 5, 1, 3, 
4, 5, null));
+        cmd12.append(String.format(clusteringTTLUpdate, 5, 8, 1, 4, 5, 6));
+        cmd12.append("APPLY BATCH ");
+        execute(cmd12.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
+                row(1, 3, 4, 5, 5),
+                row(1, 4, 5, 6, 8)
+        );
+
+        Thread.sleep(6000);
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering WHERE 
id=1"),
+                row(1, 3, 4, 5, null),
+                row(1, 4, 5, 6, null)
+        );
+    }
+
+
+    @Test
+    public void testBatchStaticTTLConditionalInteraction() throws Throwable
+    {
+
+        createTable(String.format("CREATE TABLE %s.clustering_static (\n" +
+                "  id int,\n" +
+                "  clustering1 int,\n" +
+                "  clustering2 int,\n" +
+                "  clustering3 int,\n" +
+                "  sval int static, \n" +
+                "  val int, \n" +
+                " PRIMARY KEY(id, clustering1, clustering2, clustering3)" +
+                ")", KEYSPACE));
+
+        execute("DELETE FROM " + KEYSPACE +".clustering_static WHERE id=1");
+
+        String clusteringInsert = "INSERT INTO " + KEYSPACE + 
".clustering_static(id, clustering1, clustering2, clustering3, val) VALUES(%s, 
%s, %s, %s, %s); ";
+        String clusteringTTLInsert = "INSERT INTO " + KEYSPACE + 
".clustering_static(id, clustering1, clustering2, clustering3, val) VALUES(%s, 
%s, %s, %s, %s) USING TTL %s; ";
+        String clusteringStaticInsert = "INSERT INTO " + KEYSPACE + 
".clustering_static(id, clustering1, clustering2, clustering3, sval, val) 
VALUES(%s, %s, %s, %s, %s, %s); ";
+        String clusteringConditionalInsert = "INSERT INTO " + KEYSPACE + 
".clustering_static(id, clustering1, clustering2, clustering3, val) VALUES(%s, 
%s, %s, %s, %s) IF NOT EXISTS; ";
+        String clusteringConditionalTTLInsert = "INSERT INTO " + KEYSPACE + 
".clustering_static(id, clustering1, clustering2, clustering3, val) VALUES(%s, 
%s, %s, %s, %s)  IF NOT EXISTS USING TTL %s; ";
+        String clusteringUpdate = "UPDATE " + KEYSPACE + ".clustering_static 
SET val=%s WHERE id=%s AND clustering1=%s AND clustering2=%s AND clustering3=%s 
;";
+        String clusteringStaticUpdate = "UPDATE " + KEYSPACE + 
".clustering_static SET sval=%s WHERE id=%s ;";
+        String clusteringTTLUpdate = "UPDATE " + KEYSPACE + 
".clustering_static USING TTL %s SET val=%s WHERE id=%s AND clustering1=%s AND 
clustering2=%s AND clustering3=%s ;";
+        String clusteringStaticConditionalUpdate = "UPDATE " + KEYSPACE + 
".clustering_static SET val=%s WHERE id=%s AND clustering1=%s AND 
clustering2=%s AND clustering3=%s IF sval=%s ;";
+        String clusteringConditionalTTLUpdate = "UPDATE " + KEYSPACE + 
".clustering_static USING TTL %s SET val=%s WHERE id=%s AND clustering1=%s AND 
clustering2=%s AND clustering3=%s IF val=%s ;";
+        String clusteringStaticConditionalTTLUpdate = "UPDATE " + KEYSPACE + 
".clustering_static USING TTL %s SET val=%s WHERE id=%s AND clustering1=%s AND 
clustering2=%s AND clustering3=%s IF sval=%s ;";
+        String clusteringStaticConditionalStaticUpdate = "UPDATE " + KEYSPACE 
+".clustering_static SET sval=%s WHERE id=%s IF sval=%s; ";
+        String clusteringDelete = "DELETE FROM " + KEYSPACE + 
".clustering_static WHERE id=%s AND clustering1=%s AND clustering2=%s AND 
clustering3=%s ;";
+        String clusteringRangeDelete = "DELETE FROM " + KEYSPACE + 
".clustering_static WHERE id=%s AND clustering1=%s ;";
+        String clusteringConditionalDelete = "DELETE FROM " + KEYSPACE + 
".clustering_static WHERE id=%s AND clustering1=%s AND clustering2=%s AND 
clustering3=%s IF val=%s ; ";
+        String clusteringStaticConditionalDelete = "DELETE FROM " + KEYSPACE + 
".clustering_static WHERE id=%s AND clustering1=%s AND clustering2=%s AND 
clustering3=%s IF sval=%s ; ";
+
+
+        execute("BEGIN BATCH " + String.format(clusteringStaticInsert, 1, 1, 
1, 1, 1, 1) + " APPLY BATCH");
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"), row(1, 1, 1, 1, 1, 1));
+
+        StringBuilder cmd2 = new StringBuilder();
+        cmd2.append("BEGIN BATCH ");
+        cmd2.append(String.format(clusteringInsert, 1, 1, 1, 2, 2));
+        cmd2.append(String.format(clusteringStaticConditionalUpdate, 11, 1, 1, 
1, 1, 1));
+        cmd2.append("APPLY BATCH ");
+        execute(cmd2.toString());
+
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 1, 1, 1, 1, 11),
+                row(1, 1, 1, 2, 1, 2)
+        );
+
+
+        StringBuilder cmd3 = new StringBuilder();
+        cmd3.append("BEGIN BATCH ");
+        cmd3.append(String.format(clusteringInsert, 1, 1, 2, 3, 23));
+        cmd3.append(String.format(clusteringStaticUpdate, 22, 1));
+        cmd3.append(String.format(clusteringDelete, 1, 1, 1, 1));
+        cmd3.append("APPLY BATCH ");
+        execute(cmd3.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 1, 1, 2, 22, 2),
+                row(1, 1, 2, 3, 22, 23)
+        );
+
+        StringBuilder cmd4 = new StringBuilder();
+        cmd4.append("BEGIN BATCH ");
+        cmd4.append(String.format(clusteringInsert, 1, 2, 3, 4, 1234));
+        cmd4.append(String.format(clusteringStaticConditionalTTLUpdate, 5, 
234, 1, 1, 1, 2, 22));
+        cmd4.append("APPLY BATCH ");
+        execute(cmd4.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 1, 1, 2, 22, 234),
+                row(1, 1, 2, 3, 22, 23),
+                row(1, 2, 3, 4, 22, 1234)
+        );
+
+        Thread.sleep(6000);
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 1, 1, 2, 22, null),
+                row(1, 1, 2, 3, 22, 23),
+                row(1, 2, 3, 4, 22, 1234)
+        );
+
+        StringBuilder cmd5 = new StringBuilder();
+        cmd5.append("BEGIN BATCH ");
+        cmd5.append(String.format(clusteringRangeDelete, 1, 2));
+        cmd5.append(String.format(clusteringStaticConditionalUpdate, 1234, 1, 
1, 1, 2, 22));
+        cmd5.append("APPLY BATCH ");
+        execute(cmd5.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 1, 1, 2, 22, 1234),
+                row(1, 1, 2, 3, 22, 23)
+        );
+
+        StringBuilder cmd6 = new StringBuilder();
+        cmd6.append("BEGIN BATCH ");
+        cmd6.append(String.format(clusteringUpdate, 345, 1, 3, 4, 5));
+        cmd6.append(String.format(clusteringStaticConditionalUpdate, 1, 1, 1, 
1, 2, 22));
+        cmd6.append("APPLY BATCH ");
+        execute(cmd6.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 1, 1, 2, 22, 1),
+                row(1, 1, 2, 3, 22, 23),
+                row(1, 3, 4, 5, 22, 345)
+        );
+
+
+        StringBuilder cmd7 = new StringBuilder();
+        cmd7.append("BEGIN BATCH ");
+        cmd7.append(String.format(clusteringDelete, 1, 3, 4, 5));
+        cmd7.append(String.format(clusteringStaticConditionalUpdate, 2300, 1, 
1, 2, 3, 1));  // SHOULD NOT MATCH
+        cmd7.append("APPLY BATCH ");
+        execute(cmd7.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 1, 1, 2, 22, 1),
+                row(1, 1, 2, 3, 22, 23),
+                row(1, 3, 4, 5, 22, 345)
+        );
+
+        StringBuilder cmd8 = new StringBuilder();
+        cmd8.append("BEGIN BATCH ");
+        cmd8.append(String.format(clusteringConditionalDelete, 1, 3, 4, 5, 
345));
+        cmd8.append(String.format(clusteringRangeDelete, 1, 1));
+        cmd8.append(String.format(clusteringInsert, 1, 2, 3, 4, 5));
+        cmd8.append("APPLY BATCH ");
+        execute(cmd8.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 2, 3, 4, 22, 5)
+        );
+
+        StringBuilder cmd9 = new StringBuilder();
+        cmd9.append("BEGIN BATCH ");
+        cmd9.append(String.format(clusteringConditionalInsert, 1, 3, 4, 5, 
345));
+        cmd9.append(String.format(clusteringDelete, 1, 2, 3, 4));
+        cmd9.append("APPLY BATCH ");
+        execute(cmd9.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 3, 4, 5, 22, 345)
+        );
+
+        StringBuilder cmd10 = new StringBuilder();
+        cmd10.append("BEGIN BATCH ");
+        cmd10.append(String.format(clusteringTTLInsert, 1, 2, 3, 4, 5, 5));
+        cmd10.append(String.format(clusteringConditionalTTLUpdate, 10, 5, 1, 
3, 4, 5, 345));
+        cmd10.append("APPLY BATCH ");
+        execute(cmd10.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 2, 3, 4, 22, 5), // 5 second TTL
+                row(1, 3, 4, 5, 22, 5)  // 10 second TTL
+        );
+
+        Thread.sleep(6000);
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 3, 4, 5, 22, 5) // now 4 second TTL
+        );
+
+        StringBuilder cmd11 = new StringBuilder();
+        cmd11.append("BEGIN BATCH ");
+        cmd11.append(String.format(clusteringConditionalTTLInsert, 1, 2, 3, 4, 
5, 5));
+        cmd11.append(String.format(clusteringInsert,1, 4, 5, 6, 7));
+        cmd11.append("APPLY BATCH ");
+        execute(cmd11.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 2, 3, 4, 22, 5), // This one has 5 seconds left
+                row(1, 3, 4, 5, 22, 5), // This one should have 4 seconds left
+                row(1, 4, 5, 6, 22, 7) // This one has no TTL
+        );
+
+        Thread.sleep(6000);
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 3, 4, 5, 22, null), // We had a row here before from 
cmd9, but we've ttl'd out the value in cmd11
+                row(1, 4, 5, 6, 22, 7)
+        );
+
+        StringBuilder cmd12 = new StringBuilder();
+        cmd12.append("BEGIN BATCH ");
+        cmd12.append(String.format(clusteringConditionalTTLUpdate, 5, 5, 1, 3, 
4, 5, null));
+        cmd12.append(String.format(clusteringTTLUpdate, 5, 8, 1, 4, 5, 6));
+        cmd12.append("APPLY BATCH ");
+        execute(cmd12.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 3, 4, 5, 22, 5),
+                row(1, 4, 5, 6, 22, 8)
+        );
+
+        Thread.sleep(6000);
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 3, 4, 5, 22, null),
+                row(1, 4, 5, 6, 22, null)
+        );
+
+        StringBuilder cmd13 = new StringBuilder();
+        cmd13.append("BEGIN BATCH ");
+        cmd13.append(String.format(clusteringStaticConditionalDelete, 1, 3, 4, 
5, 22));
+        cmd13.append(String.format(clusteringInsert, 1, 2, 3, 4, 5));
+        cmd13.append("APPLY BATCH ");
+        execute(cmd13.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 2, 3, 4, 22, 5),
+                row(1, 4, 5, 6, 22, null)
+        );
+
+        StringBuilder cmd14 = new StringBuilder();
+        cmd14.append("BEGIN BATCH ");
+        cmd14.append(String.format(clusteringStaticConditionalStaticUpdate, 
23, 1, 22));
+        cmd14.append(String.format(clusteringDelete, 1, 4, 5, 6));
+        cmd14.append("APPLY BATCH ");
+        execute(cmd14.toString());
+
+        assertRows(execute("SELECT * FROM " + KEYSPACE+".clustering_static 
WHERE id=1"),
+                row(1, 2, 3, 4, 23, 5)
+        );
     }
 
 }


---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscr...@cassandra.apache.org
For additional commands, e-mail: commits-h...@cassandra.apache.org

Reply via email to