midori-contrib 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: 393f08c7ad62a5acac4c3ff58767946de3440d2f
4
+ data.tar.gz: 4bb1e8b95c10350a57d42761f2818353920be756
5
+ SHA512:
6
+ metadata.gz: 3709e3e7f72a1794af4822273402728780cd3a83cf6eff11a9b3159338ff665c6c07c385cd3661cd1a96ea15cadfcdb5f6b95200ad21c3fcdaf11fd9a30947b0
7
+ data.tar.gz: c11f2937a9deb52f787e25bdad8c6a1e209364e1df19f9e21d200fc26ba0d5f83ccf875f78249ccebcf51504c14469c95649c988b057086611cc5db52f366e48
data/.editorconfig ADDED
@@ -0,0 +1,9 @@
1
+ root = true
2
+
3
+ [*]
4
+ end_of_line = lf
5
+ insert_final_newline = true
6
+
7
+ [*.rb]
8
+ indent_style = space
9
+ indent_size = 2
data/Gemfile.lock ADDED
@@ -0,0 +1,77 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ midori-contrib (0.0.1)
5
+ em-midori (~> 0.3)
6
+
7
+ GEM
8
+ remote: https://rubygems.org/
9
+ specs:
10
+ codeclimate-test-reporter (1.0.7)
11
+ simplecov
12
+ diff-lcs (1.3)
13
+ docile (1.1.5)
14
+ em-midori (0.3.0)
15
+ midori_http_parser (~> 0.6.1)
16
+ mustermann (~> 1.0)
17
+ nio4r (~> 2.0)
18
+ hiredis (0.6.1)
19
+ json (2.1.0)
20
+ kramdown (1.13.2)
21
+ midori_http_parser (0.6.1.3)
22
+ mustermann (1.0.0)
23
+ mysql2 (0.4.6)
24
+ nest (3.1.1)
25
+ redic
26
+ nio4r (2.1.0)
27
+ ohm (3.1.1)
28
+ nest (~> 3)
29
+ redic (~> 1.5.0)
30
+ stal
31
+ pg (0.21.0)
32
+ rake (12.0.0)
33
+ redic (1.5.0)
34
+ hiredis
35
+ rspec (3.6.0)
36
+ rspec-core (~> 3.6.0)
37
+ rspec-expectations (~> 3.6.0)
38
+ rspec-mocks (~> 3.6.0)
39
+ rspec-core (3.6.0)
40
+ rspec-support (~> 3.6.0)
41
+ rspec-expectations (3.6.0)
42
+ diff-lcs (>= 1.2.0, < 2.0)
43
+ rspec-support (~> 3.6.0)
44
+ rspec-mocks (3.6.0)
45
+ diff-lcs (>= 1.2.0, < 2.0)
46
+ rspec-support (~> 3.6.0)
47
+ rspec-support (3.6.0)
48
+ sequel (4.47.0)
49
+ simplecov (0.14.1)
50
+ docile (~> 1.1.0)
51
+ json (>= 1.8, < 3)
52
+ simplecov-html (~> 0.10.0)
53
+ simplecov-html (0.10.1)
54
+ stal (0.3.0)
55
+ redic (~> 1.5)
56
+ yard (0.9.9)
57
+
58
+ PLATFORMS
59
+ ruby
60
+
61
+ DEPENDENCIES
62
+ bundler (~> 1.0)
63
+ codeclimate-test-reporter (~> 1.0)
64
+ hiredis (~> 0.6.0)
65
+ kramdown (~> 1.13)
66
+ midori-contrib!
67
+ mysql2 (~> 0.4)
68
+ ohm (~> 3.0)
69
+ pg (~> 0.17)
70
+ rake (~> 12.0)
71
+ rspec (~> 3.0)
72
+ sequel (~> 4.40)
73
+ simplecov (~> 0.14)
74
+ yard (~> 0.9)
75
+
76
+ BUNDLED WITH
77
+ 1.14.6
@@ -0,0 +1,51 @@
1
+ ##
2
+ # Midori Extension of File reading and writing
3
+ class MidoriContrib::File
4
+ # Init File object
5
+ # @param [Array] args same args like File.new
6
+ def initialize(*args)
7
+ @file = File.new(*args)
8
+ end
9
+
10
+ # read file
11
+ # @return [String] string readed
12
+ def read
13
+ await(Promise.new do |resolve|
14
+ data = ''
15
+ EventLoop.register(@file, :r) do
16
+ if @file.eof?
17
+ EventLoop.deregister(@file)
18
+ resolve.call(data)
19
+ else
20
+ data << @file.read_nonblock(16384)
21
+ end
22
+ end
23
+ end)
24
+ end
25
+
26
+ # write file
27
+ # @param [String] data string to be written
28
+ def write(data)
29
+ await(Promise.new do |resolve|
30
+ written = 0
31
+ EventLoop.register(@file, :w) do
32
+ written += @file.write_nonblock(data[written..-1])
33
+ if written == data.size
34
+ EventLoop.deregister(@file)
35
+ resolve.call(written)
36
+ end
37
+ end
38
+ end)
39
+ end
40
+
41
+ # raw file object
42
+ # @return [File] file
43
+ def raw
44
+ @file
45
+ end
46
+
47
+ # Close the file
48
+ def close
49
+ @file.close
50
+ end
51
+ end
@@ -0,0 +1,42 @@
1
+ require 'net/protocol'
2
+
3
+ ##
4
+ # Meta programming Net class for async HTTP and FTP connection
5
+ class Net::BufferedIO
6
+ # Wait till io finishes
7
+ # @param [Symbol] interest
8
+ def wait_io(interest)
9
+ await(Promise.new do |resolve|
10
+ io = @io.to_io
11
+ EventLoop.register(io, interest) do
12
+ EventLoop.deregister(io)
13
+ resolve.call(self)
14
+ end
15
+ end)
16
+ end
17
+
18
+ # Fill until the operation finishes
19
+ def rbuf_fill
20
+ loop do
21
+ case rv = @io.read_nonblock(BUFSIZE, exception: false)
22
+ when String
23
+ return @rbuf << rv
24
+ when :wait_readable
25
+ wait_io(:r)
26
+ # @io.to_io.wait_readable(@read_timeout) or raise Net::ReadTimeout
27
+ # continue looping
28
+ when :wait_writable
29
+ # OpenSSL::Buffering#read_nonblock may fail with IO::WaitWritable.
30
+ # http://www.openssl.org/support/faq.html#PROG10
31
+ # :nocov:
32
+ wait_io(:w)
33
+ # @io.to_io.wait_writable(@read_timeout) or raise Net::ReadTimeout
34
+ # continue looping
35
+ when nil
36
+ # callers do not care about backtrace, so avoid allocating for it
37
+ raise EOFError, 'end of file reached', []
38
+ # :nocov:
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,99 @@
1
+ ##
2
+ # Meta-programming hiredis for redis async extension
3
+ module Hiredis
4
+ require 'hiredis/connection'
5
+ # Overwrite with ruby implementation to hook IO
6
+ require 'hiredis/ruby/connection'
7
+ require 'hiredis/ruby/reader'
8
+ # Redis Connection
9
+ Connection = Ruby::Connection
10
+ # Redis Result Reader
11
+ Reader = Ruby::Reader
12
+
13
+ ##
14
+ # Meta-programming hiredis for redis async extension
15
+ module Ruby
16
+ ##
17
+ # Meta-programming hiredis for redis async extension
18
+ class Connection
19
+ # Do redis query
20
+ # @param [Array] args equal to Hiredis write args
21
+ def query(args)
22
+ await(Promise.new do |resolve|
23
+ read_flag = false
24
+ data = pre_write(args)
25
+ written = 0
26
+ EventLoop.register(@sock, :rw) do |monitor|
27
+ if read_flag && monitor.readable?
28
+ # Reading
29
+ _read(resolve, @sock)
30
+ end
31
+ if !read_flag && monitor.writable?
32
+ # Writing
33
+ written += @sock.write_nonblock(data[written..-1])
34
+ read_flag = true if written == string_size(data)
35
+ end
36
+ end
37
+ end)
38
+ end
39
+
40
+ private
41
+ def pre_write(args)
42
+ command = []
43
+ command << "*#{args.size}"
44
+ args.each do |arg|
45
+ arg = arg.to_s
46
+ command << "$#{string_size arg}"
47
+ command << arg
48
+ end
49
+ data = command.join(COMMAND_DELIMITER) + COMMAND_DELIMITER
50
+ data.force_encoding('binary') if data.respond_to?(:force_encoding)
51
+ data
52
+ end
53
+
54
+ def _read(resolve, sock)
55
+ @reader.feed @sock.read_nonblock(1024)
56
+ reply = @reader.gets
57
+ if reply
58
+ EventLoop.deregister(sock)
59
+ resolve.call(reply)
60
+ end
61
+ end
62
+ end
63
+ end
64
+ end
65
+
66
+ require 'redic'
67
+
68
+ ##
69
+ # Meta-programming Redic for redis async extension
70
+ class Redic
71
+ # Meta-programming Redic for redis async extension
72
+ class Client
73
+ # Connect redis, yield optional
74
+ def connect
75
+ establish_connection unless connected?
76
+ if block_given?
77
+ # Redic default yield
78
+ # :nocov:
79
+ @semaphore.synchronize do
80
+ yield
81
+ end
82
+ # :nocov:
83
+ end
84
+ end
85
+
86
+ # Call without thread lock
87
+ # @param [Array] args same params as Redic
88
+ def call(*args)
89
+ @connection.query(*args)
90
+ end
91
+ end
92
+
93
+ # Call without thread lock
94
+ # @param [Array] args same params as Redic
95
+ def call(*args)
96
+ @client.connect
97
+ @client.call(args)
98
+ end
99
+ end
@@ -0,0 +1,111 @@
1
+ require 'sequel'
2
+ require 'sequel/adapters/mysql2'
3
+
4
+ # Management of MySQL Sockets
5
+ MYSQL_SOCKETS = {}
6
+
7
+ ##
8
+ # Meta-programming Sequel for async extensions
9
+ module Sequel
10
+ # Midori Extension of sequel MySQL through meta programming
11
+ module Mysql2
12
+ # Midori Extension of sequel MySQL through meta programming
13
+ class Database
14
+ # Execute the given SQL on the given connection. If the :type
15
+ # option is :select, yield the result of the query, otherwise
16
+ # yield the connection if a block is given.
17
+ # @param [Mysql2::Client] conn connection to database
18
+ # @param [String] sql sql query
19
+ # @param [Hash] opts optional options
20
+ # @return [Mysql2::Result] MySQL results
21
+ def _execute(conn, sql, opts) # rubocop:disable Metrics/MethodLength, Metrics/CyclomaticComplexity
22
+ begin
23
+ # :nocov:
24
+ stream = opts[:stream]
25
+ if NativePreparedStatements
26
+ if (args = opts[:arguments])
27
+ args = args.map{|arg| bound_variable_value(arg)}
28
+ end
29
+
30
+ case sql
31
+ when ::Mysql2::Statement
32
+ stmt = sql
33
+ when Dataset
34
+ sql = sql.sql
35
+ close_stmt = true
36
+ stmt = conn.prepare(sql)
37
+ end
38
+ end
39
+
40
+ r = log_connection_yield((log_sql = opts[:log_sql]) ? sql + log_sql : sql, conn, args) do
41
+ if stmt
42
+ conn.query_options.merge!(cache_rows: true,
43
+ database_timezone: timezone,
44
+ application_timezone: Sequel.application_timezone,
45
+ stream: stream,
46
+ cast_booleans: convert_tinyint_to_bool)
47
+ stmt.execute(*args)
48
+ # :nocov:
49
+ else
50
+ if MYSQL_SOCKETS[conn.socket].nil?
51
+ MYSQL_SOCKETS[conn.socket] = IO::open(conn.socket)
52
+ end
53
+ socket = MYSQL_SOCKETS[conn.socket]
54
+ await(Promise.new do |resolve|
55
+ count = 0
56
+ EventLoop.register(socket, :rw) do
57
+ if (count == 0)
58
+ # Writable
59
+ count += 1
60
+ conn.query(sql,
61
+ database_timezone: timezone,
62
+ application_timezone: Sequel.application_timezone,
63
+ stream: stream,
64
+ async: true)
65
+ else
66
+ # Readable
67
+ begin
68
+ EventLoop.deregister(socket)
69
+ resolve.call(conn.async_result)
70
+ rescue ::Mysql2::Error => e
71
+ resolve.call(PromiseException.new(e))
72
+ next
73
+ end
74
+ end
75
+ end
76
+ end)
77
+ end
78
+ end
79
+
80
+ # :nocov:
81
+ if opts[:type] == :select
82
+ if r
83
+ if stream
84
+ begin
85
+ r2 = yield r
86
+ ensure
87
+ # If r2 is nil, it means the block did not exit normally,
88
+ # so the rest of the results must be drained to prevent
89
+ # "commands out of sync" errors.
90
+ r.each{} unless r2
91
+ end
92
+ else
93
+ yield r
94
+ end
95
+ end
96
+ elsif block_given?
97
+ yield conn
98
+ end
99
+ rescue ::Mysql2::Error => e
100
+ raise_error(e)
101
+ ensure
102
+ if stmt
103
+ conn.query_options.replace(conn.instance_variable_get(:@sequel_default_query_options))
104
+ stmt.close if close_stmt
105
+ end
106
+ # :nocov:
107
+ end
108
+ end
109
+ end
110
+ end
111
+ end
@@ -0,0 +1,45 @@
1
+ require 'sequel'
2
+ require 'sequel/adapters/postgres'
3
+
4
+ # Management of Postgres Sockets
5
+ POSTGRES_SOCKETS = {}
6
+
7
+ ##
8
+ # Midori Extension of sequel postgres through meta programming
9
+ class Sequel::Postgres::Adapter
10
+ # Call a sql request asynchronously
11
+ # @param [String] sql sql request
12
+ # @param [Array] args args to send
13
+ # @return [Array] sql query result
14
+ def execute_query(sql, args)
15
+ @db.log_connection_yield(sql, self, args) do
16
+ if POSTGRES_SOCKETS[self].nil?
17
+ POSTGRES_SOCKETS[self] = IO::open(socket)
18
+ end
19
+ socket_object = POSTGRES_SOCKETS[self]
20
+ await(Promise.new do |resolve|
21
+ count = 0
22
+ EventLoop.register(socket_object, :rw) do
23
+ begin
24
+ if (count == 0)
25
+ # Writable
26
+ unless is_busy
27
+ send_query(sql)
28
+ count += 1
29
+ end
30
+ else
31
+ # Readable
32
+ EventLoop.deregister(socket_object)
33
+ resolve.call(get_result)
34
+ end
35
+ # For extra errors
36
+ # :nocov:
37
+ rescue => e
38
+ resolve.call(PromiseException.new(e))
39
+ # :nocov:
40
+ end
41
+ end
42
+ end)
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,5 @@
1
+ # Midori Contrib Module
2
+ module MidoriContrib
3
+ # Current Version Code
4
+ VERSION = '0.0.1'.freeze
5
+ end
@@ -0,0 +1,19 @@
1
+ require './lib/midori-contrib'
2
+
3
+ Gem::Specification.new do |s|
4
+ s.name = 'midori-contrib'
5
+ s.version = MidoriContrib::VERSION
6
+ s.required_ruby_version = '>=2.2.6'
7
+ s.date = Time.now.strftime('%Y-%m-%d')
8
+ s.summary = 'Various extensions for midori'
9
+ s.description = 'Various extensions officially supported for midori'
10
+ s.authors = ['HeckPsi Lab']
11
+ s.email = 'business@heckpsi.com'
12
+ s.require_paths = ['lib']
13
+ s.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(spec|.resources)/}) } \
14
+ - %w(README.md CONTRIBUTOR_COVENANT_CODE_OF_CONDUCT.md Gemfile Rakefile em-midori.gemspec .gitignore .rspec .codeclimate.yml .rubocop.yml .travis.yml logo.png Rakefile Gemfile)
15
+ s.homepage = 'https://github.com/heckpsi-lab/midori-contrib'
16
+ s.metadata = { 'issue_tracker' => 'https://github.com/heckpsi-lab/midori-contrib/issues' }
17
+ s.license = 'MIT'
18
+ s.add_runtime_dependency 'em-midori', '~> 0.3'
19
+ end
metadata ADDED
@@ -0,0 +1,67 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: midori-contrib
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - HeckPsi Lab
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2017-06-15 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: em-midori
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '0.3'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '0.3'
27
+ description: Various extensions officially supported for midori
28
+ email: business@heckpsi.com
29
+ executables: []
30
+ extensions: []
31
+ extra_rdoc_files: []
32
+ files:
33
+ - ".editorconfig"
34
+ - Gemfile.lock
35
+ - lib/midori-contrib.rb
36
+ - lib/midori-contrib/file.rb
37
+ - lib/midori-contrib/net.rb
38
+ - lib/midori-contrib/redic.rb
39
+ - lib/midori-contrib/sequel/mysql2.rb
40
+ - lib/midori-contrib/sequel/postgres.rb
41
+ - midori-contrib.gemspec
42
+ homepage: https://github.com/heckpsi-lab/midori-contrib
43
+ licenses:
44
+ - MIT
45
+ metadata:
46
+ issue_tracker: https://github.com/heckpsi-lab/midori-contrib/issues
47
+ post_install_message:
48
+ rdoc_options: []
49
+ require_paths:
50
+ - lib
51
+ required_ruby_version: !ruby/object:Gem::Requirement
52
+ requirements:
53
+ - - ">="
54
+ - !ruby/object:Gem::Version
55
+ version: 2.2.6
56
+ required_rubygems_version: !ruby/object:Gem::Requirement
57
+ requirements:
58
+ - - ">="
59
+ - !ruby/object:Gem::Version
60
+ version: '0'
61
+ requirements: []
62
+ rubyforge_project:
63
+ rubygems_version: 2.6.10
64
+ signing_key:
65
+ specification_version: 4
66
+ summary: Various extensions for midori
67
+ test_files: []