Merge branch 'cassandra-3.0' into trunk
Project: http://git-wip-us.apache.org/repos/asf/cassandra/repo Commit: http://git-wip-us.apache.org/repos/asf/cassandra/commit/64f12ab2 Tree: http://git-wip-us.apache.org/repos/asf/cassandra/tree/64f12ab2 Diff: http://git-wip-us.apache.org/repos/asf/cassandra/diff/64f12ab2 Branch: refs/heads/trunk Commit: 64f12ab2c82aea80bb8afdc0bf6b72fa706c0ff5 Parents: 4354db2 d600f51 Author: Stefania Alborghetti <stefania.alborghe...@datastax.com> Authored: Mon Sep 12 16:57:03 2016 +0800 Committer: Stefania Alborghetti <stefania.alborghe...@datastax.com> Committed: Mon Sep 12 16:58:08 2016 +0800 ---------------------------------------------------------------------- CHANGES.txt | 1 + .../org/apache/cassandra/db/LegacyLayout.java | 66 +++++++++++--------- .../cassandra/db/marshal/CompositeType.java | 26 -------- 3 files changed, 38 insertions(+), 55 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cassandra/blob/64f12ab2/CHANGES.txt ---------------------------------------------------------------------- diff --cc CHANGES.txt index 520a338,f0ec3e3..3ab144e --- a/CHANGES.txt +++ b/CHANGES.txt @@@ -1,64 -1,6 +1,65 @@@ -3.0.9 +3.10 + * Fix Cassandra Stress reporting thread model and precision (CASSANDRA-12585) + * Add JMH benchmarks.jar (CASSANDRA-12586) + * Add row offset support to SASI (CASSANDRA-11990) + * Cleanup uses of AlterTableStatementColumn (CASSANDRA-12567) + * Add keep-alive to streaming (CASSANDRA-11841) + * Tracing payload is passed through newSession(..) (CASSANDRA-11706) + * avoid deleting non existing sstable files and improve related log messages (CASSANDRA-12261) + * json/yaml output format for nodetool compactionhistory (CASSANDRA-12486) + * Retry all internode messages once after a connection is + closed and reopened (CASSANDRA-12192) + * Add support to rebuild from targeted replica (CASSANDRA-9875) + * Add sequence distribution type to cassandra stress (CASSANDRA-12490) + * "SELECT * FROM foo LIMIT ;" does not error out (CASSANDRA-12154) + * Define executeLocally() at the ReadQuery Level (CASSANDRA-12474) + * Extend read/write failure messages with a map of replica addresses + to error codes in the v5 native protocol (CASSANDRA-12311) + * Fix rebuild of SASI indexes with existing index files (CASSANDRA-12374) + * Let DatabaseDescriptor not implicitly startup services (CASSANDRA-9054, 12550) + * Fix clustering indexes in presence of static columns in SASI (CASSANDRA-12378) + * Fix queries on columns with reversed type on SASI indexes (CASSANDRA-12223) + * Added slow query log (CASSANDRA-12403) + * Count full coordinated request against timeout (CASSANDRA-12256) + * Allow TTL with null value on insert and update (CASSANDRA-12216) + * Make decommission operation resumable (CASSANDRA-12008) + * Add support to one-way targeted repair (CASSANDRA-9876) + * Remove clientutil jar (CASSANDRA-11635) + * Fix compaction throughput throttle (CASSANDRA-12366) + * Delay releasing Memtable memory on flush until PostFlush has finished running (CASSANDRA-12358) + * Cassandra stress should dump all setting on startup (CASSANDRA-11914) + * Make it possible to compact a given token range (CASSANDRA-10643) + * Allow updating DynamicEndpointSnitch properties via JMX (CASSANDRA-12179) + * Collect metrics on queries by consistency level (CASSANDRA-7384) + * Add support for GROUP BY to SELECT statement (CASSANDRA-10707) + * Deprecate memtable_cleanup_threshold and update default for memtable_flush_writers (CASSANDRA-12228) + * Upgrade to OHC 0.4.4 (CASSANDRA-12133) + * Add version command to cassandra-stress (CASSANDRA-12258) + * Create compaction-stress tool (CASSANDRA-11844) + * Garbage-collecting compaction operation and schema option (CASSANDRA-7019) + * Add beta protocol flag for v5 native protocol (CASSANDRA-12142) + * Support filtering on non-PRIMARY KEY columns in the CREATE + MATERIALIZED VIEW statement's WHERE clause (CASSANDRA-10368) + * Unify STDOUT and SYSTEMLOG logback format (CASSANDRA-12004) + * COPY FROM should raise error for non-existing input files (CASSANDRA-12174) + * Faster write path (CASSANDRA-12269) + * Option to leave omitted columns in INSERT JSON unset (CASSANDRA-11424) + * Support json/yaml output in nodetool tpstats (CASSANDRA-12035) + * Expose metrics for successful/failed authentication attempts (CASSANDRA-10635) + * Prepend snapshot name with "truncated" or "dropped" when a snapshot + is taken before truncating or dropping a table (CASSANDRA-12178) + * Optimize RestrictionSet (CASSANDRA-12153) + * cqlsh does not automatically downgrade CQL version (CASSANDRA-12150) + * Omit (de)serialization of state variable in UDAs (CASSANDRA-9613) + * Create a system table to expose prepared statements (CASSANDRA-8831) + * Reuse DataOutputBuffer from ColumnIndex (CASSANDRA-11970) + * Remove DatabaseDescriptor dependency from SegmentedFile (CASSANDRA-11580) + * Add supplied username to authentication error messages (CASSANDRA-12076) + * Remove pre-startup check for open JMX port (CASSANDRA-12074) + * Remove compaction Severity from DynamicEndpointSnitch (CASSANDRA-11738) + * Restore resumable hints delivery (CASSANDRA-11960) +Merged from 3.0: + * Handle composite prefixes with final EOC=0 as in 2.x and refactor LegacyLayout.decodeBound (CASSANDRA-12423) - * Fix paging for 2.x to 3.x upgrades (CASSANDRA-11195) * select_distinct_with_deletions_test failing on non-vnode environments (CASSANDRA-11126) * Stack Overflow returned to queries while upgrading (CASSANDRA-12527) * Fix legacy regex for temporary files from 2.2 (CASSANDRA-12565) http://git-wip-us.apache.org/repos/asf/cassandra/blob/64f12ab2/src/java/org/apache/cassandra/db/LegacyLayout.java ---------------------------------------------------------------------- diff --cc src/java/org/apache/cassandra/db/LegacyLayout.java index 4fdf28c,c8e7536..ab62a0e --- a/src/java/org/apache/cassandra/db/LegacyLayout.java +++ b/src/java/org/apache/cassandra/db/LegacyLayout.java @@@ -187,47 -186,55 +187,55 @@@ public abstract class LegacyLayou if (!bound.hasRemaining()) return isStart ? LegacyBound.BOTTOM : LegacyBound.TOP; - List<CompositeType.CompositeComponent> components = metadata.isCompound() - ? CompositeType.deconstruct(bound) - : Collections.singletonList(new CompositeType.CompositeComponent(bound, (byte) 0)); - - // Either it's a prefix of the clustering, or it's the bound of a collection range tombstone (and thus has - // the collection column name) - assert components.size() <= metadata.comparator.size() || (!metadata.isCompactTable() && components.size() == metadata.comparator.size() + 1); - - List<CompositeType.CompositeComponent> prefix = components.size() <= metadata.comparator.size() - ? components - : components.subList(0, metadata.comparator.size()); - ClusteringPrefix.Kind boundKind; + if (!metadata.isCompound()) + { + // The non compound case is a lot easier, in that there is no EOC nor collection to worry about, so dealing + // with that first. - return new LegacyBound(isStart ? Slice.Bound.inclusiveStartOf(bound) : Slice.Bound.inclusiveEndOf(bound), false, null); ++ return new LegacyBound(isStart ? ClusteringBound.inclusiveStartOf(bound) : ClusteringBound.inclusiveEndOf(bound), false, null); + } + + int clusteringSize = metadata.comparator.size(); + + List<ByteBuffer> components = CompositeType.splitName(bound); + byte eoc = CompositeType.lastEOC(bound); + + // There can be more components than the clustering size only in the case this is the bound of a collection + // range tombstone. In which case, there is exactly one more component, and that component is the name of the + // collection being selected/deleted. + assert components.size() <= clusteringSize || (!metadata.isCompactTable() && components.size() == clusteringSize + 1); + + ColumnDefinition collectionName = null; + if (components.size() > clusteringSize) + collectionName = metadata.getColumnDefinition(components.remove(clusteringSize)); + + boolean isInclusive; if (isStart) { - if (components.get(components.size() - 1).eoc > 0) - boundKind = ClusteringPrefix.Kind.EXCL_START_BOUND; - else - boundKind = ClusteringPrefix.Kind.INCL_START_BOUND; + isInclusive = eoc <= 0; } else { - if (components.get(components.size() - 1).eoc < 0) - boundKind = ClusteringPrefix.Kind.EXCL_END_BOUND; - else - boundKind = ClusteringPrefix.Kind.INCL_END_BOUND; - } + isInclusive = eoc >= 0; - ByteBuffer[] prefixValues = new ByteBuffer[prefix.size()]; - for (int i = 0; i < prefix.size(); i++) - prefixValues[i] = prefix.get(i).value; - ClusteringBound sb = ClusteringBound.create(boundKind, prefixValues); + // for an end bound, if we only have a prefix of all the components and the final EOC is zero, + // then it should only match up to the prefix but no further, that is, it is an inclusive bound + // of the exact prefix but an exclusive bound of anything beyond it, so adding an empty + // composite value ensures this behavior, see CASSANDRA-12423 for more details + if (eoc == 0 && components.size() < clusteringSize) + { + components.add(ByteBufferUtil.EMPTY_BYTE_BUFFER); + isInclusive = false; + } + } - ColumnDefinition collectionName = components.size() == metadata.comparator.size() + 1 - ? metadata.getColumnDefinition(components.get(metadata.comparator.size()).value) - : null; - Slice.Bound.Kind boundKind = Slice.Bound.boundKind(isStart, isInclusive); - Slice.Bound sb = Slice.Bound.create(boundKind, components.toArray(new ByteBuffer[components.size()])); -- return new LegacyBound(sb, metadata.isCompound() && CompositeType.isStaticName(bound), collectionName); ++ ClusteringPrefix.Kind boundKind = ClusteringBound.boundKind(isStart, isInclusive); ++ ClusteringBound cb = ClusteringBound.create(boundKind, components.toArray(new ByteBuffer[components.size()])); ++ return new LegacyBound(cb, metadata.isCompound() && CompositeType.isStaticName(bound), collectionName); } - public static ByteBuffer encodeBound(CFMetaData metadata, Slice.Bound bound, boolean isStart) + public static ByteBuffer encodeBound(CFMetaData metadata, ClusteringBound bound, boolean isStart) { - if (bound == Slice.Bound.BOTTOM || bound == Slice.Bound.TOP || metadata.comparator.size() == 0) + if (bound == ClusteringBound.BOTTOM || bound == ClusteringBound.TOP || metadata.comparator.size() == 0) return ByteBufferUtil.EMPTY_BYTE_BUFFER; ClusteringPrefix clustering = bound.clustering(); http://git-wip-us.apache.org/repos/asf/cassandra/blob/64f12ab2/src/java/org/apache/cassandra/db/marshal/CompositeType.java ----------------------------------------------------------------------