orientdb_client 0.0.2 → 0.0.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/.travis.yml +8 -1
- data/CHANGELOG.md +19 -0
- data/Gemfile +2 -0
- data/Gemfiles/Gemfile.as3.2 +9 -0
- data/Gemfiles/Gemfile.as4.0 +9 -0
- data/README.md +27 -8
- data/lib/orientdb_client/instrumentation/log_subscriber.rb +22 -0
- data/lib/orientdb_client/instrumenters/memory.rb +26 -0
- data/lib/orientdb_client/instrumenters/noop.rb +9 -0
- data/lib/orientdb_client/version.rb +1 -1
- data/lib/orientdb_client.rb +29 -14
- data/orientdb_client.gemspec +0 -1
- data/spec/integration/orientdb_client/instrumentation/log_subscriber_spec.rb +56 -0
- data/spec/orientdb_client_spec.rb +60 -10
- metadata +10 -17
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 34b02fe8fb6024627b8f8b7da8b29740018eef44
|
4
|
+
data.tar.gz: 293559a446780800aa63e846cad714eef7e24d31
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 8b2d8dcbdd22d90bd872b182694d410bba586205cb99216f0e89d50cdcd7925d6e963986b1f9d904fd023c894784c941b70ed3080faf2acadd3b759a801e21f1
|
7
|
+
data.tar.gz: 88e1a49b4dd43aef5caee889180f3cd8f1ab6ceec199ea47dfdac42e3fee82c887dbe7ba4ff5457316b011bc176cf5e2cc5f2c624266b950f5a8538beffba931
|
data/.gitignore
CHANGED
data/.travis.yml
CHANGED
data/CHANGELOG.md
ADDED
@@ -0,0 +1,19 @@
|
|
1
|
+
# Changelog
|
2
|
+
|
3
|
+
## Master
|
4
|
+
|
5
|
+
## 0.0.3
|
6
|
+
|
7
|
+
* Added `CHANGELOG.md`
|
8
|
+
* Breaking change: Swapped logging to use ActiveSupport::Notifications (#16). You will need to
|
9
|
+
update any code that assigns `MyClient::logger = `. Requests and response processing are
|
10
|
+
both instrumented.
|
11
|
+
|
12
|
+
## 0.0.2
|
13
|
+
|
14
|
+
* Integrated Travic CI (#15).
|
15
|
+
* Add handling more Orientdb errors (#14).
|
16
|
+
|
17
|
+
## 0.0.1
|
18
|
+
|
19
|
+
* Initial release.
|
data/Gemfile
CHANGED
data/README.md
CHANGED
@@ -44,20 +44,39 @@ my_client.query('select * from V')
|
|
44
44
|
# create database
|
45
45
|
my_client.create_database('new_db', 'plocal', 'graph')
|
46
46
|
|
47
|
-
# use a different logger
|
48
|
-
class MyLogger
|
49
|
-
def info(message)
|
50
|
-
puts "my message: #{message}"
|
51
|
-
end
|
52
|
-
end
|
53
|
-
Orientdb::logger = MyLogger.new
|
54
|
-
|
55
47
|
# use a different HttpAdapter
|
56
48
|
require 'orientdb_client'
|
57
49
|
require 'orientdb_client/http_adapters/curb_adapter'
|
58
50
|
client = OrientdbClient.client(adapter: 'CurbAdapter')
|
59
51
|
```
|
60
52
|
|
53
|
+
## Logging/instrumentation
|
54
|
+
|
55
|
+
OrientdbClient does no logging by default, but will use ActiveSupport::Notifications
|
56
|
+
if you `require 'orientdb_client/instrumentation/log_subscriber'`.
|
57
|
+
|
58
|
+
If you are using Rails, this should *just work*.
|
59
|
+
|
60
|
+
If you aren't, you'll need to manually specify the logger, like so:
|
61
|
+
|
62
|
+
|
63
|
+
```ruby
|
64
|
+
# activesupport version 3
|
65
|
+
OrientdbClient::Instrumentation::LogSubscriber.logger = Logger.new(STDOUT)
|
66
|
+
|
67
|
+
# activesupport version 4
|
68
|
+
ActiveSupport::LogSubscriber.logger = Logger.new(STDOUT)
|
69
|
+
```
|
70
|
+
|
71
|
+
The right-hand side of the assignment here can be an instance of whatever
|
72
|
+
logger class you want.
|
73
|
+
|
74
|
+
The following events are instrumented:
|
75
|
+
|
76
|
+
* `request.orientdb_client`: most of this is corresponds to time spent in HTTP
|
77
|
+
* `process_response.orientdb_client`: most of this will correspond to JSON parsing
|
78
|
+
and error response code/message handling.
|
79
|
+
|
61
80
|
## HTTP Adapters
|
62
81
|
|
63
82
|
OrientdbClient currently supports Typhoeus and Curb HTTP adapters.
|
@@ -0,0 +1,22 @@
|
|
1
|
+
require 'active_support/notifications'
|
2
|
+
require 'active_support/log_subscriber'
|
3
|
+
|
4
|
+
module OrientdbClient
|
5
|
+
module Instrumentation
|
6
|
+
class LogSubscriber < ::ActiveSupport::LogSubscriber
|
7
|
+
def request(event)
|
8
|
+
return unless logger.debug?
|
9
|
+
|
10
|
+
method = event.payload[:method]
|
11
|
+
response_code = event.payload[:response_code]
|
12
|
+
url = event.payload[:url]
|
13
|
+
request = "#{method} #{url}: #{response_code}"
|
14
|
+
|
15
|
+
name = '%s (%.1fms)' % ["OrientdbClient request", event.duration]
|
16
|
+
debug " #{color(name, YELLOW, true)} [ #{request} ]"
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
OrientdbClient::Instrumentation::LogSubscriber.attach_to :orientdb_client
|
@@ -0,0 +1,26 @@
|
|
1
|
+
module OrientdbClient
|
2
|
+
module Instrumenters
|
3
|
+
# Instrumentor that is useful for tests as it stores each of the events that
|
4
|
+
# are instrumented.
|
5
|
+
class Memory
|
6
|
+
Event = Struct.new(:name, :payload, :result)
|
7
|
+
|
8
|
+
attr_reader :events
|
9
|
+
|
10
|
+
def initialize
|
11
|
+
@events = []
|
12
|
+
end
|
13
|
+
|
14
|
+
def instrument(name, payload = {})
|
15
|
+
result = if block_given?
|
16
|
+
yield payload
|
17
|
+
else
|
18
|
+
nil
|
19
|
+
end
|
20
|
+
|
21
|
+
@events << Event.new(name, payload, result)
|
22
|
+
result
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
data/lib/orientdb_client.rb
CHANGED
@@ -1,13 +1,13 @@
|
|
1
|
+
require 'forwardable'
|
1
2
|
require "orientdb_client/version"
|
2
3
|
require "orientdb_client/errors"
|
3
4
|
require "orientdb_client/http_adapters"
|
4
5
|
require "orientdb_client/http_adapters/typhoeus_adapter"
|
5
6
|
require "orientdb_client/class_configurator"
|
7
|
+
require "orientdb_client/instrumenters/noop"
|
6
8
|
|
7
9
|
require 'oj'
|
8
10
|
require 'cgi'
|
9
|
-
require 'logger'
|
10
|
-
require 'rainbow'
|
11
11
|
|
12
12
|
module OrientdbClient
|
13
13
|
class << self
|
@@ -20,7 +20,8 @@ module OrientdbClient
|
|
20
20
|
|
21
21
|
class Client
|
22
22
|
attr_reader :http_client
|
23
|
-
|
23
|
+
extend Forwardable
|
24
|
+
def_delegators :@instrumenter, :instrument
|
24
25
|
|
25
26
|
def initialize(options)
|
26
27
|
options = {
|
@@ -34,10 +35,10 @@ module OrientdbClient
|
|
34
35
|
else
|
35
36
|
HttpAdapters::TyphoeusAdapter
|
36
37
|
end
|
38
|
+
@instrumenter = options[:instrumenter] || Instrumenters::Noop
|
37
39
|
@http_client = adapter_klass.new
|
38
40
|
@node = Node.new(host: @host, port: @port, http_client: @http_client, client: self)
|
39
41
|
@connected = false
|
40
|
-
@logger = Logger.new(STDOUT)
|
41
42
|
self
|
42
43
|
end
|
43
44
|
|
@@ -251,12 +252,17 @@ module OrientdbClient
|
|
251
252
|
|
252
253
|
def request(method, path, options = {})
|
253
254
|
url = build_url(path)
|
254
|
-
|
255
|
-
|
256
|
-
|
257
|
-
|
258
|
-
|
259
|
-
|
255
|
+
request_instrumentation_hash = {method: method, url: url, options: options}
|
256
|
+
raw_response = safe_instrument('request.orientdb_client', request_instrumentation_hash) do |payload|
|
257
|
+
response = @http_client.request(method, url, options)
|
258
|
+
payload[:response_code] = response.response_code
|
259
|
+
response
|
260
|
+
end
|
261
|
+
response_instrumentation_hash = request_instrumentation_hash.merge(response_code: raw_response.response_code)
|
262
|
+
processed_response = safe_instrument('process_response.orientdb_client', response_instrumentation_hash) do |payload|
|
263
|
+
handle_response(raw_response)
|
264
|
+
end
|
265
|
+
processed_response
|
260
266
|
end
|
261
267
|
|
262
268
|
def build_url(path)
|
@@ -381,10 +387,19 @@ module OrientdbClient
|
|
381
387
|
end
|
382
388
|
end
|
383
389
|
|
384
|
-
|
385
|
-
|
386
|
-
|
390
|
+
# Ensures instrumentation will complete even if exception is raised.
|
391
|
+
def safe_instrument(event_name, args)
|
392
|
+
err = nil
|
393
|
+
result = @client.instrument(event_name, args) do |payload|
|
394
|
+
begin
|
395
|
+
yield payload
|
396
|
+
rescue => e
|
397
|
+
payload[:error] = e.class.to_s
|
398
|
+
err = e
|
399
|
+
end
|
400
|
+
end
|
401
|
+
raise err if err
|
402
|
+
result
|
387
403
|
end
|
388
|
-
|
389
404
|
end
|
390
405
|
end
|
data/orientdb_client.gemspec
CHANGED
@@ -0,0 +1,56 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
require 'logger'
|
3
|
+
require 'stringio'
|
4
|
+
require 'orientdb_client/instrumentation/log_subscriber'
|
5
|
+
|
6
|
+
# Only required for testing purposes, no difference in public API that impacts
|
7
|
+
# actual libraryr code. Rails 4 changes `.logger=` from a `class_attribute` to a
|
8
|
+
# `attr_writer` which affects inheritabiltiy.
|
9
|
+
begin
|
10
|
+
require 'active_support/gem_version'
|
11
|
+
version = ActiveSupport::VERSION::MAJOR
|
12
|
+
rescue LoadError
|
13
|
+
version = 3
|
14
|
+
end
|
15
|
+
|
16
|
+
RSpec.describe OrientdbClient::Instrumentation::LogSubscriber do
|
17
|
+
let(:client) { OrientdbClient.client instrumenter: ActiveSupport::Notifications }
|
18
|
+
|
19
|
+
before do
|
20
|
+
@io = StringIO.new
|
21
|
+
if version == 3
|
22
|
+
OrientdbClient::Instrumentation::LogSubscriber.logger = Logger.new(@io)
|
23
|
+
else
|
24
|
+
ActiveSupport::LogSubscriber.logger = Logger.new(@io)
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
after do
|
29
|
+
if version == 3
|
30
|
+
OrientdbClient::Instrumentation::LogSubscriber.logger = nil
|
31
|
+
else
|
32
|
+
ActiveSupport::LogSubscriber.logger = nil
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
let(:regex) { Regexp.new('get http://localhost:2480/listDatabases') }
|
37
|
+
|
38
|
+
it "works" do
|
39
|
+
begin
|
40
|
+
client.list_databases
|
41
|
+
rescue
|
42
|
+
end
|
43
|
+
log = @io.string
|
44
|
+
expect(log).to match(regex)
|
45
|
+
end
|
46
|
+
|
47
|
+
it "works through exceptions" do
|
48
|
+
allow_any_instance_of(OrientdbClient::HttpAdapters::TyphoeusAdapter).to receive(:request) { raise 'err' }
|
49
|
+
begin
|
50
|
+
client.list_databases
|
51
|
+
rescue
|
52
|
+
end
|
53
|
+
log = @io.string
|
54
|
+
expect(log).to match(regex)
|
55
|
+
end
|
56
|
+
end
|
@@ -1,11 +1,8 @@
|
|
1
1
|
require 'spec_helper'
|
2
|
+
require 'orientdb_client/instrumenters/memory'
|
2
3
|
|
3
4
|
RSpec.describe OrientdbClient do
|
4
|
-
let(:client)
|
5
|
-
c = OrientdbClient.client
|
6
|
-
c.logger.level = Logger::ERROR
|
7
|
-
c
|
8
|
-
end
|
5
|
+
let(:client) { OrientdbClient.client }
|
9
6
|
let(:username) { OrientdbClient::Test::Username }
|
10
7
|
let(:valid_username) { OrientdbClient::Test::Username }
|
11
8
|
let(:password) { OrientdbClient::Test::Password }
|
@@ -680,16 +677,69 @@ RSpec.describe OrientdbClient do
|
|
680
677
|
end
|
681
678
|
end
|
682
679
|
|
680
|
+
describe 'instrumentation' do
|
681
|
+
let(:memory_instrumenter) { OrientdbClient::Instrumenters::Memory.new }
|
682
|
+
let(:client) { OrientdbClient.client(instrumenter: memory_instrumenter) }
|
683
|
+
|
684
|
+
before do
|
685
|
+
client.connect(username: username, password: password, db: db)
|
686
|
+
end
|
687
|
+
|
688
|
+
it 'instruments requests' do
|
689
|
+
client.list_databases
|
690
|
+
request_events = memory_instrumenter.events.select {|e| e.name == 'request.orientdb_client' }
|
691
|
+
expect(request_events.size).to eq(2)
|
692
|
+
|
693
|
+
connect_request_event = request_events.first
|
694
|
+
expect(connect_request_event.payload[:url]).to match(/connect/)
|
695
|
+
expect(connect_request_event.payload[:response_code]).to eq(204)
|
696
|
+
|
697
|
+
list_event = request_events.last
|
698
|
+
expect(list_event.payload[:url]).to match(/listDatabases/)
|
699
|
+
expect(list_event.payload[:response_code]).to eq(200)
|
700
|
+
end
|
701
|
+
|
702
|
+
it 'works when the request fails' do
|
703
|
+
allow(client.http_client).to receive(:request).and_call_original
|
704
|
+
allow(client.http_client).to receive(:request).with(:get, "http://localhost:2480/class/orientdb_client_rb_test/OUser", anything) { raise 'err' }
|
705
|
+
|
706
|
+
begin
|
707
|
+
client.get_class('OUser')
|
708
|
+
rescue
|
709
|
+
ensure
|
710
|
+
expect(memory_instrumenter.events.last.payload[:error]).to eq('RuntimeError')
|
711
|
+
end
|
712
|
+
end
|
713
|
+
|
714
|
+
it 'instruments response handling' do
|
715
|
+
client.list_databases
|
716
|
+
response_events = memory_instrumenter.events.select {|e| e.name == 'process_response.orientdb_client' }
|
717
|
+
expect(response_events.size).to eq(2)
|
718
|
+
|
719
|
+
connect_response_event = response_events.first
|
720
|
+
expect(connect_response_event.payload[:url]).to match(/connect/)
|
721
|
+
expect(connect_response_event.payload[:response_code]).to eq(204)
|
722
|
+
|
723
|
+
list_response_event = response_events.last
|
724
|
+
expect(list_response_event.payload[:url]).to match(/listDatabases/)
|
725
|
+
expect(list_response_event.payload[:response_code]).to eq(200)
|
726
|
+
end
|
727
|
+
|
728
|
+
it 'works when the response handling fails' do
|
729
|
+
begin
|
730
|
+
client.command('insert into OUser CONTENT ' + Oj.dump({a:1}))
|
731
|
+
rescue
|
732
|
+
ensure
|
733
|
+
expect(memory_instrumenter.events.last.payload[:error]).to eq('OrientdbClient::SerializationException')
|
734
|
+
end
|
735
|
+
end
|
736
|
+
end
|
683
737
|
end
|
684
738
|
|
685
739
|
# These specs will sometimes fail, not too much we can do about that, depends
|
686
740
|
# on timing/threading in ruby and odb
|
687
741
|
describe 'mvcc handling', type: :integration do
|
688
|
-
let(:client)
|
689
|
-
c = OrientdbClient.client
|
690
|
-
c.logger.level = Logger::ERROR
|
691
|
-
c
|
692
|
-
end
|
742
|
+
let(:client) { OrientdbClient.client }
|
693
743
|
before do
|
694
744
|
client.connect(username: username, password: password, db: db)
|
695
745
|
if client.has_class?('Person')
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: orientdb_client
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Luke Rodgers
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-11-
|
11
|
+
date: 2015-11-21 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: typhoeus
|
@@ -38,20 +38,6 @@ dependencies:
|
|
38
38
|
- - "~>"
|
39
39
|
- !ruby/object:Gem::Version
|
40
40
|
version: '2.0'
|
41
|
-
- !ruby/object:Gem::Dependency
|
42
|
-
name: rainbow
|
43
|
-
requirement: !ruby/object:Gem::Requirement
|
44
|
-
requirements:
|
45
|
-
- - ">"
|
46
|
-
- !ruby/object:Gem::Version
|
47
|
-
version: '1.99'
|
48
|
-
type: :runtime
|
49
|
-
prerelease: false
|
50
|
-
version_requirements: !ruby/object:Gem::Requirement
|
51
|
-
requirements:
|
52
|
-
- - ">"
|
53
|
-
- !ruby/object:Gem::Version
|
54
|
-
version: '1.99'
|
55
41
|
- !ruby/object:Gem::Dependency
|
56
42
|
name: rake
|
57
43
|
requirement: !ruby/object:Gem::Requirement
|
@@ -147,7 +133,10 @@ files:
|
|
147
133
|
- ".gitignore"
|
148
134
|
- ".rspec"
|
149
135
|
- ".travis.yml"
|
136
|
+
- CHANGELOG.md
|
150
137
|
- Gemfile
|
138
|
+
- Gemfiles/Gemfile.as3.2
|
139
|
+
- Gemfiles/Gemfile.as4.0
|
151
140
|
- LICENSE.txt
|
152
141
|
- README.md
|
153
142
|
- Rakefile
|
@@ -157,10 +146,14 @@ files:
|
|
157
146
|
- lib/orientdb_client/http_adapters.rb
|
158
147
|
- lib/orientdb_client/http_adapters/curb_adapter.rb
|
159
148
|
- lib/orientdb_client/http_adapters/typhoeus_adapter.rb
|
149
|
+
- lib/orientdb_client/instrumentation/log_subscriber.rb
|
150
|
+
- lib/orientdb_client/instrumenters/memory.rb
|
151
|
+
- lib/orientdb_client/instrumenters/noop.rb
|
160
152
|
- lib/orientdb_client/test.rb
|
161
153
|
- lib/orientdb_client/version.rb
|
162
154
|
- orientdb_client.gemspec
|
163
155
|
- spec/curb_adapter_spec.rb
|
156
|
+
- spec/integration/orientdb_client/instrumentation/log_subscriber_spec.rb
|
164
157
|
- spec/orientdb_client_spec.rb
|
165
158
|
- spec/spec_helper.rb
|
166
159
|
- spec/support/shared_examples_for_http_adapter.rb
|
@@ -191,8 +184,8 @@ specification_version: 4
|
|
191
184
|
summary: Orientdb ruby client
|
192
185
|
test_files:
|
193
186
|
- spec/curb_adapter_spec.rb
|
187
|
+
- spec/integration/orientdb_client/instrumentation/log_subscriber_spec.rb
|
194
188
|
- spec/orientdb_client_spec.rb
|
195
189
|
- spec/spec_helper.rb
|
196
190
|
- spec/support/shared_examples_for_http_adapter.rb
|
197
191
|
- spec/typhoeus_adapter_spec.rb
|
198
|
-
has_rdoc:
|