cassandra-driver 2.0.1 → 2.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (118) hide show
  1. checksums.yaml +13 -5
  2. data/README.md +18 -9
  3. data/ext/cassandra_murmur3/cassandra_murmur3.c +1 -1
  4. data/lib/cassandra.rb +5 -1
  5. data/lib/cassandra/address_resolution.rb +1 -1
  6. data/lib/cassandra/address_resolution/policies/ec2_multi_region.rb +1 -1
  7. data/lib/cassandra/address_resolution/policies/none.rb +1 -1
  8. data/lib/cassandra/auth.rb +1 -1
  9. data/lib/cassandra/auth/providers.rb +1 -1
  10. data/lib/cassandra/auth/providers/password.rb +1 -1
  11. data/lib/cassandra/cluster.rb +1 -1
  12. data/lib/cassandra/cluster/client.rb +33 -13
  13. data/lib/cassandra/cluster/connection_pool.rb +1 -1
  14. data/lib/cassandra/cluster/connector.rb +1 -36
  15. data/lib/cassandra/cluster/control_connection.rb +85 -9
  16. data/lib/cassandra/cluster/failed_connection.rb +1 -1
  17. data/lib/cassandra/cluster/metadata.rb +1 -1
  18. data/lib/cassandra/cluster/options.rb +15 -4
  19. data/lib/cassandra/cluster/registry.rb +1 -1
  20. data/lib/cassandra/cluster/schema.rb +76 -16
  21. data/lib/cassandra/cluster/schema/partitioners.rb +1 -1
  22. data/lib/cassandra/cluster/schema/partitioners/murmur3.rb +1 -1
  23. data/lib/cassandra/cluster/schema/partitioners/ordered.rb +1 -1
  24. data/lib/cassandra/cluster/schema/partitioners/random.rb +1 -1
  25. data/lib/cassandra/cluster/schema/replication_strategies.rb +1 -1
  26. data/lib/cassandra/cluster/schema/replication_strategies/network_topology.rb +1 -1
  27. data/lib/cassandra/cluster/schema/replication_strategies/none.rb +1 -1
  28. data/lib/cassandra/cluster/schema/replication_strategies/simple.rb +1 -1
  29. data/lib/cassandra/cluster/schema/type_parser.rb +35 -8
  30. data/lib/cassandra/column.rb +10 -14
  31. data/lib/cassandra/compression.rb +1 -1
  32. data/lib/cassandra/compression/compressors/lz4.rb +1 -1
  33. data/lib/cassandra/compression/compressors/snappy.rb +1 -1
  34. data/lib/cassandra/driver.rb +2 -2
  35. data/lib/cassandra/errors.rb +1 -1
  36. data/lib/cassandra/execution/info.rb +1 -1
  37. data/lib/cassandra/execution/options.rb +3 -2
  38. data/lib/cassandra/execution/trace.rb +1 -1
  39. data/lib/cassandra/executors.rb +1 -1
  40. data/lib/cassandra/future.rb +1 -1
  41. data/lib/cassandra/host.rb +1 -1
  42. data/lib/cassandra/keyspace.rb +55 -5
  43. data/lib/cassandra/listener.rb +1 -1
  44. data/lib/cassandra/load_balancing.rb +1 -1
  45. data/lib/cassandra/load_balancing/policies.rb +1 -1
  46. data/lib/cassandra/load_balancing/policies/dc_aware_round_robin.rb +1 -1
  47. data/lib/cassandra/load_balancing/policies/round_robin.rb +1 -1
  48. data/lib/cassandra/load_balancing/policies/token_aware.rb +1 -1
  49. data/lib/cassandra/load_balancing/policies/white_list.rb +1 -1
  50. data/lib/cassandra/null_logger.rb +1 -1
  51. data/lib/cassandra/protocol.rb +6 -1
  52. data/lib/cassandra/protocol/coder.rb +319 -84
  53. data/lib/cassandra/protocol/cql_byte_buffer.rb +1 -1
  54. data/lib/cassandra/protocol/cql_protocol_handler.rb +24 -10
  55. data/lib/cassandra/protocol/request.rb +1 -1
  56. data/lib/cassandra/protocol/requests/auth_response_request.rb +1 -1
  57. data/lib/cassandra/protocol/requests/batch_request.rb +1 -1
  58. data/lib/cassandra/protocol/requests/credentials_request.rb +1 -1
  59. data/lib/cassandra/protocol/requests/execute_request.rb +1 -1
  60. data/lib/cassandra/protocol/requests/options_request.rb +1 -1
  61. data/lib/cassandra/protocol/requests/prepare_request.rb +1 -1
  62. data/lib/cassandra/protocol/requests/query_request.rb +5 -3
  63. data/lib/cassandra/protocol/requests/register_request.rb +1 -1
  64. data/lib/cassandra/protocol/requests/startup_request.rb +1 -1
  65. data/lib/cassandra/protocol/requests/void_query_request.rb +1 -1
  66. data/lib/cassandra/protocol/response.rb +1 -1
  67. data/lib/cassandra/protocol/responses/already_exists_error_response.rb +1 -1
  68. data/lib/cassandra/protocol/responses/auth_challenge_response.rb +1 -1
  69. data/lib/cassandra/protocol/responses/auth_success_response.rb +1 -1
  70. data/lib/cassandra/protocol/responses/authenticate_response.rb +1 -1
  71. data/lib/cassandra/protocol/responses/error_response.rb +1 -1
  72. data/lib/cassandra/protocol/responses/event_response.rb +1 -1
  73. data/lib/cassandra/protocol/responses/prepared_result_response.rb +1 -1
  74. data/lib/cassandra/protocol/responses/raw_rows_result_response.rb +9 -2
  75. data/lib/cassandra/protocol/responses/read_timeout_error_response.rb +1 -1
  76. data/lib/cassandra/protocol/responses/ready_response.rb +1 -1
  77. data/lib/cassandra/protocol/responses/result_response.rb +1 -1
  78. data/lib/cassandra/protocol/responses/rows_result_response.rb +1 -1
  79. data/lib/cassandra/protocol/responses/schema_change_event_response.rb +21 -6
  80. data/lib/cassandra/protocol/responses/schema_change_result_response.rb +18 -8
  81. data/lib/cassandra/protocol/responses/set_keyspace_result_response.rb +1 -1
  82. data/lib/cassandra/protocol/responses/status_change_event_response.rb +1 -1
  83. data/lib/cassandra/protocol/responses/supported_response.rb +1 -1
  84. data/lib/cassandra/protocol/responses/topology_change_event_response.rb +1 -1
  85. data/lib/cassandra/protocol/responses/unavailable_error_response.rb +1 -1
  86. data/lib/cassandra/protocol/responses/unprepared_error_response.rb +1 -1
  87. data/lib/cassandra/protocol/responses/void_result_response.rb +1 -1
  88. data/lib/cassandra/protocol/responses/write_timeout_error_response.rb +1 -1
  89. data/lib/cassandra/protocol/v1.rb +4 -2
  90. data/lib/cassandra/protocol/v3.rb +280 -0
  91. data/lib/cassandra/reconnection.rb +1 -1
  92. data/lib/cassandra/reconnection/policies.rb +1 -1
  93. data/lib/cassandra/reconnection/policies/constant.rb +1 -1
  94. data/lib/cassandra/reconnection/policies/exponential.rb +1 -1
  95. data/lib/cassandra/result.rb +1 -1
  96. data/lib/cassandra/retry.rb +1 -1
  97. data/lib/cassandra/retry/policies.rb +1 -1
  98. data/lib/cassandra/retry/policies/default.rb +1 -1
  99. data/lib/cassandra/retry/policies/downgrading_consistency.rb +1 -1
  100. data/lib/cassandra/retry/policies/fallthrough.rb +1 -1
  101. data/lib/cassandra/session.rb +14 -80
  102. data/lib/cassandra/statement.rb +1 -1
  103. data/lib/cassandra/statements.rb +1 -1
  104. data/lib/cassandra/statements/batch.rb +10 -25
  105. data/lib/cassandra/statements/bound.rb +1 -1
  106. data/lib/cassandra/statements/prepared.rb +24 -31
  107. data/lib/cassandra/statements/simple.rb +22 -66
  108. data/lib/cassandra/statements/void.rb +1 -1
  109. data/lib/cassandra/table.rb +36 -5
  110. data/lib/cassandra/time_uuid.rb +1 -1
  111. data/lib/cassandra/tuple.rb +124 -0
  112. data/lib/cassandra/types.rb +1406 -0
  113. data/lib/cassandra/udt.rb +420 -0
  114. data/lib/cassandra/util.rb +42 -64
  115. data/lib/cassandra/uuid.rb +1 -1
  116. data/lib/cassandra/uuid/generator.rb +1 -1
  117. data/lib/cassandra/version.rb +2 -2
  118. metadata +19 -15
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -91,7 +91,7 @@ module Cassandra
91
91
  end
92
92
 
93
93
  let(:port) { 9042 }
94
- let(:protocol_version) { 2 }
94
+ let(:protocol_version) { 3 }
95
95
  let(:connect_timeout) { 10 }
96
96
  let(:ssl) { false }
97
97
  let(:logger) { NullLogger.new }
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -76,12 +76,13 @@ module Cassandra
76
76
  unless paging_state.nil?
77
77
  paging_state = String(paging_state)
78
78
  Util.assert_not_empty(paging_state) { ":paging_state must not be empty" }
79
+ Util.assert(!page_size.nil?) { ":page_size is required when :paging_state is given" }
79
80
  end
80
81
 
81
82
  if arguments.nil?
82
83
  arguments = EMPTY_LIST
83
84
  else
84
- Util.assert_instance_of(::Array, arguments) { ":arguments must be an Array, #{arguments.inspect} given" }
85
+ Util.assert_instance_of_one_of([::Array, ::Hash], arguments) { ":arguments must be an Array or a Hash, #{arguments.inspect} given" }
85
86
  end
86
87
 
87
88
  @consistency = consistency
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -51,11 +51,12 @@ module Cassandra
51
51
  attr_reader :replication
52
52
 
53
53
  # @private
54
- def initialize(name, durable_writes, replication, tables)
54
+ def initialize(name, durable_writes, replication, tables, types)
55
55
  @name = name
56
56
  @durable_writes = durable_writes
57
57
  @replication = replication
58
58
  @tables = tables
59
+ @types = types
59
60
  end
60
61
 
61
62
  # @return [Boolean] whether durables writes are enabled for this keyspace
@@ -91,6 +92,35 @@ module Cassandra
91
92
  end
92
93
  alias :tables :each_table
93
94
 
95
+ # @return [Boolean] whether this keyspace has a user-defined type with the
96
+ # given name
97
+ # @param name [String] user-defined type name
98
+ def has_type?(name)
99
+ @types.has_key?(name)
100
+ end
101
+
102
+ # @return [Cassandra::Types::UserDefined, nil] a type or nil
103
+ # @param name [String] user-defined type name
104
+ def type(name)
105
+ @types[name]
106
+ end
107
+
108
+ # Yield or enumerate each user-defined type present in this keyspace
109
+ # @overload each_type
110
+ # @yieldparam type [Cassandra::Types::UserDefined] current type
111
+ # @return [Cassandra::Keyspace] self
112
+ # @overload each_type
113
+ # @return [Array<Cassandra::Types::UserDefined>] a list of user-defined types
114
+ def each_type(&block)
115
+ if block_given?
116
+ @types.each_value(&block)
117
+ self
118
+ else
119
+ @types.values
120
+ end
121
+ end
122
+ alias :types :each_type
123
+
94
124
  # @return [String] a cql representation of this table
95
125
  def to_cql
96
126
  "CREATE KEYSPACE #{Util.escape_name(@name)} WITH REPLICATION = #{@replication.to_cql} AND DURABLE_WRITES = #{@durable_writes};"
@@ -102,7 +132,8 @@ module Cassandra
102
132
  @name == other.name &&
103
133
  @durable_writes == other.durable_writes &&
104
134
  @replication == other.replication &&
105
- @tables == other.raw_tables
135
+ @tables == other.raw_tables &&
136
+ @types == other.raw_types
106
137
  end
107
138
  alias :== :eql?
108
139
 
@@ -115,14 +146,28 @@ module Cassandra
115
146
  def update_table(table)
116
147
  tables = @tables.dup
117
148
  tables[table.name] = table
118
- Keyspace.new(@name, @durable_writes, @replication, tables)
149
+ Keyspace.new(@name, @durable_writes, @replication, tables, @types)
119
150
  end
120
151
 
121
152
  # @private
122
153
  def delete_table(table_name)
123
154
  tables = @tables.dup
124
155
  tables.delete(table_name)
125
- Keyspace.new(@name, @durable_writes, @replication, tables)
156
+ Keyspace.new(@name, @durable_writes, @replication, tables, @types)
157
+ end
158
+
159
+ # @private
160
+ def update_type(type)
161
+ types = @types.dup
162
+ types[type.name] = type
163
+ Keyspace.new(@name, @durable_writes, @replication, @tables, types)
164
+ end
165
+
166
+ # @private
167
+ def delete_type(type_name)
168
+ types = @types.dup
169
+ types.delete(type_name)
170
+ Keyspace.new(@name, @durable_writes, @replication, @tables, types)
126
171
  end
127
172
 
128
173
  # @private
@@ -141,5 +186,10 @@ module Cassandra
141
186
  def raw_tables
142
187
  @tables
143
188
  end
189
+
190
+ # @private
191
+ def raw_types
192
+ @types
193
+ end
144
194
  end
145
195
  end
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright 2013-2014 DataStax, Inc.
2
+ # Copyright 2013-2015 DataStax, Inc.
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License");
5
5
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -35,6 +35,10 @@ module Cassandra
35
35
  FALSE_BYTE = "\x00".freeze
36
36
  PROTOCOL_VERSION = "\x01".freeze
37
37
  COMPRESSION_OFF = "\x00".freeze
38
+
39
+ SCHEMA_CHANGE_TARGET_KEYSPACE = 'KEYSPACE'.freeze
40
+ SCHEMA_CHANGE_TARGET_TABLE = 'TABLE'.freeze
41
+ SCHEMA_CHANGE_TARGET_UDT = 'TYPE'.freeze
38
42
  end
39
43
  end
40
44
  end
@@ -76,4 +80,5 @@ require 'cassandra/protocol/requests/prepare_request'
76
80
  require 'cassandra/protocol/requests/execute_request'
77
81
  require 'cassandra/protocol/cql_protocol_handler'
78
82
  require 'cassandra/protocol/v1'
83
+ require 'cassandra/protocol/v3'
79
84
  require 'cassandra/protocol/coder'
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  #--
4
- # Copyright 2013-2014 DataStax, Inc.
4
+ # Copyright 2013-2015 DataStax, Inc.
5
5
  #
6
6
  # Licensed under the Apache License, Version 2.0 (the "License");
7
7
  # you may not use this file except in compliance with the License.
@@ -23,6 +23,241 @@ module Cassandra
23
23
  HAS_MORE_PAGES_FLAG = 0x02
24
24
  NO_METADATA_FLAG = 0x04
25
25
 
26
+ def write_values_v3(buffer, values, types, names = EMPTY_LIST)
27
+ if values && values.size > 0
28
+ buffer.append_short(values.size)
29
+ values.zip(types, names) do |(value, type, name)|
30
+ buffer.append_string(name) if name
31
+ write_value_v3(buffer, value, type)
32
+ end
33
+ buffer
34
+ else
35
+ buffer.append_short(0)
36
+ end
37
+ end
38
+
39
+ def write_value_v3(buffer, value, type)
40
+ case type.kind
41
+ when :ascii then write_ascii(buffer, value)
42
+ when :bigint, :counter then write_bigint(buffer, value)
43
+ when :blob then write_blob(buffer, value)
44
+ when :boolean then write_boolean(buffer, value)
45
+ when :decimal then write_decimal(buffer, value)
46
+ when :double then write_double(buffer, value)
47
+ when :float then write_float(buffer, value)
48
+ when :int then write_int(buffer, value)
49
+ when :inet then write_inet(buffer, value)
50
+ when :timestamp then write_timestamp(buffer, value)
51
+ when :uuid, :timeuuid then write_uuid(buffer, value)
52
+ when :varchar then write_varchar(buffer, value)
53
+ when :varint then write_varint(buffer, value)
54
+ when :list, :set
55
+ if value
56
+ raw = CqlByteBuffer.new
57
+ value_type = type.value_type
58
+
59
+ raw.append_int(value.size)
60
+ value.each do |element|
61
+ write_value_v3(raw, element, value_type)
62
+ end
63
+
64
+ buffer.append_bytes(raw)
65
+ else
66
+ buffer.append_int(-1)
67
+ end
68
+ when :map
69
+ if value
70
+ raw = CqlByteBuffer.new
71
+ key_type = type.key_type
72
+ value_type = type.value_type
73
+
74
+ raw.append_int(value.size)
75
+ value.each do |key, value|
76
+ write_value_v3(raw, key, key_type)
77
+ write_value_v3(raw, value, value_type)
78
+ end
79
+
80
+ buffer.append_bytes(raw)
81
+ else
82
+ buffer.append_int(-1)
83
+ end
84
+ when :udt
85
+ if value
86
+ raw = CqlByteBuffer.new
87
+ fields = type.fields
88
+
89
+ fields.each do |field|
90
+ write_value_v3(raw, value[field.name], field.type)
91
+ end
92
+
93
+ buffer.append_bytes(raw)
94
+ else
95
+ buffer.append_int(-1)
96
+ end
97
+ when :tuple
98
+ if value
99
+ raw = CqlByteBuffer.new
100
+ members = type.members
101
+
102
+ members.each_with_index do |member_type, i|
103
+ write_value_v3(raw, value[i], member_type)
104
+ end
105
+
106
+ buffer.append_bytes(raw)
107
+ else
108
+ buffer.append_int(-1)
109
+ end
110
+ else
111
+ raise Errors::EncodingError, %(Unsupported value type: #{type})
112
+ end
113
+ end
114
+
115
+ def read_values_v3(buffer, column_metadata)
116
+ ::Array.new(buffer.read_int) do |i|
117
+ row = ::Hash.new
118
+
119
+ column_metadata.each do |(_, _, column, type)|
120
+ row[column] = read_value_v3(buffer, type)
121
+ end
122
+
123
+ row
124
+ end
125
+ end
126
+
127
+ def read_value_v3(buffer, type)
128
+ case type.kind
129
+ when :ascii then read_ascii(buffer)
130
+ when :bigint, :counter then read_bigint(buffer)
131
+ when :blob then buffer.read_bytes
132
+ when :boolean then read_boolean(buffer)
133
+ when :decimal then read_decimal(buffer)
134
+ when :double then read_double(buffer)
135
+ when :float then read_float(buffer)
136
+ when :int then read_int(buffer)
137
+ when :timestamp then read_timestamp(buffer)
138
+ when :uuid then read_uuid(buffer)
139
+ when :timeuuid then read_uuid(buffer, TimeUuid)
140
+ when :varchar then read_varchar(buffer)
141
+ when :varint then read_varint(buffer)
142
+ when :inet then read_inet(buffer)
143
+ when :list
144
+ return nil unless read_size(buffer)
145
+
146
+ value_type = type.value_type
147
+ ::Array.new(buffer.read_signed_int) { read_value_v3(buffer, value_type) }
148
+ when :map
149
+ return nil unless read_size(buffer)
150
+
151
+ key_type = type.key_type
152
+ value_type = type.value_type
153
+ value = ::Hash.new
154
+
155
+ buffer.read_signed_int.times do
156
+ value[read_value_v3(buffer, key_type)] = read_value_v3(buffer, value_type)
157
+ end
158
+
159
+ value
160
+ when :set
161
+ return nil unless read_size(buffer)
162
+
163
+ value_type = type.value_type
164
+ value = ::Set.new
165
+
166
+ buffer.read_signed_int.times do
167
+ value << read_value_v3(buffer, value_type)
168
+ end
169
+
170
+ value
171
+ when :udt
172
+ return nil unless read_size(buffer)
173
+
174
+ keyspace = type.keyspace
175
+ name = type.name
176
+ fields = type.fields
177
+ values = ::Hash.new
178
+
179
+ fields.each do |field|
180
+ if buffer.empty?
181
+ values[field.name] = nil
182
+ else
183
+ values[field.name] = read_value_v3(buffer, field.type)
184
+ end
185
+ end
186
+
187
+ Cassandra::UDT::Strict.new(keyspace, name, fields, values)
188
+ when :tuple
189
+ return nil unless read_size(buffer)
190
+
191
+ members = type.members
192
+ values = ::Array.new
193
+
194
+ members.each do |member_type|
195
+ break if buffer.empty?
196
+ values << read_value_v3(buffer, member_type)
197
+ end
198
+
199
+ values.fill(nil, values.length, (members.length - values.length))
200
+
201
+ Cassandra::Tuple::Strict.new(members, values)
202
+ else
203
+ raise Errors::DecodingError, %(Unsupported value type: #{type})
204
+ end
205
+ end
206
+
207
+ def read_metadata_v3(buffer)
208
+ flags = buffer.read_int
209
+ count = buffer.read_int
210
+
211
+ paging_state = nil
212
+ paging_state = buffer.read_bytes if flags & HAS_MORE_PAGES_FLAG != 0
213
+ column_specs = nil
214
+
215
+ if flags & NO_METADATA_FLAG == 0
216
+ if flags & GLOBAL_TABLES_SPEC_FLAG != 0
217
+ keyspace_name = buffer.read_string
218
+ table_name = buffer.read_string
219
+
220
+ column_specs = ::Array.new(count) do |i|
221
+ [keyspace_name, table_name, buffer.read_string, read_type_v3(buffer)]
222
+ end
223
+ else
224
+ column_specs = ::Array.new(count) do |i|
225
+ [buffer.read_string, buffer.read_string, buffer.read_string, read_type_v3(buffer)]
226
+ end
227
+ end
228
+ end
229
+
230
+ [column_specs, paging_state]
231
+ end
232
+
233
+ def read_type_v3(buffer)
234
+ case buffer.read_unsigned_short
235
+ when 0x0000 then Types.custom(buffer.read_string)
236
+ when 0x0001 then Types.ascii
237
+ when 0x0002 then Types.bigint
238
+ when 0x0003 then Types.blob
239
+ when 0x0004 then Types.boolean
240
+ when 0x0005 then Types.counter
241
+ when 0x0006 then Types.decimal
242
+ when 0x0007 then Types.double
243
+ when 0x0008 then Types.float
244
+ when 0x0009 then Types.int
245
+ when 0x000B then Types.timestamp
246
+ when 0x000C then Types.uuid
247
+ when 0x000D then Types.varchar
248
+ when 0x000E then Types.varint
249
+ when 0x000F then Types.timeuuid
250
+ when 0x0010 then Types.inet
251
+ when 0x0020 then Types.list(read_type_v3(buffer))
252
+ when 0x0021 then Types.map(read_type_v3(buffer), read_type_v3(buffer))
253
+ when 0x0022 then Types.set(read_type_v3(buffer))
254
+ when 0x0030 then Types.udt(*read_user_defined_type(buffer))
255
+ when 0x0031 then Types.tuple(*read_tuple(buffer))
256
+ else
257
+ raise Errors::DecodingError, %(Unsupported column type: #{id})
258
+ end
259
+ end
260
+
26
261
  def write_values_v1(buffer, values, types)
27
262
  if values && values.size > 0
28
263
  buffer.append_short(values.size)
@@ -36,7 +271,7 @@ module Cassandra
36
271
  end
37
272
 
38
273
  def write_value_v1(buffer, value, type)
39
- case type
274
+ case type.kind
40
275
  when :ascii then write_ascii(buffer, value)
41
276
  when :bigint, :counter then write_bigint(buffer, value)
42
277
  when :blob then write_blob(buffer, value)
@@ -50,40 +285,35 @@ module Cassandra
50
285
  when :timestamp then write_timestamp(buffer, value)
51
286
  when :timeuuid, :uuid then write_uuid(buffer, value)
52
287
  when :varint then write_varint(buffer, value)
53
- when ::Array
54
- case type.first
55
- when :list, :set
56
- if value
57
- raw = CqlByteBuffer.new
58
- value_type = type[1]
59
-
60
- raw.append_short(value.size)
61
- value.each do |element|
62
- write_short_value(raw, element, value_type)
63
- end
64
-
65
- buffer.append_bytes(raw)
66
- else
67
- buffer.append_int(-1)
288
+ when :list, :set
289
+ if value
290
+ raw = CqlByteBuffer.new
291
+ value_type = type.value_type
292
+
293
+ raw.append_short(value.size)
294
+ value.each do |element|
295
+ write_short_value(raw, element, value_type)
68
296
  end
69
- when :map
70
- if value
71
- raw = CqlByteBuffer.new
72
- key_type = type[1]
73
- value_type = type[2]
74
-
75
- raw.append_short(value.size)
76
- value.each do |key, value|
77
- write_short_value(raw, key, key_type)
78
- write_short_value(raw, value, value_type)
79
- end
80
-
81
- buffer.append_bytes(raw)
82
- else
83
- buffer.append_int(-1)
297
+
298
+ buffer.append_bytes(raw)
299
+ else
300
+ buffer.append_int(-1)
301
+ end
302
+ when :map
303
+ if value
304
+ raw = CqlByteBuffer.new
305
+ key_type = type.key_type
306
+ value_type = type.value_type
307
+
308
+ raw.append_short(value.size)
309
+ value.each do |key, value|
310
+ write_short_value(raw, key, key_type)
311
+ write_short_value(raw, value, value_type)
84
312
  end
313
+
314
+ buffer.append_bytes(raw)
85
315
  else
86
- raise Errors::EncodingError, %(Unsupported value type: #{type})
316
+ buffer.append_int(-1)
87
317
  end
88
318
  else
89
319
  raise Errors::EncodingError, %(Unsupported value type: #{type})
@@ -103,7 +333,7 @@ module Cassandra
103
333
  end
104
334
 
105
335
  def read_value_v1(buffer, type)
106
- case type
336
+ case type.kind
107
337
  when :ascii then read_ascii(buffer)
108
338
  when :bigint, :counter then read_bigint(buffer)
109
339
  when :blob then buffer.read_bytes
@@ -118,43 +348,36 @@ module Cassandra
118
348
  when :uuid then read_uuid(buffer)
119
349
  when :timeuuid then read_uuid(buffer, TimeUuid)
120
350
  when :inet then read_inet(buffer)
121
- when ::Array
122
- case type.first
123
- when :list
124
- return nil unless read_size(buffer)
351
+ when :list
352
+ return nil unless read_size(buffer)
125
353
 
126
- value_type = type[1]
127
- ::Array.new(buffer.read_short) { read_short_value(buffer, value_type) }
128
- when :map
129
- return nil unless read_size(buffer)
354
+ value_type = type.value_type
355
+ ::Array.new(buffer.read_short) { read_short_value(buffer, value_type) }
356
+ when :map
357
+ return nil unless read_size(buffer)
130
358
 
131
- key_type = type[1]
132
- value_type = type[2]
359
+ key_type = type.key_type
360
+ value_type = type.value_type
133
361
 
134
- value = ::Hash.new
362
+ value = ::Hash.new
135
363
 
136
- buffer.read_short.times do
137
- value[read_short_value(buffer, key_type)] = read_short_value(buffer, value_type)
138
- end
364
+ buffer.read_short.times do
365
+ value[read_short_value(buffer, key_type)] = read_short_value(buffer, value_type)
366
+ end
139
367
 
140
- value
141
- when :set
142
- return nil unless read_size(buffer)
368
+ value
369
+ when :set
370
+ return nil unless read_size(buffer)
143
371
 
144
- value_type = type[1]
372
+ value_type = type.value_type
145
373
 
146
- value = ::Set.new
374
+ value = ::Set.new
147
375
 
148
- buffer.read_short.times do
149
- value << read_short_value(buffer, value_type)
150
- end
151
-
152
- value
153
- when :custom
154
- buffer.read_bytes
155
- else
156
- raise Errors::DecodingError, %(Unsupported complex value type: #{type})
376
+ buffer.read_short.times do
377
+ value << read_short_value(buffer, value_type)
157
378
  end
379
+
380
+ value
158
381
  else
159
382
  raise Errors::DecodingError, %(Unsupported value type: #{type})
160
383
  end
@@ -190,26 +413,26 @@ module Cassandra
190
413
  kind = buffer.read_unsigned_short
191
414
 
192
415
  case kind
193
- when 0x0000 then [:custom, buffer.read_string]
194
- when 0x0001 then :ascii
195
- when 0x0002 then :bigint
196
- when 0x0003 then :blob
197
- when 0x0004 then :boolean
198
- when 0x0005 then :counter
199
- when 0x0006 then :decimal
200
- when 0x0007 then :double
201
- when 0x0008 then :float
202
- when 0x0009 then :int
203
- when 0x000A then :text
204
- when 0x000B then :timestamp
205
- when 0x000C then :uuid
206
- when 0x000D then :varchar
207
- when 0x000E then :varint
208
- when 0x000F then :timeuuid
209
- when 0x0010 then :inet
210
- when 0x0020 then [:list, read_type_v1(buffer)]
211
- when 0x0021 then [:map, read_type_v1(buffer), read_type_v1(buffer)]
212
- when 0x0022 then [:set, read_type_v1(buffer)]
416
+ when 0x0000 then Types.custom(buffer.read_string)
417
+ when 0x0001 then Types.ascii
418
+ when 0x0002 then Types.bigint
419
+ when 0x0003 then Types.blob
420
+ when 0x0004 then Types.boolean
421
+ when 0x0005 then Types.counter
422
+ when 0x0006 then Types.decimal
423
+ when 0x0007 then Types.double
424
+ when 0x0008 then Types.float
425
+ when 0x0009 then Types.int
426
+ when 0x000A then Types.text
427
+ when 0x000B then Types.timestamp
428
+ when 0x000C then Types.uuid
429
+ when 0x000D then Types.varchar
430
+ when 0x000E then Types.varint
431
+ when 0x000F then Types.timeuuid
432
+ when 0x0010 then Types.inet
433
+ when 0x0020 then Types.list(read_type_v1(buffer))
434
+ when 0x0021 then Types.map(read_type_v1(buffer), read_type_v1(buffer))
435
+ when 0x0022 then Types.set(read_type_v1(buffer))
213
436
  else
214
437
  raise Errors::DecodingError, %(Unsupported column type: #{kind})
215
438
  end
@@ -380,7 +603,7 @@ module Cassandra
380
603
  end
381
604
 
382
605
  def read_short_value(buffer, type)
383
- case type
606
+ case type.kind
384
607
  when :ascii
385
608
  value = buffer.read_short_bytes
386
609
  value && value.force_encoding(::Encoding::ASCII)
@@ -427,7 +650,7 @@ module Cassandra
427
650
  end
428
651
 
429
652
  def write_short_value(buffer, value, type)
430
- case type
653
+ case type.kind
431
654
  when :ascii
432
655
  buffer.append_short_bytes(value && value.encode(::Encoding::ASCII))
433
656
  when :bigint, :counter
@@ -506,6 +729,18 @@ module Cassandra
506
729
 
507
730
  size
508
731
  end
732
+
733
+ def read_tuple(buffer)
734
+ ::Array.new(buffer.read_short) { read_type_v3(buffer) }
735
+ end
736
+
737
+ def read_user_defined_type(buffer)
738
+ keyspace = buffer.read_string
739
+ name = buffer.read_string
740
+ fields = ::Array.new(buffer.read_short) { [buffer.read_string, read_type_v3(buffer)] }
741
+
742
+ [keyspace, name, fields]
743
+ end
509
744
  end
510
745
  end
511
746
  end