You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cassandra.apache.org by bl...@apache.org on 2017/01/27 14:51:39 UTC

[2/7] cassandra git commit: Merge branch cassandra-2.2 into cassandra-3.0

Merge branch cassandra-2.2 into cassandra-3.0


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

Branch: refs/heads/trunk
Commit: 714edbce9a38c70a0f031a73d3c1a20f7f2b4bb3
Parents: e1da99a 70e33d9
Author: Benjamin Lerer <b....@gmail.com>
Authored: Fri Jan 27 15:26:18 2017 +0100
Committer: Benjamin Lerer <b....@gmail.com>
Committed: Fri Jan 27 15:29:40 2017 +0100

----------------------------------------------------------------------
 CHANGES.txt                                     |   1 +
 .../apache/cassandra/cql3/ColumnCondition.java  |  62 ++++++-
 .../operations/InsertUpdateIfConditionTest.java | 162 ++++++++++++++++++-
 3 files changed, 215 insertions(+), 10 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cassandra/blob/714edbce/CHANGES.txt
----------------------------------------------------------------------
diff --cc CHANGES.txt
index 3796a8d,c5e5335..547fc07
--- a/CHANGES.txt
+++ b/CHANGES.txt
@@@ -1,32 -1,5 +1,33 @@@
 -2.2.9
 +3.0.11
 + * Better error when modifying function permissions without explicit keyspace (CASSANDRA-12925)
 + * Indexer is not correctly invoked when building indexes over sstables (CASSANDRA-13075)
 + * Read repair is not blocking repair to finish in foreground repair (CASSANDRA-13115)
 + * Stress daemon help is incorrect (CASSANDRA-12563)
 + * Remove ALTER TYPE support (CASSANDRA-12443)
 + * Fix assertion for certain legacy range tombstone pattern (CASSANDRA-12203)
 + * Set javac encoding to utf-8 (CASSANDRA-11077)
 + * Replace empty strings with null values if they cannot be converted (CASSANDRA-12794)
 + * Fixed flacky SSTableRewriterTest: check file counts before calling validateCFS (CASSANDRA-12348)
 + * Fix deserialization of 2.x DeletedCells (CASSANDRA-12620)
 + * Add parent repair session id to anticompaction log message (CASSANDRA-12186)
 + * Improve contention handling on failure to acquire MV lock for streaming and hints (CASSANDRA-12905)
 + * Fix DELETE and UPDATE queries with empty IN restrictions (CASSANDRA-12829)
 + * Mark MVs as built after successful bootstrap (CASSANDRA-12984)
 + * Estimated TS drop-time histogram updated with Cell.NO_DELETION_TIME (CASSANDRA-13040)
 + * Nodetool compactionstats fails with NullPointerException (CASSANDRA-13021)
 + * Thread local pools never cleaned up (CASSANDRA-13033)
 + * Set RPC_READY to false when draining or if a node is marked as shutdown (CASSANDRA-12781)
 + * Make sure sstables only get committed when it's safe to discard commit log records (CASSANDRA-12956)
 + * Reject default_time_to_live option when creating or altering MVs (CASSANDRA-12868)
 + * Nodetool should use a more sane max heap size (CASSANDRA-12739)
 + * LocalToken ensures token values are cloned on heap (CASSANDRA-12651)
 + * AnticompactionRequestSerializer serializedSize is incorrect (CASSANDRA-12934)
 + * Prevent reloading of logback.xml from UDF sandbox (CASSANDRA-12535)
 + * Reenable HeapPool (CASSANDRA-12900)
 +Merged from 2.2:
+  * Fix handling of nulls and unsets in IN conditions (CASSANDRA-12981) 
 + * Fix race causing infinite loop if Thrift server is stopped before it starts listening (CASSANDRA-12856)
 + * CompactionTasks now correctly drops sstables out of compaction when not enough disk space is available (CASSANDRA-12979)
   * Remove support for non-JavaScript UDFs (CASSANDRA-12883)
   * Fix DynamicEndpointSnitch noop in multi-datacenter situations (CASSANDRA-13074)
   * cqlsh copy-from: encode column names to avoid primary key parsing errors (CASSANDRA-12909)

http://git-wip-us.apache.org/repos/asf/cassandra/blob/714edbce/src/java/org/apache/cassandra/cql3/ColumnCondition.java
----------------------------------------------------------------------
diff --cc src/java/org/apache/cassandra/cql3/ColumnCondition.java
index b13e534,3412e71..60e67f3
--- a/src/java/org/apache/cassandra/cql3/ColumnCondition.java
+++ b/src/java/org/apache/cassandra/cql3/ColumnCondition.java
@@@ -23,8 -23,16 +23,9 @@@ import java.util.*
  import com.google.common.collect.Iterators;
  
  import org.apache.cassandra.config.ColumnDefinition;
+ import org.apache.cassandra.cql3.Term.Terminal;
  import org.apache.cassandra.cql3.functions.Function;
 -import org.apache.cassandra.db.Cell;
 -import org.apache.cassandra.db.ColumnFamily;
 -import org.apache.cassandra.db.composites.CellName;
 -import org.apache.cassandra.db.composites.CellNameType;
 -import org.apache.cassandra.db.composites.Composite;
 -import org.apache.cassandra.db.filter.ColumnSlice;
 +import org.apache.cassandra.db.rows.*;
  import org.apache.cassandra.db.marshal.*;
  import org.apache.cassandra.exceptions.InvalidRequestException;
  import org.apache.cassandra.transport.Server;

http://git-wip-us.apache.org/repos/asf/cassandra/blob/714edbce/test/unit/org/apache/cassandra/cql3/validation/operations/InsertUpdateIfConditionTest.java
----------------------------------------------------------------------
diff --cc test/unit/org/apache/cassandra/cql3/validation/operations/InsertUpdateIfConditionTest.java
index fd02a69,6396727..8adce7a
--- a/test/unit/org/apache/cassandra/cql3/validation/operations/InsertUpdateIfConditionTest.java
+++ b/test/unit/org/apache/cassandra/cql3/validation/operations/InsertUpdateIfConditionTest.java
@@@ -155,8 -150,6 +159,7 @@@ public class InsertUpdateIfConditionTes
                               "UPDATE %s SET v1 = 3, v2 = 'bar' WHERE k = 0 IF v1 >= ?", unset());
          assertInvalidMessage("Invalid 'unset' value in condition",
                               "UPDATE %s SET v1 = 3, v2 = 'bar' WHERE k = 0 IF v1 != ?", unset());
-         assertInvalidMessage("Invalid 'unset' value in condition",
-                              "UPDATE %s SET v1 = 3, v2 = 'bar' WHERE k = 0 IF v1 IN (?, ?)", unset(), 1);
++
      }
  
      /**
@@@ -1482,107 -1306,158 +1485,262 @@@
                     row(7, 7, null, null, 7));
      }
  
 +    /**
 +     * Test for CASSANDRA-12060, using a table without clustering.
 +     */
 +    @Test
 +    public void testMultiExistConditionOnSameRowNoClustering() throws Throwable
 +    {
 +        createTable("CREATE TABLE %s (k int PRIMARY KEY, v1 text, v2 text)");
 +
 +        // Multiple inserts on the same row with not exist conditions
 +        assertRows(execute("BEGIN BATCH "
 +                           + "INSERT INTO %1$s (k, v1) values (0, 'foo') IF NOT EXISTS; "
 +                           + "INSERT INTO %1$s (k, v2) values (0, 'bar') IF NOT EXISTS; "
 +                           + "APPLY BATCH"),
 +                   row(true));
 +
 +        assertRows(execute("SELECT * FROM %s WHERE k = 0"), row(0, "foo", "bar"));
 +
 +        // Same, but both insert on the same column: doing so would almost surely be a user error, but that's the
 +        // original case reported in #12867, so being thorough.
 +        assertRows(execute("BEGIN BATCH "
 +                           + "INSERT INTO %1$s (k, v1) values (1, 'foo') IF NOT EXISTS; "
 +                           + "INSERT INTO %1$s (k, v1) values (1, 'bar') IF NOT EXISTS; "
 +                           + "APPLY BATCH"),
 +                   row(true));
 +
 +        // As all statement gets the same timestamp, the biggest value ends up winning, so that's "foo"
 +        assertRows(execute("SELECT * FROM %s WHERE k = 1"), row(1, "foo", null));
 +
 +        // Multiple deletes on the same row with exists conditions (note that this is somewhat non-sensical, one of the
 +        // delete is redundant, we're just checking it doesn't break something)
 +        assertRows(execute("BEGIN BATCH "
 +                           + "DELETE FROM %1$s WHERE k = 0 IF EXISTS; "
 +                           + "DELETE FROM %1$s WHERE k = 0 IF EXISTS; "
 +                           + "APPLY BATCH"),
 +                   row(true));
 +
 +        assertEmpty(execute("SELECT * FROM %s WHERE k = 0"));
 +
 +        // Validate we can't mix different type of conditions however
 +        assertInvalidMessage("Cannot mix IF EXISTS and IF NOT EXISTS conditions for the same row",
 +                             "BEGIN BATCH "
 +                           + "INSERT INTO %1$s (k, v1) values (1, 'foo') IF NOT EXISTS; "
 +                           + "DELETE FROM %1$s WHERE k = 1 IF EXISTS; "
 +                           + "APPLY BATCH");
 +
 +        assertInvalidMessage("Cannot mix IF conditions and IF NOT EXISTS for the same row",
 +                             "BEGIN BATCH "
 +                             + "INSERT INTO %1$s (k, v1) values (1, 'foo') IF NOT EXISTS; "
 +                             + "UPDATE %1$s SET v2 = 'bar' WHERE k = 1 IF v1 = 'foo'; "
 +                             + "APPLY BATCH");
 +    }
 +
 +    /**
 +     * Test for CASSANDRA-12060, using a table with clustering.
 +     */
 +    @Test
 +    public void testMultiExistConditionOnSameRowClustering() throws Throwable
 +    {
 +        createTable("CREATE TABLE %s (k int, t int, v1 text, v2 text, PRIMARY KEY (k, t))");
 +
 +        // Multiple inserts on the same row with not exist conditions
 +        assertRows(execute("BEGIN BATCH "
 +                           + "INSERT INTO %1$s (k, t, v1) values (0, 0, 'foo') IF NOT EXISTS; "
 +                           + "INSERT INTO %1$s (k, t, v2) values (0, 0, 'bar') IF NOT EXISTS; "
 +                           + "APPLY BATCH"),
 +                   row(true));
 +
 +        assertRows(execute("SELECT * FROM %s WHERE k = 0"), row(0, 0, "foo", "bar"));
 +
 +        // Same, but both insert on the same column: doing so would almost surely be a user error, but that's the
 +        // original case reported in #12867, so being thorough.
 +        assertRows(execute("BEGIN BATCH "
 +                           + "INSERT INTO %1$s (k, t, v1) values (1, 0, 'foo') IF NOT EXISTS; "
 +                           + "INSERT INTO %1$s (k, t, v1) values (1, 0, 'bar') IF NOT EXISTS; "
 +                           + "APPLY BATCH"),
 +                   row(true));
 +
 +        // As all statement gets the same timestamp, the biggest value ends up winning, so that's "foo"
 +        assertRows(execute("SELECT * FROM %s WHERE k = 1"), row(1, 0, "foo", null));
 +
 +        // Multiple deletes on the same row with exists conditions (note that this is somewhat non-sensical, one of the
 +        // delete is redundant, we're just checking it doesn't break something)
 +        assertRows(execute("BEGIN BATCH "
 +                           + "DELETE FROM %1$s WHERE k = 0 AND t = 0 IF EXISTS; "
 +                           + "DELETE FROM %1$s WHERE k = 0 AND t = 0 IF EXISTS; "
 +                           + "APPLY BATCH"),
 +                   row(true));
 +
 +        assertEmpty(execute("SELECT * FROM %s WHERE k = 0"));
 +
 +        // Validate we can't mix different type of conditions however
 +        assertInvalidMessage("Cannot mix IF EXISTS and IF NOT EXISTS conditions for the same row",
 +                             "BEGIN BATCH "
 +                             + "INSERT INTO %1$s (k, t, v1) values (1, 0, 'foo') IF NOT EXISTS; "
 +                             + "DELETE FROM %1$s WHERE k = 1 AND t = 0 IF EXISTS; "
 +                             + "APPLY BATCH");
 +
 +        assertInvalidMessage("Cannot mix IF conditions and IF NOT EXISTS for the same row",
 +                             "BEGIN BATCH "
 +                             + "INSERT INTO %1$s (k, t, v1) values (1, 0, 'foo') IF NOT EXISTS; "
 +                             + "UPDATE %1$s SET v2 = 'bar' WHERE k = 1 AND t = 0 IF v1 = 'foo'; "
 +                             + "APPLY BATCH");
 +    }
++
+     @Test
+     public void testInMarkerWithUDTs() throws Throwable
+     {
+         String typename = createType("CREATE TYPE %s (a int, b text)");
+         String myType = KEYSPACE + '.' + typename;
+ 
+             createTable("CREATE TABLE %s (k int PRIMARY KEY, v frozen<" + myType + "> )");
+ 
+             Object v = userType(0, "abc");
+             execute("INSERT INTO %s (k, v) VALUES (?, ?)", 0, v);
+ 
+             // Does not apply
+             assertRows(execute("UPDATE %s SET v = {a: 0, b: 'bc'} WHERE k = 0 IF v IN (?, ?)", userType(1, "abc"), userType(0, "ac")),
+                        row(false, v));
+             assertRows(execute("UPDATE %s SET v = {a: 0, b: 'bc'} WHERE k = 0 IF v IN (?, ?)", userType(1, "abc"), null),
+                        row(false, v));
+             assertRows(execute("UPDATE %s SET v = {a: 0, b: 'bc'} WHERE k = 0 IF v IN (?, ?)", userType(1, "abc"), unset()),
+                        row(false, v));
+             assertRows(execute("UPDATE %s SET v = {a: 0, b: 'bc'} WHERE k = 0 IF v IN (?, ?)", null, null),
+                        row(false, v));
+             assertRows(execute("UPDATE %s SET v = {a: 0, b: 'bc'} WHERE k = 0 IF v IN (?, ?)", unset(), unset()),
+                        row(false, v));
+             assertRows(execute("UPDATE %s SET v = {a: 0, b: 'bc'} WHERE k = 0 IF v IN ?", list(userType(1, "abc"), userType(0, "ac"))),
+                        row(false, v));
+ 
+             // Does apply
+             assertRows(execute("UPDATE %s SET v = {a: 0, b: 'bc'} WHERE k = 0 IF v IN (?, ?)", userType(0, "abc"), userType(0, "ac")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET v = {a: 1, b: 'bc'} WHERE k = 0 IF v IN (?, ?)", userType(0, "bc"), null),
+                        row(true));
+             assertRows(execute("UPDATE %s SET v = {a: 1, b: 'ac'} WHERE k = 0 IF v IN (?, ?, ?)", userType(0, "bc"), unset(), userType(1, "bc")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET v = {a: 0, b: 'abc'} WHERE k = 0 IF v IN ?", list(userType(1, "ac"), userType(0, "ac"))),
+                        row(true));
+ 
+             assertInvalidMessage("Invalid null list in IN condition",
+                                  "UPDATE %s SET v = {a: 0, b: 'bc'} WHERE k = 0 IF v IN ?", (List<ByteBuffer>) null);
+             assertInvalidMessage("Invalid 'unset' value in condition",
+                                  "UPDATE %s SET v = {a: 0, b: 'bc'} WHERE k = 0 IF v IN ?", unset());
+     }
+ 
+     @Test
+     public void testInMarkerWithLists() throws Throwable
+     {
+         for (boolean frozen : new boolean[]{false, true})
+         {
+             createTable(String.format("CREATE TABLE %%s (k int PRIMARY KEY, l %s)",
+                                       frozen
+                                       ? "frozen<list<text>>"
+                                       : "list<text>"));
+ 
+             execute("INSERT INTO %s(k, l) VALUES (0, ['foo', 'bar', 'foobar'])");
+ 
+             // Does not apply
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l IN (?, ?)", list("foo", "foobar"), list("bar", "foobar")),
+                        row(false, list("foo", "bar", "foobar")));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l IN (?, ?)", list("foo", "foobar"), null),
+                        row(false, list("foo", "bar", "foobar")));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l IN (?, ?)", list("foo", "foobar"), unset()),
+                        row(false, list("foo", "bar", "foobar")));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l IN (?, ?)", null, null),
+                        row(false, list("foo", "bar", "foobar")));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l IN ?", list(list("foo", "foobar"), list("bar", "foobar"))),
+                        row(false, list("foo", "bar", "foobar")));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l[?] IN ?", 1, list("foo", "foobar")),
+                        row(false, list("foo", "bar", "foobar")));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l[?] IN (?, ?)", 1, "foo", "foobar"),
+                        row(false, list("foo", "bar", "foobar")));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l[?] IN (?, ?)", 1, "foo", null),
+                        row(false, list("foo", "bar", "foobar")));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l[?] IN (?, ?)", 1, "foo", unset()),
+                        row(false, list("foo", "bar", "foobar")));
+ 
+             // Does apply
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l IN (?, ?)", list("foo", "bar", "foobar"), list("bar", "foobar")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'foobar'] WHERE k = 0 IF l IN (?, ?, ?)", list("foo", "bar", "foobar"), null, list("foo", "bar")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l IN (?, ?, ?)", list("foo", "bar", "foobar"), unset(), list("foo", "foobar")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'foobar'] WHERE k = 0 IF l IN (?, ?)", list("bar", "foobar"), list("foo", "bar")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l[?] IN ?", 1, list("bar", "foobar")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'foobar'] WHERE k = 0 IF l[?] IN (?, ?, ?)", 1, "bar", null, "foobar"),
+                        row(true));
+             assertRows(execute("UPDATE %s SET l = ['foo', 'foobar'] WHERE k = 0 IF l[?] IN (?, ?, ?)", 1, "bar", unset(), "foobar"),
+                        row(true));
+ 
+             assertInvalidMessage("Invalid null list in IN condition",
+                                  "UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l IN ?", (List<ByteBuffer>) null);
+             assertInvalidMessage("Invalid 'unset' value in condition",
+                                  "UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l IN ?", unset());
+             assertInvalidMessage("Invalid 'unset' value in condition",
+                                  "UPDATE %s SET l = ['foo', 'bar'] WHERE k = 0 IF l[?] IN ?", 1, unset());
+         }
+     }
+ 
+     @Test
+     public void testInMarkerWithMaps() throws Throwable
+     {
+         for (boolean frozen : new boolean[] {false, true})
+         {
+             createTable(String.format("CREATE TABLE %%s (k int PRIMARY KEY, m %s)",
+                                       frozen
+                                       ? "frozen<map<text, text>>"
+                                       : "map<text, text>"));
+ 
+             execute("INSERT INTO %s (k, m) VALUES (0, {'foo' : 'bar'})");
+ 
+             // Does not apply
+             assertRows(execute("UPDATE %s SET m = {'foo' : 'foobar'} WHERE k = 0 IF m IN (?, ?)", map("foo", "foobar"), map("bar", "foobar")),
+                        row(false, map("foo", "bar")));
+             assertRows(execute("UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m IN (?, ?)", map("foo", "foobar"), null),
+                        row(false, map("foo", "bar")));
+             assertRows(execute("UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m IN (?, ?)", map("foo", "foobar"), unset()),
+                        row(false, map("foo", "bar")));
+             assertRows(execute("UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m IN (?, ?)", null, null),
+                        row(false, map("foo", "bar")));
+             assertRows(execute("UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m IN ?", list(map("foo", "foobar"), map("bar", "foobar"))),
+                        row(false, map("foo", "bar")));
+             assertRows(execute("UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m[?] IN ?", "foo", list("foo", "foobar")),
+                        row(false, map("foo", "bar")));
+             assertRows(execute("UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m[?] IN (?, ?)", "foo", "foo", "foobar"),
+                        row(false, map("foo", "bar")));
+             assertRows(execute("UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m[?] IN (?, ?)", "foo", "foo", null),
+                        row(false, map("foo", "bar")));
+             assertRows(execute("UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m[?] IN (?, ?)", "foo", "foo", unset()),
+                        row(false, map("foo", "bar")));
+ 
+             // Does apply
+             assertRows(execute("UPDATE %s SET m = {'foo' : 'foobar'} WHERE k = 0 IF m IN (?, ?)", map("foo", "foobar"), map("foo", "bar")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET m = {'foo' : 'bar'} WHERE k = 0 IF m IN (?, ?, ?)", map("bar", "foobar"), null, map("foo", "foobar")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET m = {'foo' : 'bar'} WHERE k = 0 IF m IN (?, ?, ?)", map("bar", "foobar"), unset(), map("foo", "bar")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET m = {'foo' : 'foobar'} WHERE k = 0 IF m IN ?", list(map("foo", "bar"), map("bar", "foobar"))),
+                        row(true));
+             assertRows(execute("UPDATE %s SET m = {'foo' : 'bar'} WHERE k = 0 IF m[?] IN ?", "foo", list("bar", "foobar")),
+                        row(true));
+             assertRows(execute("UPDATE %s SET m = {'foo' : 'foobar'} WHERE k = 0 IF m[?] IN (?, ?, ?)", "foo", "bar", null, "foobar"),
+                        row(true));
+             assertRows(execute("UPDATE %s SET m = {'foo' : 'foobar'} WHERE k = 0 IF m[?] IN (?, ?, ?)", "foo", "bar", unset(), "foobar"),
+                        row(true));
+ 
+             assertInvalidMessage("Invalid null list in IN condition",
+                                  "UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m IN ?", (List<ByteBuffer>) null);
+             assertInvalidMessage("Invalid 'unset' value in condition",
+                                  "UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m IN ?", unset());
+             assertInvalidMessage("Invalid 'unset' value in condition",
+                                  "UPDATE %s SET  m = {'foo' : 'foobar'} WHERE k = 0 IF m[?] IN ?", "foo", unset());
+         }
+     }
  }