1
1
use crate :: cass_collection_types:: CassCollectionType ;
2
2
use crate :: cass_error:: CassError ;
3
- use crate :: cass_types:: { CassDataType , MapDataType } ;
3
+ use crate :: cass_types:: { CassDataType , CassDataTypeInner , MapDataType } ;
4
4
use crate :: types:: * ;
5
5
use crate :: value:: CassCqlValue ;
6
6
use crate :: { argconv:: * , value} ;
7
7
use std:: convert:: TryFrom ;
8
8
use std:: sync:: Arc ;
9
9
10
10
// These constants help us to save an allocation in case user calls `cass_collection_new` (untyped collection).
11
- static UNTYPED_LIST_TYPE : CassDataType = CassDataType :: List {
11
+ static UNTYPED_LIST_TYPE : CassDataType = CassDataType :: new ( CassDataTypeInner :: List {
12
12
typ : None ,
13
13
frozen : false ,
14
- } ;
15
- static UNTYPED_SET_TYPE : CassDataType = CassDataType :: Set {
14
+ } ) ;
15
+ static UNTYPED_SET_TYPE : CassDataType = CassDataType :: new ( CassDataTypeInner :: Set {
16
16
typ : None ,
17
17
frozen : false ,
18
- } ;
19
- static UNTYPED_MAP_TYPE : CassDataType = CassDataType :: Map {
18
+ } ) ;
19
+ static UNTYPED_MAP_TYPE : CassDataType = CassDataType :: new ( CassDataTypeInner :: Map {
20
20
typ : MapDataType :: Untyped ,
21
21
frozen : false ,
22
- } ;
22
+ } ) ;
23
23
24
24
#[ derive( Clone ) ]
25
25
pub struct CassCollection {
@@ -35,18 +35,22 @@ impl CassCollection {
35
35
let index = self . items . len ( ) ;
36
36
37
37
// Do validation only if it's a typed collection.
38
- if let Some ( data_type) = & self . data_type {
39
- match data_type. as_ref ( ) {
40
- CassDataType :: List { typ : subtype, .. }
41
- | CassDataType :: Set { typ : subtype, .. } => {
38
+ if let Some ( data_type) = & self
39
+ . data_type
40
+ . as_ref ( )
41
+ . map ( |dt| unsafe { dt. get_unchecked ( ) } )
42
+ {
43
+ match data_type {
44
+ CassDataTypeInner :: List { typ : subtype, .. }
45
+ | CassDataTypeInner :: Set { typ : subtype, .. } => {
42
46
if let Some ( subtype) = subtype {
43
47
if !value:: is_type_compatible ( value, subtype) {
44
48
return CassError :: CASS_ERROR_LIB_INVALID_VALUE_TYPE ;
45
49
}
46
50
}
47
51
}
48
52
49
- CassDataType :: Map { typ, .. } => {
53
+ CassDataTypeInner :: Map { typ, .. } => {
50
54
// Cpp-driver does the typecheck only if both map types are present...
51
55
// However, we decided not to mimic this behaviour (which is probably a bug).
52
56
// We will do the typecheck if just the key type is defined as well (half-typed maps).
@@ -146,12 +150,16 @@ unsafe extern "C" fn cass_collection_new_from_data_type(
146
150
item_count : size_t ,
147
151
) -> * mut CassCollection {
148
152
let data_type = clone_arced ( data_type) ;
149
- let ( capacity, collection_type) = match data_type. as_ref ( ) {
150
- CassDataType :: List { .. } => ( item_count, CassCollectionType :: CASS_COLLECTION_TYPE_LIST ) ,
151
- CassDataType :: Set { .. } => ( item_count, CassCollectionType :: CASS_COLLECTION_TYPE_SET ) ,
153
+ let ( capacity, collection_type) = match data_type. get_unchecked ( ) {
154
+ CassDataTypeInner :: List { .. } => {
155
+ ( item_count, CassCollectionType :: CASS_COLLECTION_TYPE_LIST )
156
+ }
157
+ CassDataTypeInner :: Set { .. } => ( item_count, CassCollectionType :: CASS_COLLECTION_TYPE_SET ) ,
152
158
// Maps consist of a key and a value, so twice
153
159
// the number of CassCqlValue will be stored.
154
- CassDataType :: Map { .. } => ( item_count * 2 , CassCollectionType :: CASS_COLLECTION_TYPE_MAP ) ,
160
+ CassDataTypeInner :: Map { .. } => {
161
+ ( item_count * 2 , CassCollectionType :: CASS_COLLECTION_TYPE_MAP )
162
+ }
155
163
_ => return std:: ptr:: null_mut ( ) ,
156
164
} ;
157
165
let capacity = capacity as usize ;
@@ -216,7 +224,7 @@ mod tests {
216
224
217
225
use crate :: {
218
226
cass_error:: CassError ,
219
- cass_types:: { CassDataType , CassValueType , MapDataType } ,
227
+ cass_types:: { CassDataType , CassDataTypeInner , CassValueType , MapDataType } ,
220
228
collection:: {
221
229
cass_collection_append_double, cass_collection_append_float, cass_collection_free,
222
230
} ,
@@ -256,7 +264,7 @@ mod tests {
256
264
257
265
// untyped map (via cass_collection_new_from_data_type - collection's type is Some(untyped_map)).
258
266
{
259
- let dt = Arc :: new ( CassDataType :: Map {
267
+ let dt = CassDataType :: new_arced ( CassDataTypeInner :: Map {
260
268
typ : MapDataType :: Untyped ,
261
269
frozen : false ,
262
270
} ) ;
@@ -285,8 +293,8 @@ mod tests {
285
293
286
294
// half-typed map (key-only)
287
295
{
288
- let dt = Arc :: new ( CassDataType :: Map {
289
- typ : MapDataType :: Key ( Arc :: new ( CassDataType :: Value (
296
+ let dt = CassDataType :: new_arced ( CassDataTypeInner :: Map {
297
+ typ : MapDataType :: Key ( CassDataType :: new_arced ( CassDataTypeInner :: Value (
290
298
CassValueType :: CASS_VALUE_TYPE_BOOLEAN ,
291
299
) ) ) ,
292
300
frozen : false ,
@@ -324,10 +332,12 @@ mod tests {
324
332
325
333
// typed map
326
334
{
327
- let dt = Arc :: new ( CassDataType :: Map {
335
+ let dt = CassDataType :: new_arced ( CassDataTypeInner :: Map {
328
336
typ : MapDataType :: KeyAndValue (
329
- Arc :: new ( CassDataType :: Value ( CassValueType :: CASS_VALUE_TYPE_BOOLEAN ) ) ,
330
- Arc :: new ( CassDataType :: Value (
337
+ CassDataType :: new_arced ( CassDataTypeInner :: Value (
338
+ CassValueType :: CASS_VALUE_TYPE_BOOLEAN ,
339
+ ) ) ,
340
+ CassDataType :: new_arced ( CassDataTypeInner :: Value (
331
341
CassValueType :: CASS_VALUE_TYPE_SMALL_INT ,
332
342
) ) ,
333
343
) ,
@@ -383,7 +393,7 @@ mod tests {
383
393
384
394
// untyped set (via cass_collection_new_from_data_type, collection's type is Some(untyped_set))
385
395
{
386
- let dt = Arc :: new ( CassDataType :: Set {
396
+ let dt = CassDataType :: new_arced ( CassDataTypeInner :: Set {
387
397
typ : None ,
388
398
frozen : false ,
389
399
} ) ;
@@ -404,8 +414,8 @@ mod tests {
404
414
405
415
// typed set
406
416
{
407
- let dt = Arc :: new ( CassDataType :: Set {
408
- typ : Some ( Arc :: new ( CassDataType :: Value (
417
+ let dt = CassDataType :: new_arced ( CassDataTypeInner :: Set {
418
+ typ : Some ( CassDataType :: new_arced ( CassDataTypeInner :: Value (
409
419
CassValueType :: CASS_VALUE_TYPE_BOOLEAN ,
410
420
) ) ) ,
411
421
frozen : false ,
@@ -443,7 +453,7 @@ mod tests {
443
453
444
454
// untyped list (via cass_collection_new_from_data_type, collection's type is Some(untyped_list))
445
455
{
446
- let dt = Arc :: new ( CassDataType :: Set {
456
+ let dt = CassDataType :: new_arced ( CassDataTypeInner :: Set {
447
457
typ : None ,
448
458
frozen : false ,
449
459
} ) ;
@@ -464,8 +474,8 @@ mod tests {
464
474
465
475
// typed list
466
476
{
467
- let dt = Arc :: new ( CassDataType :: Set {
468
- typ : Some ( Arc :: new ( CassDataType :: Value (
477
+ let dt = CassDataType :: new_arced ( CassDataTypeInner :: Set {
478
+ typ : Some ( CassDataType :: new_arced ( CassDataTypeInner :: Value (
469
479
CassValueType :: CASS_VALUE_TYPE_BOOLEAN ,
470
480
) ) ) ,
471
481
frozen : false ,
0 commit comments