gotime-cassandra_object 2.0.0 → 2.1.0
Sign up to get free protection for your applications and to get access to all the features.
- data/Gemfile.lock +1 -1
- data/gotime-cassandra_object.gemspec +1 -1
- data/lib/cassandra_object/attributes.rb +11 -17
- data/lib/cassandra_object/base.rb +3 -6
- data/lib/cassandra_object/connection.rb +1 -1
- data/lib/cassandra_object/finder_methods.rb +4 -0
- data/lib/cassandra_object/persistence.rb +1 -4
- data/lib/cassandra_object/timestamps.rb +9 -13
- data/lib/cassandra_object/type.rb +19 -0
- data/lib/cassandra_object/types/boolean_type.rb +23 -0
- data/lib/cassandra_object/types/date_type.rb +20 -0
- data/lib/cassandra_object/types/float_type.rb +19 -0
- data/lib/cassandra_object/types/hash_type.rb +16 -0
- data/lib/cassandra_object/types/integer_type.rb +19 -0
- data/lib/cassandra_object/types/string_type.rb +16 -0
- data/lib/cassandra_object/types/time_type.rb +27 -0
- data/lib/cassandra_object/types/time_with_zone_type.rb +18 -0
- data/lib/cassandra_object/types/utf8_string_type.rb +18 -0
- data/lib/cassandra_object/types.rb +9 -148
- data/lib/cassandra_object.rb +14 -2
- data/test/base_test.rb +18 -0
- data/test/finder_methods_test.rb +8 -0
- data/test/identity_test.rb +1 -1
- data/test/test_helper.rb +4 -0
- data/test/timestamps_test.rb +27 -0
- data/test/types/boolean_type_test.rb +23 -0
- data/test/types/date_type_test.rb +4 -0
- data/test/types/float_type_test.rb +4 -0
- data/test/types/hash_type_test.rb +4 -0
- data/test/types/integer_type_test.rb +18 -0
- data/test/types/string_type_test.rb +4 -0
- data/test/types/time_type_test.rb +4 -0
- data/test/types/utf8_string_type_test.rb +4 -0
- data/test-old/types_test.rb +1 -1
- metadata +38 -9
- data/lib/cassandra_object/type_registration.rb +0 -11
data/Gemfile.lock
CHANGED
@@ -1,12 +1,10 @@
|
|
1
1
|
module CassandraObject
|
2
2
|
class Attribute
|
3
3
|
attr_reader :name, :converter, :expected_type
|
4
|
-
def initialize(name,
|
4
|
+
def initialize(name, converter, expected_type)
|
5
5
|
@name = name.to_s
|
6
|
-
@owner_class = owner_class
|
7
6
|
@converter = converter
|
8
7
|
@expected_type = expected_type
|
9
|
-
@options = options
|
10
8
|
end
|
11
9
|
|
12
10
|
def check_value!(value)
|
@@ -25,33 +23,29 @@ module CassandraObject
|
|
25
23
|
self.model_attributes = {}.with_indifferent_access
|
26
24
|
end
|
27
25
|
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
26
|
+
if type_mapping = CassandraObject::Type.get_mapping(options[:type])
|
27
|
+
converter = type_mapping.converter
|
28
|
+
expected_type = type_mapping.expected_type
|
29
|
+
elsif options[:converter]
|
30
|
+
converter = options[:converter]
|
31
|
+
expected_type = options[:type]
|
32
|
+
else
|
33
|
+
raise "Unknown type #{options[:type]}"
|
33
34
|
end
|
34
35
|
|
35
|
-
model_attributes[name] = Attribute.new(name,
|
36
|
+
model_attributes[name] = Attribute.new(name, converter, expected_type)
|
36
37
|
end
|
37
38
|
|
38
39
|
def define_attribute_methods
|
39
40
|
super(model_attributes.keys)
|
40
41
|
end
|
41
|
-
|
42
|
-
def register_attribute_type(name, expected_type, converter)
|
43
|
-
attribute_types[name] = { expected_type: expected_type, converter: converter }.with_indifferent_access
|
44
|
-
end
|
45
42
|
end
|
46
43
|
|
47
44
|
included do
|
48
45
|
class_attribute :model_attributes
|
49
46
|
self.model_attributes = {}.with_indifferent_access
|
50
47
|
|
51
|
-
attribute_method_suffix("", "=")
|
52
|
-
|
53
|
-
cattr_accessor :attribute_types
|
54
|
-
self.attribute_types = {}.with_indifferent_access
|
48
|
+
attribute_method_suffix("", "=")
|
55
49
|
end
|
56
50
|
|
57
51
|
def write_attribute(name, value)
|
@@ -2,10 +2,11 @@ require 'cassandra/0.8'
|
|
2
2
|
require 'set'
|
3
3
|
|
4
4
|
require 'cassandra_object/log_subscriber'
|
5
|
+
require 'cassandra_object/types'
|
5
6
|
|
6
7
|
module CassandraObject
|
7
8
|
class Base
|
8
|
-
|
9
|
+
class << self
|
9
10
|
def column_family=(column_family)
|
10
11
|
@column_family = column_family
|
11
12
|
end
|
@@ -13,10 +14,7 @@ module CassandraObject
|
|
13
14
|
def column_family
|
14
15
|
@column_family || name.pluralize
|
15
16
|
end
|
16
|
-
end
|
17
|
-
extend Naming
|
18
17
|
|
19
|
-
class << self
|
20
18
|
def base_class
|
21
19
|
klass = self
|
22
20
|
while klass.superclass != Base
|
@@ -40,6 +38,7 @@ module CassandraObject
|
|
40
38
|
include Associations
|
41
39
|
include Batches
|
42
40
|
include FinderMethods
|
41
|
+
include Timestamps
|
43
42
|
|
44
43
|
attr_reader :attributes
|
45
44
|
attr_accessor :key
|
@@ -62,5 +61,3 @@ module CassandraObject
|
|
62
61
|
end
|
63
62
|
end
|
64
63
|
end
|
65
|
-
|
66
|
-
require 'cassandra_object/type_registration'
|
@@ -59,9 +59,6 @@ module CassandraObject
|
|
59
59
|
# remove any attributes we don't know about. we would do this earlier, but we want to make such
|
60
60
|
# attributes available to migrations
|
61
61
|
attributes.delete_if{|k,_| !model_attributes.keys.include?(k)}
|
62
|
-
p "attributes = #{attributes.inspect}"
|
63
|
-
|
64
|
-
p "attributes.slice = #{attributes.dup.slice!(*model_attributes.keys).inspect}"
|
65
62
|
|
66
63
|
allocate.tap do |object|
|
67
64
|
object.instance_variable_set("@schema_version", attributes.delete('schema_version'))
|
@@ -73,7 +70,7 @@ module CassandraObject
|
|
73
70
|
end
|
74
71
|
|
75
72
|
def encode_columns_hash(attributes, schema_version)
|
76
|
-
attributes.inject(
|
73
|
+
attributes.inject({}) do |memo, (column_name, value)|
|
77
74
|
# cassandra stores bytes, not strings, so it has no concept of encodings. The ruby thrift gem
|
78
75
|
# expects all strings to be encoded as ascii-8bit.
|
79
76
|
# don't attempt to encode columns that are nil
|
@@ -3,21 +3,17 @@ module CassandraObject
|
|
3
3
|
extend ActiveSupport::Concern
|
4
4
|
|
5
5
|
included do
|
6
|
-
|
6
|
+
attribute :created_at, type: :time#_with_zone
|
7
|
+
attribute :updated_at, type: :time#_with_zone
|
7
8
|
|
8
|
-
|
9
|
-
|
9
|
+
before_create do #|r|
|
10
|
+
self.created_at ||= Time.current
|
11
|
+
self.updated_at ||= Time.current
|
12
|
+
end
|
10
13
|
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
def set_created_at
|
16
|
-
self.created_at = Time.current unless timestamp_override
|
17
|
-
end
|
18
|
-
|
19
|
-
def set_updated_at
|
20
|
-
self.updated_at = Time.current unless timestamp_override
|
14
|
+
before_update if: :changed? do #|r|
|
15
|
+
self.updated_at = Time.current
|
16
|
+
end
|
21
17
|
end
|
22
18
|
end
|
23
19
|
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Type
|
3
|
+
class TypeMapping < Struct.new(:expected_type, :converter)
|
4
|
+
end
|
5
|
+
|
6
|
+
cattr_accessor :attribute_types
|
7
|
+
self.attribute_types = {}.with_indifferent_access
|
8
|
+
|
9
|
+
class << self
|
10
|
+
def register(name, expected_type, converter)
|
11
|
+
attribute_types[name] = TypeMapping.new(expected_type, converter)
|
12
|
+
end
|
13
|
+
|
14
|
+
def get_mapping(name)
|
15
|
+
attribute_types[name]
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Types
|
3
|
+
module BooleanType
|
4
|
+
TRUE_VALS = [true, 'true', '1']
|
5
|
+
FALSE_VALS = [false, 'false', '0', '', nil]
|
6
|
+
VALID_VALS = TRUE_VALS + FALSE_VALS
|
7
|
+
|
8
|
+
def encode(bool)
|
9
|
+
unless VALID_VALS.include?(bool)
|
10
|
+
raise ArgumentError.new("#{self} requires a boolean")
|
11
|
+
end
|
12
|
+
TRUE_VALS.include?(bool) ? '1' : '0'
|
13
|
+
end
|
14
|
+
module_function :encode
|
15
|
+
|
16
|
+
def decode(str)
|
17
|
+
raise ArgumentError.new("Cannot convert #{str} into a boolean") unless VALID_VALS.include?(str)
|
18
|
+
TRUE_VALS.include?(str)
|
19
|
+
end
|
20
|
+
module_function :decode
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Types
|
3
|
+
module DateType
|
4
|
+
FORMAT = '%Y-%m-%d'
|
5
|
+
REGEX = /\A\d{4}-\d{2}-\d{2}\Z/
|
6
|
+
def encode(date)
|
7
|
+
raise ArgumentError.new("#{self} requires a Date") unless date.kind_of?(Date)
|
8
|
+
date.strftime(FORMAT)
|
9
|
+
end
|
10
|
+
module_function :encode
|
11
|
+
|
12
|
+
def decode(str)
|
13
|
+
return nil if str.empty?
|
14
|
+
raise ArgumentError.new("Cannot convert #{str} into a Date") unless str.kind_of?(String) && str.match(REGEX)
|
15
|
+
Date.strptime(str, FORMAT)
|
16
|
+
end
|
17
|
+
module_function :decode
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Types
|
3
|
+
module FloatType
|
4
|
+
REGEX = /\A[-+]?\d+(\.\d+)?\Z/
|
5
|
+
def encode(float)
|
6
|
+
raise ArgumentError.new("#{self} requires a Float") unless float.kind_of?(Float)
|
7
|
+
float.to_s
|
8
|
+
end
|
9
|
+
module_function :encode
|
10
|
+
|
11
|
+
def decode(str)
|
12
|
+
return nil if str.empty?
|
13
|
+
raise ArgumentError.new("Cannot convert #{str} into a Float") unless str.kind_of?(String) && str.match(REGEX)
|
14
|
+
str.to_f
|
15
|
+
end
|
16
|
+
module_function :decode
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Types
|
3
|
+
module HashType
|
4
|
+
def encode(hash)
|
5
|
+
raise ArgumentError.new("#{self} requires a Hash") unless hash.kind_of?(Hash)
|
6
|
+
ActiveSupport::JSON.encode(hash)
|
7
|
+
end
|
8
|
+
module_function :encode
|
9
|
+
|
10
|
+
def decode(str)
|
11
|
+
ActiveSupport::JSON.decode(str)
|
12
|
+
end
|
13
|
+
module_function :decode
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Types
|
3
|
+
module IntegerType
|
4
|
+
REGEX = /\A[-+]?\d+\Z/
|
5
|
+
def encode(int)
|
6
|
+
raise ArgumentError.new("#{self} requires an Integer. You passed #{int.inspect}") unless int.kind_of?(Integer)
|
7
|
+
int.to_s
|
8
|
+
end
|
9
|
+
module_function :encode
|
10
|
+
|
11
|
+
def decode(str)
|
12
|
+
return nil if str.empty?
|
13
|
+
raise ArgumentError.new("Cannot convert #{str} into an Integer") unless str.kind_of?(String) && str.match(REGEX)
|
14
|
+
str.to_i
|
15
|
+
end
|
16
|
+
module_function :decode
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Types
|
3
|
+
module StringType
|
4
|
+
def encode(str)
|
5
|
+
raise ArgumentError.new("#{self} requires a String") unless str.kind_of?(String)
|
6
|
+
str.dup
|
7
|
+
end
|
8
|
+
module_function :encode
|
9
|
+
|
10
|
+
def decode(str)
|
11
|
+
str
|
12
|
+
end
|
13
|
+
module_function :decode
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Types
|
3
|
+
module TimeType
|
4
|
+
# lifted from the implementation of Time.xmlschema and simplified
|
5
|
+
REGEX = /\A\s*
|
6
|
+
(-?\d+)-(\d\d)-(\d\d)
|
7
|
+
T
|
8
|
+
(\d\d):(\d\d):(\d\d)
|
9
|
+
(\.\d*)?
|
10
|
+
(Z|[+-]\d\d:\d\d)?
|
11
|
+
\s*\z/ix
|
12
|
+
|
13
|
+
def encode(time)
|
14
|
+
raise ArgumentError.new("#{self} requires a Time") unless time.kind_of?(Time)
|
15
|
+
time.xmlschema(6)
|
16
|
+
end
|
17
|
+
module_function :encode
|
18
|
+
|
19
|
+
def decode(str)
|
20
|
+
return nil if str.empty?
|
21
|
+
raise ArgumentError.new("Cannot convert #{str} into a Time") unless str.kind_of?(String) && str.match(REGEX)
|
22
|
+
Time.xmlschema(str)
|
23
|
+
end
|
24
|
+
module_function :decode
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Types
|
3
|
+
module TimeWithZoneType
|
4
|
+
def encode(time)
|
5
|
+
raise ArgumentError.new("#{self} requires a Time") unless time.kind_of?(Time)
|
6
|
+
time.utc.xmlschema(6)
|
7
|
+
end
|
8
|
+
module_function :encode
|
9
|
+
|
10
|
+
def decode(str)
|
11
|
+
return nil if str.empty?
|
12
|
+
raise ArgumentError.new("Cannot convert #{str} into a Time") unless str.kind_of?(String) && str.match(TimeType::REGEX)
|
13
|
+
Time.xmlschema(str).in_time_zone
|
14
|
+
end
|
15
|
+
module_function :decode
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
module CassandraObject
|
2
|
+
class Types
|
3
|
+
module UTF8StringType
|
4
|
+
def encode(str)
|
5
|
+
# This is technically the most correct, but it is a pain to require utf-8 encoding for all strings. Should revisit.
|
6
|
+
#raise ArgumentError.new("#{self} requires a UTF-8 encoded String") unless str.kind_of?(String) && str.encoding == Encoding::UTF_8
|
7
|
+
raise ArgumentError.new("#{self} requires a String") unless str.kind_of?(String)
|
8
|
+
str.dup
|
9
|
+
end
|
10
|
+
module_function :encode
|
11
|
+
|
12
|
+
def decode(str)
|
13
|
+
str.force_encoding('UTF-8')
|
14
|
+
end
|
15
|
+
module_function :decode
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -1,148 +1,9 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
def decode(str)
|
11
|
-
return nil if str.empty?
|
12
|
-
raise ArgumentError.new("Cannot convert #{str} into an Integer") unless str.kind_of?(String) && str.match(REGEX)
|
13
|
-
str.to_i
|
14
|
-
end
|
15
|
-
module_function :decode
|
16
|
-
end
|
17
|
-
|
18
|
-
module FloatType
|
19
|
-
REGEX = /\A[-+]?\d+(\.\d+)?\Z/
|
20
|
-
def encode(float)
|
21
|
-
raise ArgumentError.new("#{self} requires a Float") unless float.kind_of?(Float)
|
22
|
-
float.to_s
|
23
|
-
end
|
24
|
-
module_function :encode
|
25
|
-
|
26
|
-
def decode(str)
|
27
|
-
return nil if str.empty?
|
28
|
-
raise ArgumentError.new("Cannot convert #{str} into a Float") unless str.kind_of?(String) && str.match(REGEX)
|
29
|
-
str.to_f
|
30
|
-
end
|
31
|
-
module_function :decode
|
32
|
-
end
|
33
|
-
|
34
|
-
module DateType
|
35
|
-
FORMAT = '%Y-%m-%d'
|
36
|
-
REGEX = /\A\d{4}-\d{2}-\d{2}\Z/
|
37
|
-
def encode(date)
|
38
|
-
raise ArgumentError.new("#{self} requires a Date") unless date.kind_of?(Date)
|
39
|
-
date.strftime(FORMAT)
|
40
|
-
end
|
41
|
-
module_function :encode
|
42
|
-
|
43
|
-
def decode(str)
|
44
|
-
return nil if str.empty?
|
45
|
-
raise ArgumentError.new("Cannot convert #{str} into a Date") unless str.kind_of?(String) && str.match(REGEX)
|
46
|
-
Date.strptime(str, FORMAT)
|
47
|
-
end
|
48
|
-
module_function :decode
|
49
|
-
end
|
50
|
-
|
51
|
-
module TimeType
|
52
|
-
# lifted from the implementation of Time.xmlschema and simplified
|
53
|
-
REGEX = /\A\s*
|
54
|
-
(-?\d+)-(\d\d)-(\d\d)
|
55
|
-
T
|
56
|
-
(\d\d):(\d\d):(\d\d)
|
57
|
-
(\.\d*)?
|
58
|
-
(Z|[+-]\d\d:\d\d)?
|
59
|
-
\s*\z/ix
|
60
|
-
|
61
|
-
def encode(time)
|
62
|
-
raise ArgumentError.new("#{self} requires a Time") unless time.kind_of?(Time)
|
63
|
-
time.xmlschema(6)
|
64
|
-
end
|
65
|
-
module_function :encode
|
66
|
-
|
67
|
-
def decode(str)
|
68
|
-
return nil if str.empty?
|
69
|
-
raise ArgumentError.new("Cannot convert #{str} into a Time") unless str.kind_of?(String) && str.match(REGEX)
|
70
|
-
Time.xmlschema(str)
|
71
|
-
end
|
72
|
-
module_function :decode
|
73
|
-
end
|
74
|
-
|
75
|
-
module TimeWithZoneType
|
76
|
-
def encode(time)
|
77
|
-
raise ArgumentError.new("#{self} requires a Time") unless time.kind_of?(Time)
|
78
|
-
time.utc.xmlschema(6)
|
79
|
-
end
|
80
|
-
module_function :encode
|
81
|
-
|
82
|
-
def decode(str)
|
83
|
-
return nil if str.empty?
|
84
|
-
raise ArgumentError.new("Cannot convert #{str} into a Time") unless str.kind_of?(String) && str.match(TimeType::REGEX)
|
85
|
-
Time.xmlschema(str).in_time_zone
|
86
|
-
end
|
87
|
-
module_function :decode
|
88
|
-
end
|
89
|
-
|
90
|
-
module StringType
|
91
|
-
def encode(str)
|
92
|
-
raise ArgumentError.new("#{self} requires a String") unless str.kind_of?(String)
|
93
|
-
str.dup
|
94
|
-
end
|
95
|
-
module_function :encode
|
96
|
-
|
97
|
-
def decode(str)
|
98
|
-
str
|
99
|
-
end
|
100
|
-
module_function :decode
|
101
|
-
end
|
102
|
-
|
103
|
-
module UTF8StringType
|
104
|
-
def encode(str)
|
105
|
-
# This is technically the most correct, but it is a pain to require utf-8 encoding for all strings. Should revisit.
|
106
|
-
#raise ArgumentError.new("#{self} requires a UTF-8 encoded String") unless str.kind_of?(String) && str.encoding == Encoding::UTF_8
|
107
|
-
raise ArgumentError.new("#{self} requires a String") unless str.kind_of?(String)
|
108
|
-
str.dup
|
109
|
-
end
|
110
|
-
module_function :encode
|
111
|
-
|
112
|
-
def decode(str)
|
113
|
-
str.force_encoding('UTF-8')
|
114
|
-
end
|
115
|
-
module_function :decode
|
116
|
-
end
|
117
|
-
|
118
|
-
module HashType
|
119
|
-
def encode(hash)
|
120
|
-
raise ArgumentError.new("#{self} requires a Hash") unless hash.kind_of?(Hash)
|
121
|
-
ActiveSupport::JSON.encode(hash)
|
122
|
-
end
|
123
|
-
module_function :encode
|
124
|
-
|
125
|
-
def decode(str)
|
126
|
-
ActiveSupport::JSON.decode(str)
|
127
|
-
end
|
128
|
-
module_function :decode
|
129
|
-
end
|
130
|
-
|
131
|
-
module BooleanType
|
132
|
-
TRUE_VALS = [true, 'true', '1']
|
133
|
-
FALSE_VALS = [false, 'false', '0', '', nil]
|
134
|
-
def encode(bool)
|
135
|
-
unless TRUE_VALS.any? { |a| bool == a } || FALSE_VALS.any? { |a| bool == a }
|
136
|
-
raise ArgumentError.new("#{self} requires a boolean")
|
137
|
-
end
|
138
|
-
TRUE_VALS.include?(bool) ? '1' : '0'
|
139
|
-
end
|
140
|
-
module_function :encode
|
141
|
-
|
142
|
-
def decode(str)
|
143
|
-
raise ArgumentError.new("Cannot convert #{str} into a boolean") unless TRUE_VALS.any? { |a| str == a } || FALSE_VALS.any? { |a| str == a }
|
144
|
-
TRUE_VALS.include?(str)
|
145
|
-
end
|
146
|
-
module_function :decode
|
147
|
-
end
|
148
|
-
end
|
1
|
+
CassandraObject::Type.register(:boolean, Object, CassandraObject::Types::BooleanType)
|
2
|
+
CassandraObject::Type.register(:date, Date, CassandraObject::Types::DateType)
|
3
|
+
CassandraObject::Type.register(:float, Float, CassandraObject::Types::FloatType)
|
4
|
+
CassandraObject::Type.register(:hash, Hash, CassandraObject::Types::HashType)
|
5
|
+
CassandraObject::Type.register(:integer, Integer, CassandraObject::Types::IntegerType)
|
6
|
+
CassandraObject::Type.register(:time, Time, CassandraObject::Types::TimeType)
|
7
|
+
CassandraObject::Type.register(:time_with_zone, ActiveSupport::TimeWithZone, CassandraObject::Types::TimeWithZoneType)
|
8
|
+
CassandraObject::Type.register(:string, String, CassandraObject::Types::UTF8StringType) #This could be changed to StringType to support non-utf8 strings
|
9
|
+
CassandraObject::Type.register(:utf8, String, CassandraObject::Types::UTF8StringType)
|
data/lib/cassandra_object.rb
CHANGED
@@ -18,12 +18,11 @@ module CassandraObject
|
|
18
18
|
autoload :Migrations
|
19
19
|
autoload :Cursor
|
20
20
|
autoload :Collection
|
21
|
-
autoload :Types
|
22
21
|
autoload :Mocking
|
23
22
|
autoload :Batches
|
24
23
|
autoload :FinderMethods
|
25
24
|
autoload :Timestamps
|
26
|
-
|
25
|
+
autoload :Type
|
27
26
|
autoload :Schema
|
28
27
|
|
29
28
|
module Tasks
|
@@ -31,6 +30,19 @@ module CassandraObject
|
|
31
30
|
autoload :Keyspace
|
32
31
|
autoload :ColumnFamily
|
33
32
|
end
|
33
|
+
|
34
|
+
class Types
|
35
|
+
extend ActiveSupport::Autoload
|
36
|
+
|
37
|
+
autoload :BooleanType
|
38
|
+
autoload :DateType
|
39
|
+
autoload :FloatType
|
40
|
+
autoload :HashType
|
41
|
+
autoload :IntegerType
|
42
|
+
autoload :TimeType
|
43
|
+
autoload :TimeWithZoneType
|
44
|
+
autoload :UTF8StringType
|
45
|
+
end
|
34
46
|
end
|
35
47
|
|
36
48
|
require 'cassandra_object/railtie'
|
data/test/base_test.rb
ADDED
@@ -0,0 +1,18 @@
|
|
1
|
+
require 'test_helper'
|
2
|
+
|
3
|
+
class CassandraObject::BaseTest < CassandraObject::TestCase
|
4
|
+
class Son < CassandraObject::Base
|
5
|
+
end
|
6
|
+
|
7
|
+
class Grandson < Son
|
8
|
+
end
|
9
|
+
|
10
|
+
test 'base_class' do
|
11
|
+
assert_equal Son, Son.base_class
|
12
|
+
assert_equal Son, Grandson.base_class
|
13
|
+
end
|
14
|
+
|
15
|
+
test 'column family' do
|
16
|
+
assert_equal 'CassandraObject::BaseTest::Sons', Son.column_family
|
17
|
+
end
|
18
|
+
end
|
data/test/finder_methods_test.rb
CHANGED
@@ -25,4 +25,12 @@ class CassandraObject::FinderMethodsTest < CassandraObject::TestCase
|
|
25
25
|
assert_equal [first_issue, second_issue].to_set, Issue.find_with_ids(first_issue.key, second_issue.key).to_set
|
26
26
|
assert_equal [first_issue, second_issue].to_set, Issue.find_with_ids([first_issue.key, second_issue.key]).to_set
|
27
27
|
end
|
28
|
+
|
29
|
+
# test 'find single id' do
|
30
|
+
# created_issue = Issue.create
|
31
|
+
#
|
32
|
+
# found_issue = Issue.find(created_issue.id)
|
33
|
+
#
|
34
|
+
# assert_equal created_issue, found_issue
|
35
|
+
# end
|
28
36
|
end
|
data/test/identity_test.rb
CHANGED
data/test/test_helper.rb
CHANGED
@@ -1,8 +1,12 @@
|
|
1
|
+
# lib = File.expand_path("#{File.dirname(__FILE__)}/../lib")
|
2
|
+
# $:.unshift(lib) unless $:.include?('lib') || $:.include?(lib)
|
3
|
+
# require File.expand_path('../../lib/cassandra_object', __FILE__)
|
1
4
|
require 'cassandra_object'
|
2
5
|
require 'rails/test_help'
|
3
6
|
|
4
7
|
class Issue < CassandraObject::Base
|
5
8
|
key :uuid
|
9
|
+
attribute :description, type: :string
|
6
10
|
end
|
7
11
|
|
8
12
|
module CassandraObject
|
@@ -0,0 +1,27 @@
|
|
1
|
+
require 'test_helper'
|
2
|
+
|
3
|
+
class CassandraObject::TimestampsTest < CassandraObject::TestCase
|
4
|
+
test 'timestamps set on create' do
|
5
|
+
issue = Issue.create
|
6
|
+
|
7
|
+
assert_in_delta Time.now.to_i, issue.created_at.to_i, 3
|
8
|
+
assert_in_delta Time.now.to_i, issue.updated_at.to_i, 3
|
9
|
+
end
|
10
|
+
|
11
|
+
test 'updated_at set on change' do
|
12
|
+
issue = Issue.create
|
13
|
+
|
14
|
+
issue.updated_at = nil
|
15
|
+
issue.description = 'lol'
|
16
|
+
issue.save
|
17
|
+
|
18
|
+
assert_in_delta Time.now.to_i, issue.updated_at.to_i, 3
|
19
|
+
end
|
20
|
+
|
21
|
+
test 'created_at sets only if nil' do
|
22
|
+
time = 5.days.ago
|
23
|
+
issue = Issue.create created_at: time
|
24
|
+
|
25
|
+
assert_equal time, issue.created_at
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
require 'test_helper'
|
2
|
+
|
3
|
+
class CassandraObject::Types::BooleanTypeTest < CassandraObject::TestCase
|
4
|
+
test 'encode' do
|
5
|
+
assert_equal '1', CassandraObject::Types::BooleanType.encode(true)
|
6
|
+
assert_equal '1', CassandraObject::Types::BooleanType.encode('true')
|
7
|
+
assert_equal '1', CassandraObject::Types::BooleanType.encode('1')
|
8
|
+
|
9
|
+
assert_equal '0', CassandraObject::Types::BooleanType.encode(false)
|
10
|
+
assert_equal '0', CassandraObject::Types::BooleanType.encode('false')
|
11
|
+
assert_equal '0', CassandraObject::Types::BooleanType.encode('0')
|
12
|
+
assert_equal '0', CassandraObject::Types::BooleanType.encode('')
|
13
|
+
|
14
|
+
assert_raise ArgumentError do
|
15
|
+
CassandraObject::Types::BooleanType.encode('wtf')
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
test 'decode' do
|
20
|
+
assert_equal true, CassandraObject::Types::BooleanType.decode('1')
|
21
|
+
assert_equal false, CassandraObject::Types::BooleanType.decode('0')
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
require 'test_helper'
|
2
|
+
|
3
|
+
class CassandraObject::Types::IntegerTypeTest < CassandraObject::TestCase
|
4
|
+
test 'encode' do
|
5
|
+
assert_equal '3', CassandraObject::Types::IntegerType.encode(3)
|
6
|
+
assert_equal '-3', CassandraObject::Types::IntegerType.encode(-3)
|
7
|
+
|
8
|
+
assert_raise ArgumentError do
|
9
|
+
CassandraObject::Types::BooleanType.encode('xx')
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
test 'decode' do
|
14
|
+
assert_nil CassandraObject::Types::IntegerType.decode('')
|
15
|
+
assert_equal 3, CassandraObject::Types::IntegerType.decode('3')
|
16
|
+
assert_equal -3, CassandraObject::Types::IntegerType.decode('-3')
|
17
|
+
end
|
18
|
+
end
|
data/test-old/types_test.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: gotime-cassandra_object
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.
|
4
|
+
version: 2.1.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -10,11 +10,11 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date: 2011-07-
|
13
|
+
date: 2011-07-25 00:00:00.000000000Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: rails
|
17
|
-
requirement: &
|
17
|
+
requirement: &2170403800 !ruby/object:Gem::Requirement
|
18
18
|
none: false
|
19
19
|
requirements:
|
20
20
|
- - ~>
|
@@ -22,10 +22,10 @@ dependencies:
|
|
22
22
|
version: '3.0'
|
23
23
|
type: :runtime
|
24
24
|
prerelease: false
|
25
|
-
version_requirements: *
|
25
|
+
version_requirements: *2170403800
|
26
26
|
- !ruby/object:Gem::Dependency
|
27
27
|
name: cassandra
|
28
|
-
requirement: &
|
28
|
+
requirement: &2152534000 !ruby/object:Gem::Requirement
|
29
29
|
none: false
|
30
30
|
requirements:
|
31
31
|
- - ~>
|
@@ -33,10 +33,10 @@ dependencies:
|
|
33
33
|
version: 0.11.3
|
34
34
|
type: :runtime
|
35
35
|
prerelease: false
|
36
|
-
version_requirements: *
|
36
|
+
version_requirements: *2152534000
|
37
37
|
- !ruby/object:Gem::Dependency
|
38
38
|
name: bundler
|
39
|
-
requirement: &
|
39
|
+
requirement: &2152533540 !ruby/object:Gem::Requirement
|
40
40
|
none: false
|
41
41
|
requirements:
|
42
42
|
- - ~>
|
@@ -44,7 +44,7 @@ dependencies:
|
|
44
44
|
version: 1.0.0
|
45
45
|
type: :development
|
46
46
|
prerelease: false
|
47
|
-
version_requirements: *
|
47
|
+
version_requirements: *2152533540
|
48
48
|
description: Cassandra ActiveModel
|
49
49
|
email: gems@gotime.com
|
50
50
|
executables: []
|
@@ -101,8 +101,17 @@ files:
|
|
101
101
|
- lib/cassandra_object/tasks/keyspace.rb
|
102
102
|
- lib/cassandra_object/tasks/ks.rake
|
103
103
|
- lib/cassandra_object/timestamps.rb
|
104
|
-
- lib/cassandra_object/
|
104
|
+
- lib/cassandra_object/type.rb
|
105
105
|
- lib/cassandra_object/types.rb
|
106
|
+
- lib/cassandra_object/types/boolean_type.rb
|
107
|
+
- lib/cassandra_object/types/date_type.rb
|
108
|
+
- lib/cassandra_object/types/float_type.rb
|
109
|
+
- lib/cassandra_object/types/hash_type.rb
|
110
|
+
- lib/cassandra_object/types/integer_type.rb
|
111
|
+
- lib/cassandra_object/types/string_type.rb
|
112
|
+
- lib/cassandra_object/types/time_type.rb
|
113
|
+
- lib/cassandra_object/types/time_with_zone_type.rb
|
114
|
+
- lib/cassandra_object/types/utf8_string_type.rb
|
106
115
|
- lib/cassandra_object/validation.rb
|
107
116
|
- test-old/active_model_test.rb
|
108
117
|
- test-old/base_test.rb
|
@@ -126,12 +135,22 @@ files:
|
|
126
135
|
- test-old/types_test.rb
|
127
136
|
- test-old/validation_test.rb
|
128
137
|
- test-old/z_mock_test.rb
|
138
|
+
- test/base_test.rb
|
129
139
|
- test/batches_test.rb
|
130
140
|
- test/connection_test.rb
|
131
141
|
- test/finder_methods_test.rb
|
132
142
|
- test/identity_test.rb
|
133
143
|
- test/persistence_test.rb
|
134
144
|
- test/test_helper.rb
|
145
|
+
- test/timestamps_test.rb
|
146
|
+
- test/types/boolean_type_test.rb
|
147
|
+
- test/types/date_type_test.rb
|
148
|
+
- test/types/float_type_test.rb
|
149
|
+
- test/types/hash_type_test.rb
|
150
|
+
- test/types/integer_type_test.rb
|
151
|
+
- test/types/string_type_test.rb
|
152
|
+
- test/types/time_type_test.rb
|
153
|
+
- test/types/utf8_string_type_test.rb
|
135
154
|
homepage: http://github.com/gotime/cassandra_object
|
136
155
|
licenses: []
|
137
156
|
post_install_message:
|
@@ -157,9 +176,19 @@ signing_key:
|
|
157
176
|
specification_version: 3
|
158
177
|
summary: Cassandra ActiveModel
|
159
178
|
test_files:
|
179
|
+
- test/base_test.rb
|
160
180
|
- test/batches_test.rb
|
161
181
|
- test/connection_test.rb
|
162
182
|
- test/finder_methods_test.rb
|
163
183
|
- test/identity_test.rb
|
164
184
|
- test/persistence_test.rb
|
165
185
|
- test/test_helper.rb
|
186
|
+
- test/timestamps_test.rb
|
187
|
+
- test/types/boolean_type_test.rb
|
188
|
+
- test/types/date_type_test.rb
|
189
|
+
- test/types/float_type_test.rb
|
190
|
+
- test/types/hash_type_test.rb
|
191
|
+
- test/types/integer_type_test.rb
|
192
|
+
- test/types/string_type_test.rb
|
193
|
+
- test/types/time_type_test.rb
|
194
|
+
- test/types/utf8_string_type_test.rb
|
@@ -1,11 +0,0 @@
|
|
1
|
-
require 'cassandra_object/types'
|
2
|
-
|
3
|
-
CassandraObject::Base.register_attribute_type(:integer, Integer, CassandraObject::IntegerType)
|
4
|
-
CassandraObject::Base.register_attribute_type(:float, Float, CassandraObject::FloatType)
|
5
|
-
CassandraObject::Base.register_attribute_type(:date, Date, CassandraObject::DateType)
|
6
|
-
CassandraObject::Base.register_attribute_type(:time, Time, CassandraObject::TimeType)
|
7
|
-
CassandraObject::Base.register_attribute_type(:time_with_zone, ActiveSupport::TimeWithZone, CassandraObject::TimeWithZoneType)
|
8
|
-
CassandraObject::Base.register_attribute_type(:string, String, CassandraObject::UTF8StringType) #This could be changed to StringType to support non-utf8 strings
|
9
|
-
CassandraObject::Base.register_attribute_type(:utf8, String, CassandraObject::UTF8StringType)
|
10
|
-
CassandraObject::Base.register_attribute_type(:hash, Hash, CassandraObject::HashType)
|
11
|
-
CassandraObject::Base.register_attribute_type(:boolean, Object, CassandraObject::BooleanType)
|