teradata-ar 0.0.3 → 0.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/active_record/connection_adapters/teradata_adapter.rb +182 -2
- data/lib/teradata/ar/version.rb +1 -1
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 498cdd551375bd432cdf0d6f76c5dbdb3fe8ce1b
|
4
|
+
data.tar.gz: 9f092600d613e3d31c3fc9b935e08cde84488d9e
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 125abcaa7940d177e0c8c8a06d92d0dbdb171df1d67fdd9a4a3a46c7972c4cf439f52d017cb8c018a2891c3a527e0f52f71ee55a07d4979fd3a02b049c79639d
|
7
|
+
data.tar.gz: 43539430c99e2c2270e21a61c2699b10733ac01baaae1b060e3f39cb6a366102a98d5ce46b546e3a9cf84f885c60f7711670827706ade859cf1dbcff9daf2285
|
@@ -1,8 +1,20 @@
|
|
1
1
|
require 'active_record/connection_adapters/abstract_adapter'
|
2
|
+
require 'arel/visitors/bind_visitor'
|
2
3
|
|
3
4
|
#gem 'teradata-cli', :path => '~/projects/teradata-cli'
|
4
5
|
require 'teradata-cli'
|
5
6
|
|
7
|
+
class ActiveRecord::Base
|
8
|
+
def self.table_name_prefix
|
9
|
+
Rails.configuration.database_configuration[Rails.env]['table_name_prefix']
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
class ActiveRecord::Migration
|
14
|
+
def self.check_pending!
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
6
18
|
module ActiveRecord
|
7
19
|
module ConnectionHandling
|
8
20
|
def teradata_connection(config)
|
@@ -20,12 +32,30 @@ module ActiveRecord
|
|
20
32
|
module ConnectionAdapters
|
21
33
|
class TeradataAdapter < AbstractAdapter
|
22
34
|
|
35
|
+
class BindSubstitution < Arel::Visitors::ToSql
|
36
|
+
include Arel::Visitors::BindVisitor
|
37
|
+
|
38
|
+
def visit_Arel_Nodes_Limit o
|
39
|
+
end
|
40
|
+
def visit_Arel_Nodes_Offset o
|
41
|
+
end
|
42
|
+
|
43
|
+
def visit_Arel_Nodes_Top o
|
44
|
+
"TOP #{o.expr}"
|
45
|
+
end
|
46
|
+
|
47
|
+
end
|
48
|
+
|
23
49
|
def initialize(logger, logon_string, config)
|
24
50
|
@logon_string = logon_string
|
25
51
|
@charset = config[:charset]
|
52
|
+
@database = config[:database]
|
53
|
+
@table_name_prefix = config[:table_name_prefix]
|
26
54
|
@config = config
|
27
55
|
connect
|
28
56
|
super @connection, logger
|
57
|
+
@visitor = unprepared_visitor
|
58
|
+
configure_connection
|
29
59
|
end
|
30
60
|
|
31
61
|
def adapter_name
|
@@ -37,10 +67,160 @@ module ActiveRecord
|
|
37
67
|
end
|
38
68
|
private :connect
|
39
69
|
|
70
|
+
def configure_connection
|
71
|
+
execute("DATABASE #{@database}") if @database
|
72
|
+
end
|
73
|
+
private :configure_connection
|
74
|
+
|
75
|
+
# CONNECTION MANAGEMENT ====================================
|
76
|
+
|
77
|
+
def active?
|
78
|
+
@connection.execute_query('SELECT 1')
|
79
|
+
true
|
80
|
+
rescue
|
81
|
+
false
|
82
|
+
end
|
83
|
+
|
84
|
+
def reconnect!
|
85
|
+
super
|
86
|
+
disconnect!
|
87
|
+
connect
|
88
|
+
configure_connection
|
89
|
+
end
|
90
|
+
alias :reset! :reconnect!
|
91
|
+
|
92
|
+
# Disconnects from the database if already connected.
|
93
|
+
# Otherwise, this method does nothing.
|
94
|
+
def disconnect!
|
95
|
+
super
|
96
|
+
unless @connection.nil?
|
97
|
+
@connection.close
|
98
|
+
@connection = nil
|
99
|
+
end
|
100
|
+
end
|
101
|
+
|
102
|
+
# DATABASE STATEMENTS ======================================
|
103
|
+
|
40
104
|
def tables(name = nil)
|
41
|
-
|
42
|
-
[
|
105
|
+
sql = "SELECT TABLENAME FROM DBC.TABLES "
|
106
|
+
clauses = []
|
107
|
+
clauses << "DATABASENAME = '#{@database}'" if @database
|
108
|
+
clauses << "TABLENAME = '#{name}'" if name
|
109
|
+
clauses << "TABLENAME LIKE '#{@table_name_prefix}%'" if @table_name_prefix
|
110
|
+
unless clauses.empty?
|
111
|
+
sql << " WHERE " + clauses.join(' AND ')
|
112
|
+
end
|
113
|
+
rs = execute(sql)
|
114
|
+
rs.entries.collect {|record| record['TableName'].strip}
|
43
115
|
end
|
116
|
+
|
117
|
+
# Executes the SQL statement in the context of this connection.
|
118
|
+
def execute(sql, name = nil)
|
119
|
+
if name == :skip_logging
|
120
|
+
@connection.query(sql)
|
121
|
+
else
|
122
|
+
log(sql, name) { @connection.query(sql) }
|
123
|
+
end
|
124
|
+
end
|
125
|
+
|
126
|
+
# Executes +sql+ statement in the context of this connection using
|
127
|
+
# +binds+ as the bind substitutes. +name+ is logged along with
|
128
|
+
# the executed +sql+ statement.
|
129
|
+
def exec_query(sql, name = 'SQL', binds = [])
|
130
|
+
result = execute(sql, name)
|
131
|
+
if result && result.count > 0
|
132
|
+
ActiveRecord::Result.new(result.entries[0].keys, result.entries.collect{|r|r.collect{|v|v}})
|
133
|
+
else
|
134
|
+
ActiveRecord::Result.new([],[])
|
135
|
+
end
|
136
|
+
end
|
137
|
+
|
138
|
+
# Returns an ActiveRecord::Result instance.
|
139
|
+
def select(sql, name = nil, binds = [])
|
140
|
+
exec_query(sql, name)
|
141
|
+
end
|
142
|
+
|
143
|
+
# Returns an array of arrays containing the field values.
|
144
|
+
# Order is the same as that returned by +columns+.
|
145
|
+
def select_rows(sql, name = nil)
|
146
|
+
result = execute(sql, name)
|
147
|
+
if result && result.count > 0
|
148
|
+
result.entries.collect{|r|r.collect{|v|v}}
|
149
|
+
else
|
150
|
+
[]
|
151
|
+
end
|
152
|
+
end
|
153
|
+
|
154
|
+
def execute_update(sql, name = nil)
|
155
|
+
log(sql, name) { @connection.execute_update(sql) }
|
156
|
+
end
|
157
|
+
|
158
|
+
def begin_db_transaction
|
159
|
+
execute_update "BEGIN TRANSACTION"
|
160
|
+
end
|
161
|
+
|
162
|
+
def commit_db_transaction
|
163
|
+
execute_update "END TRANSACTION"
|
164
|
+
end
|
165
|
+
|
166
|
+
def rollback_db_transaction
|
167
|
+
execute_update "ROLLBACK"
|
168
|
+
end
|
169
|
+
|
170
|
+
# Returns an array of +Column+ objects for the table specified by +table_name+.
|
171
|
+
def columns(table_name)#:nodoc:
|
172
|
+
sql = "SELECT * FROM DBC.COLUMNS WHERE TABLENAME='#{table_name}'"
|
173
|
+
sql << " AND DATABASENAME='#{@database}'" if @database
|
174
|
+
rs = execute(sql)
|
175
|
+
rs.entries.collect do |record|
|
176
|
+
new_column(
|
177
|
+
record['ColumnName'].strip,
|
178
|
+
record['DefaultValue'],
|
179
|
+
build_sql_type(record),
|
180
|
+
record['Nullable'].strip == "Y"
|
181
|
+
)
|
182
|
+
end
|
183
|
+
end
|
184
|
+
|
185
|
+
def primary_key(table_name)
|
186
|
+
columns(table_name).select{|col| col.primary == true}[0].name rescue 'id'
|
187
|
+
end
|
188
|
+
|
189
|
+
# Overridden by the adapters to instantiate their specific Column type.
|
190
|
+
def new_column(field, default, type, null) # :nodoc:
|
191
|
+
Column.new(field, default, type, null)
|
192
|
+
end
|
193
|
+
|
194
|
+
# construct the sql type from the teradata column info
|
195
|
+
def build_sql_type(column)
|
196
|
+
field_type = get_field_type(column['ColumnType'])
|
197
|
+
case field_type
|
198
|
+
when "varchar"
|
199
|
+
"#{field_type}(#{column['ColumnLength']})"
|
200
|
+
when "decimal"
|
201
|
+
"#{field_type}(#{column['DecimalTotalDigits']},#{column['DecimalFractionalDigits']})"
|
202
|
+
else
|
203
|
+
field_type
|
204
|
+
end
|
205
|
+
end
|
206
|
+
|
207
|
+
def get_field_type(type)
|
208
|
+
case type.strip
|
209
|
+
when "I", "I1"
|
210
|
+
"int"
|
211
|
+
when "CV"
|
212
|
+
"varchar"
|
213
|
+
when "DA"
|
214
|
+
"date"
|
215
|
+
when "D"
|
216
|
+
"decimal"
|
217
|
+
when "TS"
|
218
|
+
"datetime"
|
219
|
+
else
|
220
|
+
raise "Column type #{type} not supported"
|
221
|
+
end
|
222
|
+
end
|
223
|
+
|
44
224
|
end
|
45
225
|
end
|
46
226
|
end
|
data/lib/teradata/ar/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: teradata-ar
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Giuseppe Privitera
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2013-10-
|
11
|
+
date: 2013-10-16 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|