data_objects 0.10.3 → 0.10.4.rc1
Sign up to get free protection for your applications and to get access to all the features.
- data/LICENSE +1 -1
- data/README.markdown +1 -1
- data/Rakefile +6 -32
- data/lib/data_objects/connection.rb +9 -6
- data/lib/data_objects/pooling.rb +1 -1
- data/lib/data_objects/spec/lib/pending_helpers.rb +11 -0
- data/lib/data_objects/spec/{helpers → lib}/ssl.rb +0 -0
- data/lib/data_objects/spec/setup.rb +5 -0
- data/lib/data_objects/spec/{command_spec.rb → shared/command_spec.rb} +54 -50
- data/lib/data_objects/spec/shared/connection_spec.rb +245 -0
- data/lib/data_objects/spec/{encoding_spec.rb → shared/encoding_spec.rb} +41 -43
- data/lib/data_objects/spec/shared/error/sql_error_spec.rb +30 -0
- data/lib/data_objects/spec/{quoting_spec.rb → shared/quoting_spec.rb} +0 -0
- data/lib/data_objects/spec/{reader_spec.rb → shared/reader_spec.rb} +31 -26
- data/lib/data_objects/spec/shared/result_spec.rb +79 -0
- data/lib/data_objects/spec/{typecast → shared/typecast}/array_spec.rb +4 -2
- data/lib/data_objects/spec/{typecast → shared/typecast}/bigdecimal_spec.rb +12 -8
- data/lib/data_objects/spec/{typecast → shared/typecast}/boolean_spec.rb +14 -10
- data/lib/data_objects/spec/{typecast → shared/typecast}/byte_array_spec.rb +6 -4
- data/lib/data_objects/spec/{typecast → shared/typecast}/class_spec.rb +5 -3
- data/lib/data_objects/spec/{typecast → shared/typecast}/date_spec.rb +13 -9
- data/lib/data_objects/spec/{typecast → shared/typecast}/datetime_spec.rb +14 -11
- data/lib/data_objects/spec/{typecast → shared/typecast}/float_spec.rb +17 -13
- data/lib/data_objects/spec/{typecast → shared/typecast}/integer_spec.rb +7 -5
- data/lib/data_objects/spec/{typecast → shared/typecast}/ipaddr_spec.rb +0 -0
- data/lib/data_objects/spec/{typecast → shared/typecast}/nil_spec.rb +23 -17
- data/lib/data_objects/spec/{typecast → shared/typecast}/other_spec.rb +11 -9
- data/lib/data_objects/spec/{typecast → shared/typecast}/range_spec.rb +4 -2
- data/lib/data_objects/spec/{typecast → shared/typecast}/string_spec.rb +10 -8
- data/lib/data_objects/spec/{typecast → shared/typecast}/time_spec.rb +44 -6
- data/lib/data_objects/transaction.rb +9 -0
- data/lib/data_objects/uri.rb +62 -4
- data/lib/data_objects/version.rb +1 -1
- data/spec/command_spec.rb +2 -2
- data/spec/connection_spec.rb +45 -25
- data/spec/pooling_spec.rb +9 -9
- data/spec/reader_spec.rb +11 -12
- data/spec/result_spec.rb +13 -11
- data/spec/spec_helper.rb +1 -16
- data/spec/transaction_spec.rb +9 -11
- data/spec/uri_spec.rb +35 -27
- data/tasks/spec.rake +8 -17
- metadata +40 -56
- data/lib/data_objects/spec/bacon.rb +0 -9
- data/lib/data_objects/spec/connection_spec.rb +0 -217
- data/lib/data_objects/spec/error/sql_error_spec.rb +0 -19
- data/lib/data_objects/spec/helpers/immediate_red_green_output.rb +0 -59
- data/lib/data_objects/spec/helpers/pending.rb +0 -22
- data/lib/data_objects/spec/result_spec.rb +0 -79
- data/tasks/metrics.rake +0 -36
@@ -1,16 +1,16 @@
|
|
1
|
-
|
1
|
+
shared_examples_for 'a driver supporting different encodings' do
|
2
2
|
|
3
|
-
|
4
|
-
@connection = DataObjects::Connection.new(CONFIG.uri)
|
5
|
-
end
|
3
|
+
describe 'character_set' do
|
6
4
|
|
7
|
-
|
8
|
-
|
9
|
-
|
5
|
+
before do
|
6
|
+
@connection = DataObjects::Connection.new(CONFIG.uri)
|
7
|
+
end
|
10
8
|
|
11
|
-
|
9
|
+
after do
|
10
|
+
@connection.close
|
11
|
+
end
|
12
12
|
|
13
|
-
|
13
|
+
it { @connection.should respond_to(:character_set) }
|
14
14
|
|
15
15
|
it 'uses utf8 by default' do
|
16
16
|
@connection.character_set.should == 'UTF-8'
|
@@ -24,9 +24,7 @@ shared 'a driver supporting different encodings' do
|
|
24
24
|
|
25
25
|
after { @latin1_connection.close }
|
26
26
|
|
27
|
-
it
|
28
|
-
@latin1_connection.character_set.should == 'ISO-8859-1'
|
29
|
-
end
|
27
|
+
it { @latin1_connection.character_set.should == 'ISO-8859-1' }
|
30
28
|
end
|
31
29
|
|
32
30
|
describe 'uses UTF-8 when an invalid encoding is given' do
|
@@ -36,29 +34,28 @@ shared 'a driver supporting different encodings' do
|
|
36
34
|
|
37
35
|
after { @latin1_connection.close }
|
38
36
|
|
39
|
-
it
|
40
|
-
@latin1_connection.character_set.should == 'UTF-8'
|
41
|
-
end
|
37
|
+
it { @latin1_connection.character_set.should == 'UTF-8' }
|
42
38
|
end
|
43
39
|
end
|
44
40
|
end
|
45
41
|
|
46
|
-
|
42
|
+
shared_examples_for 'returning correctly encoded strings for the default database encoding' do
|
47
43
|
|
48
44
|
if defined?(::Encoding)
|
49
45
|
|
46
|
+
before :all do
|
50
47
|
setup_test_environment
|
48
|
+
end
|
51
49
|
|
52
|
-
|
53
|
-
@connection.close if @connection
|
54
|
-
@connection = DataObjects::Connection.new(CONFIG.uri)
|
55
|
-
end
|
50
|
+
describe 'with encoded string support' do
|
56
51
|
|
57
|
-
|
58
|
-
|
59
|
-
|
52
|
+
before do
|
53
|
+
@connection = DataObjects::Connection.new(CONFIG.uri)
|
54
|
+
end
|
60
55
|
|
61
|
-
|
56
|
+
after do
|
57
|
+
@connection.close
|
58
|
+
end
|
62
59
|
|
63
60
|
describe 'reading a String' do
|
64
61
|
before do
|
@@ -72,9 +69,9 @@ shared 'returning correctly encoded strings for the default database encoding' d
|
|
72
69
|
end
|
73
70
|
|
74
71
|
it 'should return UTF-8 encoded String' do
|
75
|
-
@values.first.should
|
72
|
+
@values.first.should be_kind_of(String)
|
76
73
|
@values.first.encoding.name.should == 'UTF-8'
|
77
|
-
@values.last.should
|
74
|
+
@values.last.should be_kind_of(String)
|
78
75
|
@values.last.encoding.name.should == 'UTF-8'
|
79
76
|
end
|
80
77
|
end
|
@@ -93,7 +90,7 @@ shared 'returning correctly encoded strings for the default database encoding' d
|
|
93
90
|
end
|
94
91
|
|
95
92
|
it 'should return ASCII-8BIT encoded ByteArray' do
|
96
|
-
@values.first.should
|
93
|
+
@values.first.should be_kind_of(::Extlib::ByteArray)
|
97
94
|
@values.first.encoding.name.should == 'ASCII-8BIT'
|
98
95
|
end
|
99
96
|
end
|
@@ -102,25 +99,26 @@ shared 'returning correctly encoded strings for the default database encoding' d
|
|
102
99
|
|
103
100
|
end
|
104
101
|
|
105
|
-
|
102
|
+
shared_examples_for 'returning correctly encoded strings for the default internal encoding' do
|
106
103
|
|
107
104
|
if defined?(::Encoding)
|
108
105
|
|
106
|
+
before :all do
|
109
107
|
setup_test_environment
|
108
|
+
end
|
110
109
|
|
111
|
-
|
112
|
-
@connection.close if @connection
|
113
|
-
@encoding_before = Encoding.default_internal
|
114
|
-
Encoding.default_internal = 'ISO-8859-1'
|
115
|
-
@connection = DataObjects::Connection.new(CONFIG.uri)
|
116
|
-
end
|
110
|
+
describe 'with encoded string support' do
|
117
111
|
|
118
|
-
|
119
|
-
|
120
|
-
|
121
|
-
|
112
|
+
before do
|
113
|
+
@encoding_before = Encoding.default_internal
|
114
|
+
Encoding.default_internal = 'ISO-8859-1'
|
115
|
+
@connection = DataObjects::Connection.new(CONFIG.uri)
|
116
|
+
end
|
122
117
|
|
123
|
-
|
118
|
+
after do
|
119
|
+
@connection.close
|
120
|
+
Encoding.default_internal = @encoding_before
|
121
|
+
end
|
124
122
|
|
125
123
|
describe 'reading a String' do
|
126
124
|
before do
|
@@ -133,10 +131,10 @@ shared 'returning correctly encoded strings for the default internal encoding' d
|
|
133
131
|
@reader.close
|
134
132
|
end
|
135
133
|
|
136
|
-
it 'should return
|
137
|
-
@values.first.should
|
134
|
+
it 'should return ISO-8859-1 encoded String' do
|
135
|
+
@values.first.should be_kind_of(String)
|
138
136
|
@values.first.encoding.name.should == 'ISO-8859-1'
|
139
|
-
@values.last.should
|
137
|
+
@values.last.should be_kind_of(String)
|
140
138
|
@values.last.encoding.name.should == 'ISO-8859-1'
|
141
139
|
end
|
142
140
|
end
|
@@ -155,7 +153,7 @@ shared 'returning correctly encoded strings for the default internal encoding' d
|
|
155
153
|
end
|
156
154
|
|
157
155
|
it 'should return ASCII-8BIT encoded ByteArray' do
|
158
|
-
@values.first.should
|
156
|
+
@values.first.should be_kind_of(::Extlib::ByteArray)
|
159
157
|
@values.first.encoding.name.should == 'ASCII-8BIT'
|
160
158
|
end
|
161
159
|
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
shared_examples_for 'raising a SQLError' do
|
2
|
+
|
3
|
+
before :all do
|
4
|
+
setup_test_environment
|
5
|
+
end
|
6
|
+
|
7
|
+
describe "an invalid query" do
|
8
|
+
|
9
|
+
it 'should raise an error' do
|
10
|
+
@connection = DataObjects::Connection.new(CONFIG.uri)
|
11
|
+
invalid_query = @connection.create_command("SLCT * FROM widgets WHERE ad_description = ? order by id")
|
12
|
+
expect { invalid_query.execute_reader('Buy this product now!') }.to raise_error(DataObjects::SQLError)
|
13
|
+
@connection.close
|
14
|
+
end
|
15
|
+
|
16
|
+
end
|
17
|
+
|
18
|
+
|
19
|
+
describe "an invalid result set" do
|
20
|
+
|
21
|
+
it 'should raise an error' do
|
22
|
+
@connection = DataObjects::Connection.new(CONFIG.uri)
|
23
|
+
invalid_result = @connection.create_command("SELECT MAX((SELECT 1 UNION SELECT 2))")
|
24
|
+
expect { invalid_result.execute_reader }.to raise_error(DataObjects::SQLError)
|
25
|
+
@connection.close
|
26
|
+
end
|
27
|
+
|
28
|
+
end
|
29
|
+
|
30
|
+
end
|
File without changes
|
@@ -1,6 +1,8 @@
|
|
1
|
-
|
1
|
+
shared_examples_for 'a Reader' do
|
2
2
|
|
3
|
-
|
3
|
+
before :all do
|
4
|
+
setup_test_environment
|
5
|
+
end
|
4
6
|
|
5
7
|
before do
|
6
8
|
@connection = DataObjects::Connection.new(CONFIG.uri)
|
@@ -14,30 +16,33 @@ shared 'a Reader' do
|
|
14
16
|
@connection.close
|
15
17
|
end
|
16
18
|
|
17
|
-
it
|
19
|
+
it { @reader.should respond_to(:fields) }
|
18
20
|
|
19
21
|
describe 'fields' do
|
20
22
|
|
21
|
-
def array_case_insensitively_equal_to(arr)
|
22
|
-
lambda { |obj| obj.map { |f| f.downcase } == arr }
|
23
|
-
end
|
24
|
-
|
25
23
|
it 'should return the correct fields in the reader' do
|
26
24
|
# we downcase the field names as some drivers such as do_derby, do_h2,
|
27
25
|
# do_hsqldb, do_oracle return the field names as uppercase
|
28
|
-
@reader.fields.should
|
26
|
+
@reader.fields.should be_array_case_insensitively_equal_to(['code', 'name'])
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'should return the field alias as the name, when the SQL AS keyword is specified' do
|
30
|
+
reader = @connection.create_command("SELECT code AS codigo, name AS nombre FROM widgets WHERE ad_description = ? order by id").execute_reader('Buy this product now!')
|
31
|
+
reader.fields.should_not be_array_case_insensitively_equal_to(['code', 'name'])
|
32
|
+
reader.fields.should be_array_case_insensitively_equal_to(['codigo', 'nombre'])
|
33
|
+
reader.close
|
29
34
|
end
|
30
35
|
|
31
36
|
end
|
32
37
|
|
33
|
-
it
|
38
|
+
it { @reader.should respond_to(:values) }
|
34
39
|
|
35
40
|
describe 'values' do
|
36
41
|
|
37
42
|
describe 'when the reader is uninitialized' do
|
38
43
|
|
39
44
|
it 'should raise an error' do
|
40
|
-
|
45
|
+
expect { @reader.values }.to raise_error(DataObjects::DataError)
|
41
46
|
end
|
42
47
|
|
43
48
|
end
|
@@ -73,20 +78,20 @@ shared 'a Reader' do
|
|
73
78
|
end
|
74
79
|
|
75
80
|
it 'should raise an error again' do
|
76
|
-
|
81
|
+
expect { @reader.values }.to raise_error(DataObjects::DataError)
|
77
82
|
end
|
78
83
|
end
|
79
84
|
|
80
85
|
end
|
81
86
|
|
82
|
-
it
|
87
|
+
it { @reader.should respond_to(:close) }
|
83
88
|
|
84
89
|
describe 'close' do
|
85
90
|
|
86
91
|
describe 'on an open reader' do
|
87
92
|
|
88
93
|
it 'should return true' do
|
89
|
-
@reader.close.should
|
94
|
+
@reader.close.should be_true
|
90
95
|
end
|
91
96
|
|
92
97
|
end
|
@@ -98,21 +103,21 @@ shared 'a Reader' do
|
|
98
103
|
end
|
99
104
|
|
100
105
|
it 'should return false' do
|
101
|
-
@reader.close.should
|
106
|
+
@reader.close.should be_false
|
102
107
|
end
|
103
108
|
|
104
109
|
end
|
105
110
|
|
106
111
|
end
|
107
112
|
|
108
|
-
it
|
113
|
+
it { @reader.should respond_to(:next!) }
|
109
114
|
|
110
115
|
describe 'next!' do
|
111
116
|
|
112
117
|
describe 'successfully moving the cursor initially' do
|
113
118
|
|
114
119
|
it 'should return true' do
|
115
|
-
@reader.next!.should
|
120
|
+
@reader.next!.should be_true
|
116
121
|
end
|
117
122
|
|
118
123
|
end
|
@@ -125,7 +130,7 @@ shared 'a Reader' do
|
|
125
130
|
|
126
131
|
it 'should move the cursor to the next value' do
|
127
132
|
@reader.values.should == ["W0000001", "Widget 1"]
|
128
|
-
lambda { @reader.next! }.should
|
133
|
+
lambda { @reader.next! }.should change { @reader.values }
|
129
134
|
@reader.values.should == ["W0000002", "Widget 2"]
|
130
135
|
end
|
131
136
|
|
@@ -138,14 +143,14 @@ shared 'a Reader' do
|
|
138
143
|
end
|
139
144
|
|
140
145
|
it 'should return false when the end is reached' do
|
141
|
-
@reader.next!.should
|
146
|
+
@reader.next!.should be_false
|
142
147
|
end
|
143
148
|
|
144
149
|
end
|
145
150
|
|
146
151
|
end
|
147
152
|
|
148
|
-
it
|
153
|
+
it { @reader.should respond_to(:field_count) }
|
149
154
|
|
150
155
|
describe 'field_count' do
|
151
156
|
|
@@ -155,21 +160,21 @@ shared 'a Reader' do
|
|
155
160
|
|
156
161
|
end
|
157
162
|
|
158
|
-
it
|
163
|
+
it { @reader.should respond_to(:values) }
|
159
164
|
|
160
165
|
describe 'each' do
|
161
166
|
|
162
167
|
it 'should yield each row to the block for multiple columns' do
|
163
168
|
rows_yielded = 0
|
164
169
|
@reader.each do |row|
|
165
|
-
row.should
|
170
|
+
row.should respond_to(:[])
|
166
171
|
|
167
172
|
row.size.should == 2
|
168
173
|
|
169
174
|
# the field names need to be case insensitive as some drivers such as
|
170
175
|
# do_derby, do_h2, do_hsqldb return the field names as uppercase
|
171
|
-
(row['name'] || row['NAME']).should
|
172
|
-
(row['code'] || row['CODE']).should
|
176
|
+
(row['name'] || row['NAME']).should be_kind_of(String)
|
177
|
+
(row['code'] || row['CODE']).should be_kind_of(String)
|
173
178
|
|
174
179
|
rows_yielded += 1
|
175
180
|
end
|
@@ -179,13 +184,13 @@ shared 'a Reader' do
|
|
179
184
|
it 'should yield each row to the block for a single column' do
|
180
185
|
rows_yielded = 0
|
181
186
|
@reader2.each do |row|
|
182
|
-
row.should
|
187
|
+
row.should respond_to(:[])
|
183
188
|
|
184
189
|
row.size.should == 1
|
185
190
|
|
186
191
|
# the field names need to be case insensitive as some drivers such as
|
187
192
|
# do_derby, do_h2, do_hsqldb return the field names as uppercase
|
188
|
-
(row['code'] || row['CODE']).should
|
193
|
+
(row['code'] || row['CODE']).should be_kind_of(String)
|
189
194
|
|
190
195
|
rows_yielded += 1
|
191
196
|
end
|
@@ -193,7 +198,7 @@ shared 'a Reader' do
|
|
193
198
|
end
|
194
199
|
|
195
200
|
it 'should return the reader' do
|
196
|
-
@reader.each { |row| }.should
|
201
|
+
@reader.each { |row| }.should equal(@reader)
|
197
202
|
end
|
198
203
|
|
199
204
|
end
|
@@ -0,0 +1,79 @@
|
|
1
|
+
shared_examples_for 'a Result' do
|
2
|
+
|
3
|
+
before :all do
|
4
|
+
setup_test_environment
|
5
|
+
end
|
6
|
+
|
7
|
+
before do
|
8
|
+
@connection = DataObjects::Connection.new(CONFIG.uri)
|
9
|
+
@result = @connection.create_command("INSERT INTO users (name) VALUES (?)").execute_non_query("monkey")
|
10
|
+
end
|
11
|
+
|
12
|
+
after do
|
13
|
+
@connection.close
|
14
|
+
end
|
15
|
+
|
16
|
+
it { @result.should respond_to(:affected_rows) }
|
17
|
+
|
18
|
+
describe 'affected_rows' do
|
19
|
+
|
20
|
+
it 'should return the number of affected rows' do
|
21
|
+
@result.affected_rows.should == 1
|
22
|
+
end
|
23
|
+
|
24
|
+
end
|
25
|
+
|
26
|
+
end
|
27
|
+
|
28
|
+
shared_examples_for 'a Result which returns inserted key with sequences' do
|
29
|
+
|
30
|
+
describe 'insert_id' do
|
31
|
+
|
32
|
+
before do
|
33
|
+
setup_test_environment
|
34
|
+
@connection = DataObjects::Connection.new(CONFIG.uri)
|
35
|
+
command = @connection.create_command("INSERT INTO users (name) VALUES (?)")
|
36
|
+
# execute the command twice and expose the second result
|
37
|
+
command.execute_non_query("monkey")
|
38
|
+
@result = command.execute_non_query("monkey")
|
39
|
+
end
|
40
|
+
|
41
|
+
after do
|
42
|
+
@connection.close
|
43
|
+
end
|
44
|
+
|
45
|
+
it { @result.should respond_to(:affected_rows) }
|
46
|
+
|
47
|
+
it 'should return the insert_id' do
|
48
|
+
# This is actually the 2nd record inserted
|
49
|
+
@result.insert_id.should == 2
|
50
|
+
end
|
51
|
+
|
52
|
+
end
|
53
|
+
|
54
|
+
end
|
55
|
+
|
56
|
+
shared_examples_for 'a Result which returns nil without sequences' do
|
57
|
+
|
58
|
+
describe 'insert_id' do
|
59
|
+
|
60
|
+
before do
|
61
|
+
setup_test_environment
|
62
|
+
@connection = DataObjects::Connection.new(CONFIG.uri)
|
63
|
+
command = @connection.create_command("INSERT INTO invoices (invoice_number) VALUES (?)")
|
64
|
+
# execute the command twice and expose the second result
|
65
|
+
@result = command.execute_non_query("monkey")
|
66
|
+
end
|
67
|
+
|
68
|
+
after do
|
69
|
+
@connection.close
|
70
|
+
end
|
71
|
+
|
72
|
+
it 'should return the insert_id' do
|
73
|
+
# This is actually the 2nd record inserted
|
74
|
+
@result.insert_id.should be_nil
|
75
|
+
end
|
76
|
+
|
77
|
+
end
|
78
|
+
|
79
|
+
end
|