jvertica 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 2e6da18153fa70023014d8a66ec2980b8daa7b00
4
+ data.tar.gz: b8491ddb36584fe748447c52c9cf4aabcde572af
5
+ SHA512:
6
+ metadata.gz: f26634201be35948073aa79471cf0e74a12fc000877133627256980a1d09e3f2d5a9a4f39e72ae4424b49712853bd51431c4ec9e6d430b8a68e61b8386b2a9f4
7
+ data.tar.gz: 4f28345e2eb54e0a2b11bfc091cdf19ebdcf507d107cf5858e6793897a5e4e3e1238b625eb4f16497ea817e799a11ca5d09d7fcb9c709fbe2c80d941115efca9
data/.gitignore ADDED
@@ -0,0 +1,15 @@
1
+ /.yardoc
2
+ /Gemfile.lock
3
+ /_yardoc/
4
+ /coverage/
5
+ /doc/
6
+ /pkg/
7
+ /spec/reports/
8
+ /tmp/
9
+ *.bundle
10
+ *.so
11
+ *.o
12
+ *.a
13
+ mkmf.log
14
+ example
15
+ vendor
data/.rspec ADDED
@@ -0,0 +1,2 @@
1
+ --format documentation
2
+ --color
data/.ruby-version ADDED
@@ -0,0 +1 @@
1
+ jruby-1.7.16
data/.travis.yml ADDED
@@ -0,0 +1,3 @@
1
+ language: ruby
2
+ rvm:
3
+ - 2.1.4
data/Gemfile ADDED
@@ -0,0 +1,6 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in jdbc-vertica-more.gemspec
4
+ gemspec
5
+
6
+ gem 'sequel'
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2014 takahiro.nakayama
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,64 @@
1
+ # Jvertica
2
+
3
+ jvertica presents wrapper methods of jdbc-vertica java native methods.
4
+
5
+ ## Installation
6
+
7
+ Add this line to your application's Gemfile:
8
+
9
+ ```ruby
10
+ gem 'jvertica'
11
+ ```
12
+
13
+ And then execute:
14
+
15
+ $ bundle
16
+
17
+ Or install it yourself as:
18
+
19
+ $ gem install jvertica
20
+
21
+ ## Usage
22
+
23
+ ```ruby
24
+ require 'jvertica'
25
+
26
+ conn_opts = {
27
+ host: 'vertica.com',
28
+ port: 5433,
29
+ user: 'xxxxxx',
30
+ password: 'xxxxxx',
31
+ }
32
+
33
+ sql = 'select * from sandbox.jdbc_tests;'
34
+
35
+ c = Jvertica.connect conn_opts
36
+ c.query sql do |row|
37
+ p row
38
+ end
39
+ ```
40
+
41
+ ## Connection Options
42
+
43
+ see [the url](http://my.vertica.com/docs/7.1.x/HTML/index.htm#Authoring/ProgrammersGuide/ClientJDBC/JDBCConnectionProperties.htm)
44
+
45
+
46
+ ## Loading data into Vertica using COPY
47
+
48
+ ```ruby
49
+ connection.copy("COPY table FROM STDIN ...") do |stdin|
50
+ File.open('data.tsv', 'r') do |f|
51
+ begin
52
+ stdin << f.gets
53
+ end until f.eof?
54
+ end
55
+ end
56
+ ```
57
+
58
+ ## Contributing
59
+
60
+ 1. Fork it ( https://github.com/[my-github-username]/jvertica/fork )
61
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
62
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
63
+ 4. Push to the branch (`git push origin my-new-feature`)
64
+ 5. Create a new Pull Request
data/Rakefile ADDED
@@ -0,0 +1,7 @@
1
+ require "bundler/gem_tasks"
2
+ require "rspec/core/rake_task"
3
+
4
+ RSpec::Core::RakeTask.new(:spec)
5
+
6
+ task :default => :spec
7
+
data/jvertica.gemspec ADDED
@@ -0,0 +1,26 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'jvertica/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "jvertica"
8
+ spec.version = Jvertica::VERSION
9
+ spec.authors = ["takahiro.nakayama"]
10
+ spec.email = ["civitaspo@gmail.com"]
11
+ spec.summary = %q{jvertica}
12
+ spec.description = %q{jvertica presents wrapper methods of jdbc-vertica java native methods.}
13
+ spec.homepage = "https://github.com/civitaspo/jvertica"
14
+ spec.license = "MIT"
15
+
16
+ spec.files = `git ls-files -z`.split("\x0")
17
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
18
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
19
+ spec.require_paths = ["lib"]
20
+
21
+ spec.add_development_dependency "bundler", "~> 1.7"
22
+ spec.add_development_dependency "rake", "~> 10.0"
23
+ spec.add_development_dependency "rspec"
24
+
25
+ spec.add_dependency "jdbc-vertica"
26
+ end
@@ -0,0 +1,3 @@
1
+ class Jvertica
2
+ VERSION = "0.0.1"
3
+ end
data/lib/jvertica.rb ADDED
@@ -0,0 +1,390 @@
1
+ require 'java'
2
+ require 'jvertica/version'
3
+ require 'jdbc-vertica'
4
+ require Jdbc::Vertica.driver_jar
5
+
6
+ class Jvertica
7
+ unless %r{java} === RUBY_PLATFORM
8
+ warn "only for use with JRuby"
9
+ end
10
+
11
+ @@default_option_value = {
12
+ host: 'localhost',
13
+ port: 5433,
14
+ database: 'vdb',
15
+ password: '',
16
+ user: 'dbadmin',
17
+ AutoCommit: false,
18
+ }
19
+
20
+ def self.connect options = {}
21
+ new options
22
+ end
23
+
24
+ attr_reader :host, :port, :database
25
+
26
+ def initialize options
27
+ options = @@default_option_value.merge(options).to_sym
28
+ @host = options[:host]
29
+ @port = options[:port]
30
+ @database = options[:database]
31
+ %w(:host :port :database).map do |key|
32
+ options.delete key
33
+ end
34
+
35
+ prop = Properties.new
36
+ options.each do |key, value|
37
+ prop.put key.to_s, value
38
+ end
39
+
40
+ @connection = begin
41
+ DriverManager.getConnection "jdbc:vertica://#{host}:#{port}/#{database}", prop
42
+ rescue => e
43
+ raise ConnectionError.new("Connection Failed.\n" +
44
+ "Error Message => #{e.message}\n" +
45
+ "see documentation => #{@@connection_property_document_url}\n")
46
+ end
47
+ end
48
+
49
+ def close
50
+ @connection.close
51
+ end
52
+
53
+ def commit
54
+ @connection.commit
55
+ end
56
+
57
+ #def prepare query
58
+ # @pstmt = @connection.prepareStatement query
59
+ #end
60
+
61
+ #def prepared?
62
+ # @pstmt.present?
63
+ #end
64
+
65
+ #def execute *args, &blk
66
+ # TODO
67
+ #end
68
+
69
+ def property key, value = nil
70
+ key = key.to_s
71
+ if value.nil?
72
+ @connection.getProperty key
73
+ else
74
+ @connection.setProperty key, value
75
+ end
76
+ end
77
+
78
+ def query query, &blk
79
+ stmt = @connection.createStatement
80
+ case query
81
+ when %r{\A\s*copy}miu then raise InvalidQuery.new('cannot use "copy".')
82
+ when %r{\A\s*insert}miu then return stmt.executeUpdate query
83
+ when %r{\A\s*update}miu then return stmt.executeUpdate query
84
+ when %r{\A\s*delete}miu then return stmt.executeUpdate query
85
+ when %r{\A\s*drop}miu then return stmt.execute query
86
+ when %r{\A\s*create}miu then return stmt.execute query
87
+ else rs = stmt.executeQuery query
88
+ end
89
+
90
+ if block_given?
91
+ ResultSet.new(rs).each do |row|
92
+ yield row
93
+ end
94
+ else
95
+ ResultSet.new rs
96
+ end
97
+ end
98
+
99
+ def copy query, source = nil, &blk
100
+ raise InvalidQuery.new('can use only "copy".') unless %r{\A\s*copy}miu === query
101
+ stream = com.vertica.jdbc.VerticaCopyStream.new @connection, query
102
+ stream.start
103
+ begin
104
+ if !source.nil?
105
+
106
+ if source.is_a? IO
107
+ stream.addStream org.jruby.util.IOInputStream.new(source)
108
+ else
109
+ raise InvalidObject.new("source must be a IO.")
110
+ end
111
+
112
+ elsif block_given?
113
+ rio, wio = IO.pipe
114
+ begin
115
+ yield(wio)
116
+ stream.addStream org.jruby.util.IOInputStream.new(rio)
117
+ rescue => e
118
+ raise e
119
+ ensure
120
+ wio.close
121
+ rio.close
122
+ end
123
+
124
+ end
125
+ rescue => e
126
+ r = stream.finish
127
+ raise e.class.new("[affected rows: #{r}] #{e.message}")
128
+ end
129
+
130
+ begin
131
+ stream.execute
132
+ results = stream.finish
133
+ rescue => e
134
+ raise e
135
+ end
136
+
137
+ results
138
+ end
139
+
140
+ private
141
+ class ConnectionError < StandardError
142
+ end
143
+
144
+ class InvalidQuery < StandardError
145
+ end
146
+
147
+ class InvalidObject < StandardError
148
+ end
149
+
150
+ class InsufficientArgument < StandardError
151
+ end
152
+
153
+ class ResultSet
154
+ include Enumerable
155
+
156
+ def each
157
+ return enum_for(:each) unless block_given?
158
+ return if closed?
159
+
160
+ while @nrow
161
+ idx = 0
162
+ row = Jvertica::Row.new(
163
+ @col_labels,
164
+ @col_labels_d,
165
+ @getters.map{|gt|
166
+ case gt
167
+ when :getBigNum
168
+ v = @rset.getBigDecimal idx+=1
169
+ @rset.was_null ? nil : v.toPlainString.to_i
170
+ when :getBigDecimal
171
+ v = @rset.getBigDecimal idx+=1
172
+ @rset.was_null ? nil : BigDecimal.new(v.toPlainString)
173
+ else
174
+ v = @rset.send gt, idx+=1
175
+ @rset.was_null ? nil : v
176
+ end
177
+ },
178
+ @rownum += 1
179
+ )
180
+ close unless @nrow = @rset.next
181
+ yield row
182
+ end
183
+ close
184
+ end
185
+
186
+ def close
187
+ return if closed?
188
+
189
+ @rset.close
190
+ @close_callback.call if @close_callback
191
+ @closed = true
192
+ end
193
+
194
+ def closed?
195
+ @closed
196
+ end
197
+
198
+ def initialize rset, &close_callback
199
+ unless rset.respond_to? :get_meta_data
200
+ rset.close if rset
201
+ @closed = true
202
+ return
203
+ end
204
+
205
+ @close_callback = close_callback
206
+ @rset = rset
207
+ @rsmd = @rset.get_meta_data
208
+ @num_col = @rsmd.get_column_count
209
+ @getters = []
210
+ @col_labels = []
211
+ @col_labels_d = []
212
+ (1..@num_col).each do |i|
213
+ type = @rsmd.get_column_type i
214
+
215
+ @getters <<
216
+ case type
217
+ when java.sql.Types::NUMERIC, java.sql.Types::DECIMAL
218
+ precision = @rsmd.get_precision i
219
+ scale = @rsmd.get_scale i
220
+
221
+ if precision > 0 and scale >= 0
222
+ if scale > 0 then :getBigDecimal
223
+ else
224
+
225
+ if precision <= 9 then :getInt
226
+ elsif precision <= 18 then :getLong
227
+ else :getBigNum
228
+ end
229
+
230
+ end
231
+ else :getBigDecimal
232
+ end
233
+
234
+ else Jvertica::Constant::GETTER_MAP.fetch type, :get_string
235
+ end
236
+
237
+ label = @rsmd.get_column_label i
238
+ @col_labels << label
239
+ @col_labels_d << label.downcase
240
+ end
241
+
242
+ @rownum = -1
243
+ @nrow = @rset.next
244
+ @closed = false
245
+ end
246
+ end
247
+
248
+ class Row
249
+ attr_reader :labels, :values, :rownum
250
+ alias_method :keys, :labels
251
+
252
+ include Enumerable
253
+
254
+ def [] *idx
255
+ return @values[*idx] if idx.length > 1
256
+
257
+ idx = idx.first
258
+ case idx
259
+ when Fixnum
260
+ raise RangeError.new("Index out of bound") if idx >= @values.length
261
+ @values[idx]
262
+ when String, Symbol
263
+ vidx = @labels_d.index(idx.to_s.downcase) or
264
+ raise NameError.new("Unknown column label: #{idx}")
265
+ @values[vidx]
266
+ else
267
+ @values[idx]
268
+ end
269
+ end
270
+
271
+ def each(&blk)
272
+ @values.each do |v|
273
+ yield v
274
+ end
275
+ end
276
+
277
+ def inspect
278
+ strs = []
279
+ @labels.each do |col|
280
+ strs << "#{col}: #{self[col] || '(null)'}"
281
+ end
282
+ '[' + strs.join(', ') + ']'
283
+ end
284
+
285
+ def to_a
286
+ @values
287
+ end
288
+
289
+ def join sep = $OUTPUT_FIELD_SEPARATOR
290
+ to_a.join sep
291
+ end
292
+
293
+ def eql? other
294
+ self.hash == other.hash
295
+ end
296
+
297
+ def hash
298
+ @labels.zip(@values).sort.hash
299
+ end
300
+
301
+ def to_h
302
+ Hash[@labels.zip @values]
303
+ end
304
+
305
+ alias :== :eql?
306
+
307
+ def initialize col_labels, col_labels_d, values, rownum
308
+ @labels = col_labels
309
+ @labels_d = col_labels_d
310
+ @values = values
311
+ @rownum = rownum
312
+ end
313
+
314
+ def method_missing symb, *args
315
+ if vidx = @labels_d.index(symb.to_s.downcase)
316
+ @values[vidx]
317
+ elsif @values.respond_to? symb
318
+ @values.send symb, *args
319
+ else
320
+ raise NoMethodError.new("undefined method or attribute `#{symb}'")
321
+ end
322
+ end
323
+
324
+ [:id, :tap, :gem, :display, :class, :method, :methods, :trust].select do |s|
325
+ method_defined? s
326
+ end.each do |m|
327
+ undef_method m
328
+ end
329
+ end
330
+
331
+ class DriverManager < java.sql.DriverManager
332
+ end
333
+
334
+ class Properties < java.util.Properties
335
+ end
336
+
337
+ class DataSource < com.vertica.jdbc.DataSource
338
+ end
339
+
340
+ module Constant
341
+ CONNECTION_PROPERTY_DOCUMENT_URL =
342
+ 'http://my.vertica.com/docs/7.1.x/HTML/index.htm#Authoring/ProgrammersGuide/ClientJDBC/JDBCConnectionProperties.htm'
343
+
344
+ RUBY_SQL_TYPE_MAP = {
345
+ Fixnum => java.sql.Types::INTEGER,
346
+ Bignum => java.sql.Types::BIGINT,
347
+ String => java.sql.Types::VARCHAR,
348
+ Float => java.sql.Types::DOUBLE,
349
+ Time => java.sql.Types::TIMESTAMP
350
+ }
351
+ GETTER_MAP = {
352
+ java.sql.Types::TINYINT => :getInt,
353
+ java.sql.Types::SMALLINT => :getInt,
354
+ java.sql.Types::INTEGER => :getInt,
355
+ java.sql.Types::BIGINT => :getLong,
356
+ java.sql.Types::CHAR => :getString,
357
+ java.sql.Types::VARCHAR => :getString,
358
+ java.sql.Types::LONGVARCHAR => :getString,
359
+ (java.sql.Types::NCHAR rescue nil) => :getString,
360
+ (java.sql.Types::NVARCHAR rescue nil) => :getString,
361
+ (java.sql.Types::LONGNVARCHAR rescue nil) => :getString,
362
+ java.sql.Types::BINARY => :getBinaryStream,
363
+ java.sql.Types::VARBINARY => :getBinaryStream,
364
+ java.sql.Types::LONGVARBINARY => :getBinaryStream,
365
+ java.sql.Types::REAL => :getDouble,
366
+ java.sql.Types::FLOAT => :getFloat,
367
+ java.sql.Types::DOUBLE => :getDouble,
368
+ java.sql.Types::DATE => :getDate,
369
+ java.sql.Types::TIME => :getTime,
370
+ java.sql.Types::TIMESTAMP => :getTimestamp,
371
+ java.sql.Types::BLOB => :getBlob,
372
+ java.sql.Types::CLOB => :getString,
373
+ (java.sql.Types::NCLOB rescue nil) => :getString,
374
+ java.sql.Types::BOOLEAN => :getBoolean
375
+ }
376
+ end
377
+ end
378
+
379
+ class Hash
380
+ def to_sym
381
+ self.inject self.class.new do |h, (k, v)|
382
+ h[k.to_sym] = if v.is_a? self.class
383
+ v.to_sym
384
+ else
385
+ v
386
+ end
387
+ h
388
+ end
389
+ end
390
+ end
@@ -0,0 +1,11 @@
1
+ require 'spec_helper'
2
+
3
+ describe Jvertica do
4
+ it 'has a version number' do
5
+ expect(Jvertica::VERSION).not_to be nil
6
+ end
7
+
8
+ it 'does something useful' do
9
+ expect(false).to eq(true)
10
+ end
11
+ end
@@ -0,0 +1,2 @@
1
+ $LOAD_PATH.unshift File.expand_path('../../lib', __FILE__)
2
+ require 'jvertica'
metadata ADDED
@@ -0,0 +1,115 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: jvertica
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - takahiro.nakayama
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-11-19 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ requirement: !ruby/object:Gem::Requirement
15
+ requirements:
16
+ - - ~>
17
+ - !ruby/object:Gem::Version
18
+ version: '1.7'
19
+ name: bundler
20
+ prerelease: false
21
+ type: :development
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ~>
25
+ - !ruby/object:Gem::Version
26
+ version: '1.7'
27
+ - !ruby/object:Gem::Dependency
28
+ requirement: !ruby/object:Gem::Requirement
29
+ requirements:
30
+ - - ~>
31
+ - !ruby/object:Gem::Version
32
+ version: '10.0'
33
+ name: rake
34
+ prerelease: false
35
+ type: :development
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ~>
39
+ - !ruby/object:Gem::Version
40
+ version: '10.0'
41
+ - !ruby/object:Gem::Dependency
42
+ requirement: !ruby/object:Gem::Requirement
43
+ requirements:
44
+ - - '>='
45
+ - !ruby/object:Gem::Version
46
+ version: '0'
47
+ name: rspec
48
+ prerelease: false
49
+ type: :development
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - '>='
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
55
+ - !ruby/object:Gem::Dependency
56
+ requirement: !ruby/object:Gem::Requirement
57
+ requirements:
58
+ - - '>='
59
+ - !ruby/object:Gem::Version
60
+ version: '0'
61
+ name: jdbc-vertica
62
+ prerelease: false
63
+ type: :runtime
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - '>='
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ description: jvertica presents wrapper methods of jdbc-vertica java native methods.
70
+ email:
71
+ - civitaspo@gmail.com
72
+ executables: []
73
+ extensions: []
74
+ extra_rdoc_files: []
75
+ files:
76
+ - .gitignore
77
+ - .rspec
78
+ - .ruby-version
79
+ - .travis.yml
80
+ - Gemfile
81
+ - LICENSE.txt
82
+ - README.md
83
+ - Rakefile
84
+ - jvertica.gemspec
85
+ - lib/jvertica.rb
86
+ - lib/jvertica/version.rb
87
+ - spec/jvertica_spec.rb
88
+ - spec/spec_helper.rb
89
+ homepage: https://github.com/civitaspo/jvertica
90
+ licenses:
91
+ - MIT
92
+ metadata: {}
93
+ post_install_message:
94
+ rdoc_options: []
95
+ require_paths:
96
+ - lib
97
+ required_ruby_version: !ruby/object:Gem::Requirement
98
+ requirements:
99
+ - - '>='
100
+ - !ruby/object:Gem::Version
101
+ version: '0'
102
+ required_rubygems_version: !ruby/object:Gem::Requirement
103
+ requirements:
104
+ - - '>='
105
+ - !ruby/object:Gem::Version
106
+ version: '0'
107
+ requirements: []
108
+ rubyforge_project:
109
+ rubygems_version: 2.1.9
110
+ signing_key:
111
+ specification_version: 4
112
+ summary: jvertica
113
+ test_files:
114
+ - spec/jvertica_spec.rb
115
+ - spec/spec_helper.rb