rails-dbi 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- data/ChangeLog +3694 -0
- data/LICENSE +25 -0
- data/README +271 -0
- data/bin/dbi +518 -0
- data/bin/test_broken_dbi +37 -0
- data/build/Rakefile.dbi.rb +60 -0
- data/examples/test1.pl +39 -0
- data/examples/test1.rb +20 -0
- data/examples/xmltest.rb +8 -0
- data/lib/dbi/base_classes/database.rb +135 -0
- data/lib/dbi/base_classes/driver.rb +47 -0
- data/lib/dbi/base_classes/statement.rb +171 -0
- data/lib/dbi/base_classes.rb +12 -0
- data/lib/dbi/binary.rb +25 -0
- data/lib/dbi/columninfo.rb +107 -0
- data/lib/dbi/exceptions.rb +65 -0
- data/lib/dbi/handles/database.rb +241 -0
- data/lib/dbi/handles/driver.rb +60 -0
- data/lib/dbi/handles/statement.rb +408 -0
- data/lib/dbi/handles.rb +49 -0
- data/lib/dbi/row.rb +270 -0
- data/lib/dbi/sql/preparedstatement.rb +115 -0
- data/lib/dbi/sql.rb +22 -0
- data/lib/dbi/sql_type_constants.rb +75 -0
- data/lib/dbi/trace.rb +91 -0
- data/lib/dbi/types.rb +218 -0
- data/lib/dbi/typeutil.rb +109 -0
- data/lib/dbi/utils/date.rb +59 -0
- data/lib/dbi/utils/tableformatter.rb +112 -0
- data/lib/dbi/utils/time.rb +52 -0
- data/lib/dbi/utils/timestamp.rb +96 -0
- data/lib/dbi/utils/xmlformatter.rb +73 -0
- data/lib/dbi/utils.rb +60 -0
- data/lib/dbi.rb +337 -0
- data/test/dbi/tc_columninfo.rb +94 -0
- data/test/dbi/tc_date.rb +88 -0
- data/test/dbi/tc_dbi.rb +184 -0
- data/test/dbi/tc_row.rb +256 -0
- data/test/dbi/tc_sqlbind.rb +168 -0
- data/test/dbi/tc_statementhandle.rb +29 -0
- data/test/dbi/tc_time.rb +77 -0
- data/test/dbi/tc_timestamp.rb +142 -0
- data/test/dbi/tc_types.rb +268 -0
- data/test/ts_dbi.rb +15 -0
- metadata +132 -0
data/test/dbi/tc_dbi.rb
ADDED
@@ -0,0 +1,184 @@
|
|
1
|
+
######################################################################
|
2
|
+
# tc_dbi.rb
|
3
|
+
#
|
4
|
+
# Test case for the DBI module (dbi.rb).
|
5
|
+
######################################################################
|
6
|
+
$LOAD_PATH.unshift(Dir.pwd)
|
7
|
+
$LOAD_PATH.unshift(File.dirname(Dir.pwd))
|
8
|
+
$LOAD_PATH.unshift("../../lib")
|
9
|
+
$LOAD_PATH.unshift("../../lib/dbi")
|
10
|
+
$LOAD_PATH.unshift("lib")
|
11
|
+
|
12
|
+
require 'dbi'
|
13
|
+
require 'test/unit'
|
14
|
+
|
15
|
+
class TC_DBI < Test::Unit::TestCase
|
16
|
+
def setup
|
17
|
+
@db_error = DBI::DatabaseError.new("test", 1, "montana")
|
18
|
+
@db_binary = DBI::Binary.new("test")
|
19
|
+
@url_basic = 'dbi:foo:bar'
|
20
|
+
@url_inter = 'dbi:foo:bar:host'
|
21
|
+
@url_advan = 'dbi:foo:database=db;host=xx;port=99'
|
22
|
+
end
|
23
|
+
|
24
|
+
def test_dbi_version
|
25
|
+
assert_equal("0.4.5", DBI::VERSION)
|
26
|
+
end
|
27
|
+
|
28
|
+
def test_dbd_module
|
29
|
+
assert_equal("0.3", DBI::DBD::API_VERSION)
|
30
|
+
end
|
31
|
+
|
32
|
+
def test_fetch_scroll_constants
|
33
|
+
assert_equal(1, DBI::SQL_FETCH_NEXT)
|
34
|
+
assert_equal(2, DBI::SQL_FETCH_PRIOR)
|
35
|
+
assert_equal(3, DBI::SQL_FETCH_FIRST)
|
36
|
+
assert_equal(4, DBI::SQL_FETCH_LAST)
|
37
|
+
assert_equal(5, DBI::SQL_FETCH_ABSOLUTE)
|
38
|
+
assert_equal(6, DBI::SQL_FETCH_RELATIVE)
|
39
|
+
end
|
40
|
+
|
41
|
+
def test_sql_type_constants
|
42
|
+
assert_equal(1, DBI::SQL_CHAR)
|
43
|
+
assert_equal(2, DBI::SQL_NUMERIC)
|
44
|
+
assert_equal(3, DBI::SQL_DECIMAL)
|
45
|
+
assert_equal(4, DBI::SQL_INTEGER)
|
46
|
+
assert_equal(5, DBI::SQL_SMALLINT)
|
47
|
+
assert_equal(6, DBI::SQL_FLOAT)
|
48
|
+
assert_equal(7, DBI::SQL_REAL)
|
49
|
+
assert_equal(8, DBI::SQL_DOUBLE)
|
50
|
+
assert_equal(9, DBI::SQL_DATE)
|
51
|
+
assert_equal(10, DBI::SQL_TIME)
|
52
|
+
assert_equal(11, DBI::SQL_TIMESTAMP)
|
53
|
+
assert_equal(12, DBI::SQL_VARCHAR)
|
54
|
+
assert_equal(100, DBI::SQL_OTHER)
|
55
|
+
assert_equal(-1, DBI::SQL_LONGVARCHAR)
|
56
|
+
assert_equal(-2, DBI::SQL_BINARY)
|
57
|
+
assert_equal(-3, DBI::SQL_VARBINARY)
|
58
|
+
assert_equal(-4, DBI::SQL_LONGVARBINARY)
|
59
|
+
assert_equal(-5, DBI::SQL_BIGINT)
|
60
|
+
assert_equal(-6, DBI::SQL_TINYINT)
|
61
|
+
assert_equal(-7, DBI::SQL_BIT)
|
62
|
+
assert_equal(-10, DBI::SQL_BLOB)
|
63
|
+
assert_equal(-11, DBI::SQL_CLOB)
|
64
|
+
end
|
65
|
+
|
66
|
+
def test_sql_type_names
|
67
|
+
assert_equal('BIT', DBI::SQL_TYPE_NAMES[DBI::SQL_BIT])
|
68
|
+
assert_equal('TINYINT', DBI::SQL_TYPE_NAMES[DBI::SQL_TINYINT])
|
69
|
+
assert_equal('SMALLINT', DBI::SQL_TYPE_NAMES[DBI::SQL_SMALLINT])
|
70
|
+
assert_equal('INTEGER', DBI::SQL_TYPE_NAMES[DBI::SQL_INTEGER])
|
71
|
+
assert_equal('BIGINT', DBI::SQL_TYPE_NAMES[DBI::SQL_BIGINT])
|
72
|
+
assert_equal('FLOAT', DBI::SQL_TYPE_NAMES[DBI::SQL_FLOAT])
|
73
|
+
assert_equal('REAL', DBI::SQL_TYPE_NAMES[DBI::SQL_REAL])
|
74
|
+
assert_equal('DOUBLE', DBI::SQL_TYPE_NAMES[DBI::SQL_DOUBLE])
|
75
|
+
assert_equal('NUMERIC', DBI::SQL_TYPE_NAMES[DBI::SQL_NUMERIC])
|
76
|
+
assert_equal('DECIMAL', DBI::SQL_TYPE_NAMES[DBI::SQL_DECIMAL])
|
77
|
+
assert_equal('CHAR', DBI::SQL_TYPE_NAMES[DBI::SQL_CHAR])
|
78
|
+
assert_equal('VARCHAR', DBI::SQL_TYPE_NAMES[DBI::SQL_VARCHAR])
|
79
|
+
assert_equal('LONG VARCHAR', DBI::SQL_TYPE_NAMES[DBI::SQL_LONGVARCHAR])
|
80
|
+
assert_equal('DATE', DBI::SQL_TYPE_NAMES[DBI::SQL_DATE])
|
81
|
+
assert_equal('TIME', DBI::SQL_TYPE_NAMES[DBI::SQL_TIME])
|
82
|
+
assert_equal('TIMESTAMP', DBI::SQL_TYPE_NAMES[DBI::SQL_TIMESTAMP])
|
83
|
+
assert_equal('BINARY', DBI::SQL_TYPE_NAMES[DBI::SQL_BINARY])
|
84
|
+
assert_equal('VARBINARY', DBI::SQL_TYPE_NAMES[DBI::SQL_VARBINARY])
|
85
|
+
assert_equal('LONG VARBINARY',
|
86
|
+
DBI::SQL_TYPE_NAMES[DBI::SQL_LONGVARBINARY])
|
87
|
+
assert_equal('BLOB', DBI::SQL_TYPE_NAMES[DBI::SQL_BLOB])
|
88
|
+
assert_equal('CLOB', DBI::SQL_TYPE_NAMES[DBI::SQL_CLOB])
|
89
|
+
assert_equal(nil, DBI::SQL_TYPE_NAMES[DBI::SQL_OTHER])
|
90
|
+
end
|
91
|
+
|
92
|
+
def test_dbi_exception_classes
|
93
|
+
assert(DBI::Error)
|
94
|
+
assert(DBI::Warning)
|
95
|
+
assert(DBI::InterfaceError)
|
96
|
+
assert(DBI::NotImplementedError)
|
97
|
+
assert(DBI::DatabaseError)
|
98
|
+
assert(DBI::DataError)
|
99
|
+
assert(DBI::OperationalError)
|
100
|
+
assert(DBI::IntegrityError)
|
101
|
+
assert(DBI::InternalError)
|
102
|
+
assert(DBI::ProgrammingError)
|
103
|
+
assert(DBI::NotSupportedError)
|
104
|
+
end
|
105
|
+
|
106
|
+
# This error class gets extra testing since it defines some custom
|
107
|
+
# accessors.
|
108
|
+
def test_dbi_database_error
|
109
|
+
assert_respond_to(@db_error, :errstr)
|
110
|
+
assert_respond_to(@db_error, :err)
|
111
|
+
assert_respond_to(@db_error, :state)
|
112
|
+
assert_equal("test", @db_error.errstr)
|
113
|
+
assert_equal(1, @db_error.err)
|
114
|
+
assert_equal("montana", @db_error.state)
|
115
|
+
end
|
116
|
+
|
117
|
+
def test_binary_datatype
|
118
|
+
assert_respond_to(@db_binary, :data)
|
119
|
+
assert_respond_to(@db_binary, :to_s)
|
120
|
+
assert_equal("test", @db_binary.data)
|
121
|
+
assert_equal("test", @db_binary.to_s)
|
122
|
+
end
|
123
|
+
|
124
|
+
def test_misc_constants
|
125
|
+
assert_equal(2, DBI::DEFAULT_TRACE_MODE)
|
126
|
+
assert_equal(STDERR, DBI::DEFAULT_TRACE_OUTPUT)
|
127
|
+
end
|
128
|
+
|
129
|
+
def test_last_connection
|
130
|
+
assert_respond_to(DBI, :last_connection)
|
131
|
+
end
|
132
|
+
|
133
|
+
def test_convert_types
|
134
|
+
assert_respond_to(DBI, :convert_types)
|
135
|
+
assert_respond_to(DBI, :convert_types=)
|
136
|
+
end
|
137
|
+
|
138
|
+
def test_connect
|
139
|
+
assert_respond_to(DBI, :connect)
|
140
|
+
end
|
141
|
+
|
142
|
+
def test_available_drivers
|
143
|
+
assert_respond_to(DBI, :available_drivers)
|
144
|
+
assert_equal(
|
145
|
+
[
|
146
|
+
"dbi:Mysql:",
|
147
|
+
"dbi:ODBC:",
|
148
|
+
"dbi:Pg:",
|
149
|
+
"dbi:SQLite3:",
|
150
|
+
"dbi:SQLite:"
|
151
|
+
], DBI.available_drivers.sort)
|
152
|
+
end
|
153
|
+
|
154
|
+
# PRIVATE METHODS
|
155
|
+
def test_parse_url
|
156
|
+
assert_nothing_raised{ DBI.send(:parse_url, "dbi:foo:bar") }
|
157
|
+
assert_equal(["foo","bar"], DBI.send(:parse_url, @url_basic))
|
158
|
+
assert_equal(["foo","bar:host"], DBI.send(:parse_url, @url_inter))
|
159
|
+
assert_equal(["foo","database=db;host=xx;port=99"],
|
160
|
+
DBI.send(:parse_url, @url_advan)
|
161
|
+
)
|
162
|
+
end
|
163
|
+
|
164
|
+
def test_parse_url_expected_errors
|
165
|
+
assert_raises(DBI::InterfaceError){ DBI.send(:parse_url, 'dbi') }
|
166
|
+
assert_raises(DBI::InterfaceError){ DBI.send(:parse_url, 'dbi::foo') }
|
167
|
+
|
168
|
+
# XXX we're looking for a specific exception message here
|
169
|
+
assert_nothing_raised do
|
170
|
+
begin
|
171
|
+
DBI.send(:parse_url, 'dbi:blah')
|
172
|
+
rescue DBI::InterfaceError => e
|
173
|
+
assert true
|
174
|
+
assert_kind_of DBI::InterfaceError, e
|
175
|
+
assert_equal "Invalid Data Source Name", e.message
|
176
|
+
end
|
177
|
+
end
|
178
|
+
end
|
179
|
+
|
180
|
+
def teardown
|
181
|
+
@db_error = nil
|
182
|
+
@db_binary = nil
|
183
|
+
end
|
184
|
+
end
|
data/test/dbi/tc_row.rb
ADDED
@@ -0,0 +1,256 @@
|
|
1
|
+
######################################################################
|
2
|
+
# tc_row.rb
|
3
|
+
#
|
4
|
+
# Test case for the DBI::Row class.
|
5
|
+
######################################################################
|
6
|
+
$LOAD_PATH.unshift(Dir.pwd)
|
7
|
+
$LOAD_PATH.unshift(File.dirname(Dir.pwd))
|
8
|
+
$LOAD_PATH.unshift("../../lib")
|
9
|
+
$LOAD_PATH.unshift("../../lib/dbi")
|
10
|
+
$LOAD_PATH.unshift("lib")
|
11
|
+
|
12
|
+
require 'test/unit'
|
13
|
+
require 'dbi'
|
14
|
+
|
15
|
+
class TC_DBI_Row < Test::Unit::TestCase
|
16
|
+
def setup
|
17
|
+
@data = %w/Daniel Berger 36/
|
18
|
+
@cols = %w/first last age/
|
19
|
+
@coltypes = [DBI::Type::Varchar, DBI::Type::Varchar, DBI::Type::Integer]
|
20
|
+
@row = DBI::Row.new(@cols, @coltypes, @data.clone)
|
21
|
+
@row_noconv = DBI::Row.new(@cols, @coltypes, @data.clone, false)
|
22
|
+
end
|
23
|
+
|
24
|
+
def teardown
|
25
|
+
@data = nil
|
26
|
+
@cols = nil
|
27
|
+
@row = nil
|
28
|
+
end
|
29
|
+
|
30
|
+
def test_row_multiassign # this should only be an issue in 1.8.7 and up, if at all.
|
31
|
+
first, last, age = @row
|
32
|
+
assert_equal("Daniel", first)
|
33
|
+
assert_equal("Berger", last)
|
34
|
+
assert_equal(36, age)
|
35
|
+
end
|
36
|
+
|
37
|
+
def test_row_noconv
|
38
|
+
assert_nothing_raised do
|
39
|
+
assert_equal(
|
40
|
+
[
|
41
|
+
'Daniel',
|
42
|
+
'Berger',
|
43
|
+
36
|
44
|
+
], @row
|
45
|
+
)
|
46
|
+
assert_equal(@data, @row_noconv)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
# Ensure that constructor only allows Integers or Arrays (or nil)
|
51
|
+
def test_row_constructor
|
52
|
+
assert_nothing_raised{ DBI::Row.new(@cols, @coltypes) }
|
53
|
+
assert_nothing_raised{ DBI::Row.new(@cols, @coltypes, 1) }
|
54
|
+
assert_nothing_raised{ DBI::Row.new(@cols, @coltypes, nil) }
|
55
|
+
assert_nothing_raised{ DBI::Row.new(@cols, @coltypes, [1,2,3])}
|
56
|
+
assert_raises(ArgumentError){ DBI::Row.new }
|
57
|
+
assert_raises(ArgumentError){ DBI::Row.new(@cols) }
|
58
|
+
assert_raises(TypeError){ DBI::Row.new(@cols, @coltypes, {}) }
|
59
|
+
end
|
60
|
+
|
61
|
+
# Test added to ensure that Row#at is equivalent to Row#by_index. When the
|
62
|
+
# latter method is (hopefully) removed, this test can be removed as well.
|
63
|
+
def test_at
|
64
|
+
assert_respond_to(@row, :at)
|
65
|
+
assert_equal(@data[0].to_s, @row.at(0).to_s)
|
66
|
+
assert_equal(@data[1].to_s, @row.at(1).to_s)
|
67
|
+
assert_equal(@data[2].to_s, @row.at(2).to_s)
|
68
|
+
assert_equal(@data[99].to_s, @row.at(99).to_s)
|
69
|
+
end
|
70
|
+
|
71
|
+
# Should respond to Array and Enumerable methods
|
72
|
+
def test_row_delegate
|
73
|
+
assert_respond_to(@row, :length)
|
74
|
+
assert_respond_to(@row, :each)
|
75
|
+
assert_respond_to(@row, :grep)
|
76
|
+
end
|
77
|
+
|
78
|
+
def test_row_length
|
79
|
+
assert_equal(3, @row.length)
|
80
|
+
assert_equal(3, DBI::Row.new(@cols, @coltypes).length)
|
81
|
+
end
|
82
|
+
|
83
|
+
def test_row_data_by_index
|
84
|
+
assert_equal(@data[0], @row.by_index(0))
|
85
|
+
assert_equal(@data[1], @row.by_index(1))
|
86
|
+
assert_equal(@data[2], @row.by_index(2).to_s)
|
87
|
+
assert_nil(@row.by_index(3))
|
88
|
+
end
|
89
|
+
|
90
|
+
def test_row_data_by_field
|
91
|
+
assert_equal @data[0], @row.by_field('first')
|
92
|
+
assert_equal @data[1], @row.by_field('last')
|
93
|
+
assert_equal @data[2], @row.by_field('age').to_s
|
94
|
+
assert_equal nil, @row.by_field('unknown')
|
95
|
+
end
|
96
|
+
|
97
|
+
def test_row_set_values
|
98
|
+
assert_respond_to(@row, :set_values)
|
99
|
+
assert_nothing_raised{ @row.set_values(["John", "Doe", 23]) }
|
100
|
+
assert_equal("John", @row.by_index(0))
|
101
|
+
assert_equal("Doe", @row.by_index(1))
|
102
|
+
assert_equal(23, @row.by_index(2))
|
103
|
+
end
|
104
|
+
|
105
|
+
def test_row_to_h
|
106
|
+
assert_respond_to(@row, :to_h)
|
107
|
+
assert_nothing_raised{ @row.to_h }
|
108
|
+
assert_kind_of(Hash, @row.to_h)
|
109
|
+
assert_equal({"first"=>"Daniel", "last"=>"Berger", "age"=>36}, @row.to_h)
|
110
|
+
end
|
111
|
+
|
112
|
+
def test_row_column_names
|
113
|
+
assert_respond_to(@row, :column_names)
|
114
|
+
assert_nothing_raised{ @row.column_names }
|
115
|
+
assert_kind_of(Array, @row.column_names)
|
116
|
+
assert_equal(["first", "last", "age"], @row.column_names)
|
117
|
+
end
|
118
|
+
|
119
|
+
# An alias for column_names
|
120
|
+
def test_row_field_names
|
121
|
+
assert_respond_to(@row, :column_names)
|
122
|
+
assert_nothing_raised{ @row.column_names }
|
123
|
+
assert_kind_of(Array, @row.column_names)
|
124
|
+
assert_equal(["first", "last", "age"], @row.column_names)
|
125
|
+
end
|
126
|
+
|
127
|
+
def test_indexing_numeric
|
128
|
+
assert_equal(@data[0], @row[0])
|
129
|
+
assert_equal(@data[1], @row[1])
|
130
|
+
assert_equal(@data[2], @row[2].to_s)
|
131
|
+
end
|
132
|
+
|
133
|
+
def test_indexing_string_or_symbol
|
134
|
+
assert_equal(@data[0], @row['first'])
|
135
|
+
assert_equal(@data[0], @row[:first])
|
136
|
+
assert_equal(@data[1], @row['last'])
|
137
|
+
assert_equal(@data[2], @row['age'].to_s)
|
138
|
+
assert_equal(nil, @row['unknown'])
|
139
|
+
end
|
140
|
+
|
141
|
+
def test_indexing_regexp
|
142
|
+
assert_equal(["Daniel"], @row[/first/])
|
143
|
+
assert_equal(["Berger"], @row[/last/])
|
144
|
+
assert_equal([36], @row[/age/])
|
145
|
+
assert_equal(["Daniel", "Berger"], @row[/first|last/])
|
146
|
+
assert_equal([], @row[/bogus/])
|
147
|
+
end
|
148
|
+
|
149
|
+
def test_indexing_array
|
150
|
+
assert_equal(["Daniel"], @row[[0]])
|
151
|
+
assert_equal(["Daniel"], @row[["first"]])
|
152
|
+
assert_equal(["Berger"], @row[[1]])
|
153
|
+
assert_equal([36], @row[[2]])
|
154
|
+
assert_equal([nil], @row[[3]])
|
155
|
+
assert_equal(["Daniel", 36], @row[[0,2]])
|
156
|
+
assert_equal(["Daniel", 36], @row[[0,:age]])
|
157
|
+
end
|
158
|
+
|
159
|
+
def test_indexing_range
|
160
|
+
assert_equal(["Daniel","Berger"], @row[0..1])
|
161
|
+
assert_equal(["Berger",36], @row[1..2])
|
162
|
+
assert_equal(["Berger",36], @row[1..99])
|
163
|
+
assert_equal(nil, @row[90..100])
|
164
|
+
end
|
165
|
+
|
166
|
+
# The two argument reference should behave like the second form of Array#[]
|
167
|
+
def test_indexing_two_args
|
168
|
+
assert_equal([], @row[0,0])
|
169
|
+
assert_equal(["Daniel"], @row[0,1])
|
170
|
+
assert_equal(["Daniel", "Berger"], @row[0,2])
|
171
|
+
assert_equal(["Daniel", "Berger", 36], @row[0,3])
|
172
|
+
assert_equal(["Daniel", "Berger", 36], @row[0,99])
|
173
|
+
end
|
174
|
+
|
175
|
+
def test_indexing_multiple_args
|
176
|
+
assert_equal(["Berger", 36, "Daniel"], @row[:last, :age, :first])
|
177
|
+
assert_equal(["Berger", 36, "Daniel"], @row[1, :age, :first])
|
178
|
+
assert_equal(["Berger", 36, "Daniel"], @row[1, 2, :first])
|
179
|
+
assert_equal(["Berger", 36, "Daniel"], @row[1, 2, 0])
|
180
|
+
assert_equal(["Berger", 36, "Daniel", nil], @row[1, 2, 0, 9])
|
181
|
+
assert_equal(["Berger", 36, "Daniel", nil], @row[1, 2, 0, :bogus])
|
182
|
+
end
|
183
|
+
|
184
|
+
def test_indexing_assignment
|
185
|
+
assert_nothing_raised{ @row[0] = "kirk" }
|
186
|
+
assert_equal("kirk", @row[0])
|
187
|
+
|
188
|
+
assert_nothing_raised{ @row[:age] = 29 }
|
189
|
+
assert_equal(29, @row[:age])
|
190
|
+
|
191
|
+
assert_nothing_raised{ @row[1,2] = "francis" }
|
192
|
+
assert_equal("francis", @row[:last])
|
193
|
+
assert_nil(@row[:age])
|
194
|
+
end
|
195
|
+
|
196
|
+
def test_clone_with
|
197
|
+
another_row = @row.clone_with(["Jane", "Smith", 33])
|
198
|
+
assert_kind_of(DBI::Row, another_row)
|
199
|
+
assert_equal "Jane", another_row.by_index(0)
|
200
|
+
assert_equal "Smith", another_row.by_index(1)
|
201
|
+
assert_equal 33, another_row.by_index(2)
|
202
|
+
assert(@row != another_row)
|
203
|
+
end
|
204
|
+
|
205
|
+
def test_iteration
|
206
|
+
expect = @data.clone
|
207
|
+
@row.each { |value|
|
208
|
+
assert_equal(expect.shift, value.to_s)
|
209
|
+
}
|
210
|
+
assert_equal([], expect)
|
211
|
+
@row.collect { |value| "Field=#{value}" }
|
212
|
+
end
|
213
|
+
|
214
|
+
def test_row_each_with_name
|
215
|
+
assert_respond_to(@row, :each_with_name)
|
216
|
+
assert_nothing_raised{ @row.each_with_name{ } }
|
217
|
+
|
218
|
+
@row.each_with_name{ |value, column|
|
219
|
+
assert(@cols.include?(column))
|
220
|
+
assert(@data.include?(value.to_s))
|
221
|
+
}
|
222
|
+
end
|
223
|
+
|
224
|
+
def test_to_a
|
225
|
+
assert_respond_to(@row, :to_a)
|
226
|
+
assert_equal(@data, DBI::Row.new(@cols, @coltypes, @data).to_a.collect { |x| x.to_s })
|
227
|
+
end
|
228
|
+
|
229
|
+
def test_dup_clone
|
230
|
+
dupped = nil
|
231
|
+
cloned = nil
|
232
|
+
|
233
|
+
assert_nothing_raised{ dupped = @row.dup }
|
234
|
+
assert_nothing_raised{ cloned = @row.clone }
|
235
|
+
assert_nothing_raised{ @row.set_values(["Bill", "Jones", 16])}
|
236
|
+
|
237
|
+
assert_equal(@data, dupped.to_a.collect { |x| x.to_s })
|
238
|
+
assert_equal(@data, cloned.to_a.collect { |x| x.to_s })
|
239
|
+
|
240
|
+
assert(dupped.object_id != @row.object_id)
|
241
|
+
assert(cloned.object_id != @row.object_id)
|
242
|
+
end
|
243
|
+
|
244
|
+
def test_dup_ruby18
|
245
|
+
res = []
|
246
|
+
r = DBI::Row.new(["col1","col2"],[nil,nil])
|
247
|
+
|
248
|
+
[["one",1],["two",2],["three",3]].each do |x,y|
|
249
|
+
r["col1"] = x
|
250
|
+
r["col2"] = y
|
251
|
+
res << r.dup
|
252
|
+
end
|
253
|
+
|
254
|
+
assert_equal res, [["one", 1], ["two", 2], ["three", 3]]
|
255
|
+
end
|
256
|
+
end
|
@@ -0,0 +1,168 @@
|
|
1
|
+
$: << 'lib'
|
2
|
+
require 'test/unit'
|
3
|
+
require "dbi/sql"
|
4
|
+
|
5
|
+
# ====================================================================
|
6
|
+
class TestSqlBind < Test::Unit::TestCase
|
7
|
+
|
8
|
+
def bind(quoter, sql, args)
|
9
|
+
ps = DBI::SQL::PreparedStatement.new(quoter, sql)
|
10
|
+
ps.bind(DBI::Utils::ConvParam.conv_param('default', *args))
|
11
|
+
end
|
12
|
+
|
13
|
+
def test_one
|
14
|
+
assert_equal "10", bind(self, "?", [10])
|
15
|
+
assert_equal "'hi'", bind(self, "?", ["hi"])
|
16
|
+
assert_equal "I 'don''t' know", bind(self, "I ? know", ["don't"])
|
17
|
+
end
|
18
|
+
|
19
|
+
def test_many
|
20
|
+
assert_equal "WHERE age=12 AND name='Jim'",
|
21
|
+
bind(self, "WHERE age=? AND name=?", [12, 'Jim'])
|
22
|
+
end
|
23
|
+
|
24
|
+
def test_too_many
|
25
|
+
assert_raises (RuntimeError) {
|
26
|
+
bind(self, "age=?", [10, 11])
|
27
|
+
}
|
28
|
+
end
|
29
|
+
|
30
|
+
def test_too_few
|
31
|
+
assert_raises (RuntimeError) {
|
32
|
+
bind(self, "age in (?, ?, ?)", [10, 11])
|
33
|
+
}
|
34
|
+
end
|
35
|
+
|
36
|
+
def test_embedded_questions
|
37
|
+
assert_equal "10 ? 11", bind(self, "? ?? ?", [10, 11])
|
38
|
+
assert_equal "????", bind(self, "????????", [])
|
39
|
+
end
|
40
|
+
|
41
|
+
def test_questions_in_param
|
42
|
+
assert_equal "WHERE c='connected?'",
|
43
|
+
bind(self, "WHERE c=?", ["connected?"])
|
44
|
+
|
45
|
+
assert_equal "WHERE c='connected?' AND d='???'",
|
46
|
+
bind(self, "WHERE c=? AND d=?", ["connected?", "???"])
|
47
|
+
end
|
48
|
+
|
49
|
+
def test_questions_in_quotes
|
50
|
+
assert_equal "WHERE c='connected?' AND d=10",
|
51
|
+
bind(self, "WHERE c='connected?' AND d=?", [10])
|
52
|
+
end
|
53
|
+
|
54
|
+
def test_comment_dan
|
55
|
+
sql = %{--Dan's query\n--random comment\nselect column1, column2\nfrom table1\nwhere somevalue = ?}
|
56
|
+
res = %{--Dan's query\n--random comment\nselect column1, column2\nfrom table1\nwhere somevalue = 10}
|
57
|
+
assert_equal res, bind(self, sql, [10])
|
58
|
+
end
|
59
|
+
|
60
|
+
def test_minus_bug
|
61
|
+
sql = "SELECT 1 - 3"
|
62
|
+
res = "SELECT 1 - 3"
|
63
|
+
assert_equal res, bind(self, sql, [])
|
64
|
+
end
|
65
|
+
|
66
|
+
def test_minus2
|
67
|
+
sql = "SELECT * from test --Dan's query"
|
68
|
+
assert_equal sql, bind(self, sql, [])
|
69
|
+
end
|
70
|
+
|
71
|
+
def test_slash
|
72
|
+
sql = "SELECT 5 / 4"
|
73
|
+
res = "SELECT 5 / 4"
|
74
|
+
assert_equal res, bind(self, sql, [])
|
75
|
+
end
|
76
|
+
|
77
|
+
def test_much
|
78
|
+
sql = <<ENDSQL
|
79
|
+
SELECT s.id, cwajga_magic_number((cwajga_product(r.rating) ^ (1 / 1)), MAX(lastplay.lastheard), 5) as magic
|
80
|
+
INTO TEMP magic_order
|
81
|
+
FROM song AS s LEFT OUTER JOIN rating AS r ON s.id = r.song LEFT OUTER JOIN last play ON lastplay.song = s.id
|
82
|
+
WHERE r.name ILIKE 'omega697'
|
83
|
+
GROUP BY s.id;
|
84
|
+
|
85
|
+
SELECT SUM(magic) as total INTO TEMP magic_tot FROM magic_order;
|
86
|
+
|
87
|
+
SELECT id, 100.0*magic/total as percent
|
88
|
+
FROM magic_order, magic_tot
|
89
|
+
order by percent;
|
90
|
+
ENDSQL
|
91
|
+
res = sql
|
92
|
+
assert_equal res, bind(self, sql, [])
|
93
|
+
end
|
94
|
+
|
95
|
+
def test_nested_insert
|
96
|
+
sql = "insert into logins (user_id, hostmask) values ((select id from users where username = ?), ?)"
|
97
|
+
res = sql.sub(/\?/, "1")
|
98
|
+
res.sub!(/\?/, "'foo@bar'")
|
99
|
+
assert_equal res, bind(self, sql, [1, "foo@bar"])
|
100
|
+
end
|
101
|
+
|
102
|
+
end
|
103
|
+
|
104
|
+
######################################################################
|
105
|
+
class TestLex < Test::Unit::TestCase
|
106
|
+
|
107
|
+
def tokens(sql)
|
108
|
+
DBI::SQL::PreparedStatement.tokens(sql)
|
109
|
+
end
|
110
|
+
|
111
|
+
def test_non_strings
|
112
|
+
assert_equal ['This is _a t35t'],
|
113
|
+
tokens("This is _a t35t")
|
114
|
+
end
|
115
|
+
|
116
|
+
def test_simple_strings
|
117
|
+
assert_equal ["hi ", "'hello world'"],
|
118
|
+
tokens("hi 'hello world'")
|
119
|
+
assert_equal ["c = ", "''"],
|
120
|
+
tokens("c = ''")
|
121
|
+
end
|
122
|
+
|
123
|
+
def test_strings_with_quotes
|
124
|
+
assert_equal ["hi ", "'''lo world'"],
|
125
|
+
tokens("hi '''lo world'")
|
126
|
+
assert_equal ['a', "''''", 'b'],
|
127
|
+
tokens("a''''b")
|
128
|
+
end
|
129
|
+
|
130
|
+
def test_strings_with_escaped_quotes
|
131
|
+
assert_equal ["hi ", "'don\\'t do that'"],
|
132
|
+
tokens("hi 'don\\'t do that'")
|
133
|
+
assert_equal ['a', "'\\''", 'b'],
|
134
|
+
tokens("a'\\''b")
|
135
|
+
end
|
136
|
+
|
137
|
+
def test_simple_dq_strings
|
138
|
+
assert_equal ["hi ", '"hello world"'],
|
139
|
+
tokens('hi "hello world"')
|
140
|
+
assert_equal ["c = ", '""'],
|
141
|
+
tokens('c = ""')
|
142
|
+
end
|
143
|
+
|
144
|
+
def test_dq_strings_with_quotes
|
145
|
+
assert_equal ["hi ", '"""lo world"'],
|
146
|
+
tokens('hi """lo world"')
|
147
|
+
assert_equal ['a', '""""', 'b'],
|
148
|
+
tokens('a""""b')
|
149
|
+
end
|
150
|
+
|
151
|
+
def test_dq_strings_with_escaped_quotes
|
152
|
+
assert_equal ["hi ", '"don\"t do that"'],
|
153
|
+
tokens('hi "don\"t do that"')
|
154
|
+
assert_equal ['a', '"\""', 'b'],
|
155
|
+
tokens('a"\""b')
|
156
|
+
end
|
157
|
+
|
158
|
+
def test_qmarks
|
159
|
+
assert_equal ["a = ", "?"],
|
160
|
+
tokens("a = ?")
|
161
|
+
assert_equal ["'?'", " = ", "?"],
|
162
|
+
tokens("'?' = ?")
|
163
|
+
assert_equal ["'?'", " = ", "??"],
|
164
|
+
tokens("'?' = ??")
|
165
|
+
end
|
166
|
+
|
167
|
+
end
|
168
|
+
|
@@ -0,0 +1,29 @@
|
|
1
|
+
$: << 'lib'
|
2
|
+
require 'test/unit'
|
3
|
+
require 'dbi'
|
4
|
+
|
5
|
+
class TC_DBI_StatementHandle < Test::Unit::TestCase
|
6
|
+
def test_fetch
|
7
|
+
mock_handle = 'any_object'
|
8
|
+
def mock_handle.cancel; end
|
9
|
+
def mock_handle.column_info; {}; end
|
10
|
+
def mock_handle.fetch; nil; end
|
11
|
+
sth = DBI::StatementHandle.new( mock_handle, true, true, false, true)
|
12
|
+
|
13
|
+
10.times do
|
14
|
+
assert_nil sth.fetch
|
15
|
+
end
|
16
|
+
|
17
|
+
sth.raise_error = true
|
18
|
+
|
19
|
+
assert_raises(DBI::InterfaceError) do
|
20
|
+
sth.fetch
|
21
|
+
end
|
22
|
+
|
23
|
+
sth.raise_error = false
|
24
|
+
|
25
|
+
10.times do
|
26
|
+
assert_nil sth.fetch
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|