restify 0.4.0 → 0.5.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +0 -1
- data/lib/restify.rb +3 -16
- data/lib/restify/adapter/typhoeus.rb +14 -4
- data/lib/restify/context.rb +23 -6
- data/lib/restify/global.rb +32 -0
- data/lib/restify/promise.rb +33 -37
- data/lib/restify/registry.rb +26 -0
- data/lib/restify/relation.rb +27 -6
- data/lib/restify/resource.rb +14 -2
- data/lib/restify/version.rb +1 -1
- data/restify.gemspec +2 -2
- data/spec/restify/global_spec.rb +39 -0
- data/spec/restify/registry_spec.rb +52 -0
- data/spec/restify/resource_spec.rb +28 -1
- data/spec/restify_spec.rb +71 -9
- data/spec/spec_helper.rb +5 -0
- metadata +24 -18
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 056a4caf86fd6f8b72c420b0ecc705a74147c5a1
|
4
|
+
data.tar.gz: ce0ea38d4c1bdd4c9e0c08eac752eeb0669a16db
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 6a64dc7d022c4d6abc168886bcc3ef329abfee0279a47230c6457d9f9f41e6c30962ac8af0edd5211d82e5c4fcd8cb4571e0339362a53ae531a2b2eae569eb58
|
7
|
+
data.tar.gz: a551b3a408e99647ba3c0a12b452e7caf9fba94d6d49a94791d080c02ce0e26c6393c25a64b14f69b25e41bc4f37c83d3754c6c0b2429b3cee9c4c2789541b6b
|
data/README.md
CHANGED
data/lib/restify.rb
CHANGED
@@ -9,6 +9,8 @@ require 'addressable/template'
|
|
9
9
|
module Restify
|
10
10
|
require 'restify/error'
|
11
11
|
require 'restify/promise'
|
12
|
+
require 'restify/registry'
|
13
|
+
require 'restify/global'
|
12
14
|
|
13
15
|
require 'restify/context'
|
14
16
|
require 'restify/resource'
|
@@ -25,20 +27,5 @@ module Restify
|
|
25
27
|
|
26
28
|
PROCESSORS = [Processors::Json]
|
27
29
|
|
28
|
-
|
29
|
-
def new(uri, opts = {})
|
30
|
-
Relation.new Context.new(uri, opts), uri
|
31
|
-
end
|
32
|
-
|
33
|
-
def adapter
|
34
|
-
@adapter ||= begin
|
35
|
-
require 'restify/adapter/typhoeus'
|
36
|
-
Restify::Adapter::Typhoeus.new
|
37
|
-
end
|
38
|
-
end
|
39
|
-
|
40
|
-
def adapter=(adapter)
|
41
|
-
@adapter = adapter
|
42
|
-
end
|
43
|
-
end
|
30
|
+
extend Global
|
44
31
|
end
|
@@ -6,9 +6,10 @@ module Restify
|
|
6
6
|
#
|
7
7
|
class Typhoeus
|
8
8
|
|
9
|
-
def initialize
|
10
|
-
@queue
|
11
|
-
@hydra
|
9
|
+
def initialize(**options)
|
10
|
+
@queue = Queue.new
|
11
|
+
@hydra = ::Typhoeus::Hydra.new
|
12
|
+
@options = options
|
12
13
|
|
13
14
|
Thread.new do
|
14
15
|
begin
|
@@ -27,8 +28,17 @@ module Restify
|
|
27
28
|
end
|
28
29
|
end
|
29
30
|
|
31
|
+
def sync?
|
32
|
+
@options.fetch :sync, false
|
33
|
+
end
|
34
|
+
|
30
35
|
def queue(request, writer)
|
31
|
-
|
36
|
+
if sync?
|
37
|
+
@hydra.queue convert request, writer
|
38
|
+
@hydra.run
|
39
|
+
else
|
40
|
+
@queue.push [request, writer]
|
41
|
+
end
|
32
42
|
end
|
33
43
|
|
34
44
|
def call(request)
|
data/lib/restify/context.rb
CHANGED
@@ -12,17 +12,28 @@ module Restify
|
|
12
12
|
#
|
13
13
|
attr_reader :uri
|
14
14
|
|
15
|
-
|
16
|
-
|
17
|
-
|
15
|
+
# Options passed to this context.
|
16
|
+
#
|
17
|
+
# @return [Hash] Options.
|
18
|
+
#
|
19
|
+
attr_reader :options
|
20
|
+
|
21
|
+
def initialize(uri, **kwargs)
|
22
|
+
@uri = uri.is_a?(Addressable::URI) ? uri : Addressable::URI.parse(uri.to_s)
|
23
|
+
@options = kwargs
|
18
24
|
end
|
19
25
|
|
20
26
|
def join(uri)
|
21
27
|
self.uri.join uri
|
22
28
|
end
|
23
29
|
|
30
|
+
def inherit(uri, **kwargs)
|
31
|
+
uri = self.uri unless uri
|
32
|
+
Context.new uri, kwargs.merge(options)
|
33
|
+
end
|
34
|
+
|
24
35
|
def process(response)
|
25
|
-
context =
|
36
|
+
context = inherit response.uri
|
26
37
|
processor = Restify::PROCESSORS.find { |p| p.accept? response }
|
27
38
|
processor ||= Restify::Processors::Base
|
28
39
|
|
@@ -34,9 +45,9 @@ module Restify
|
|
34
45
|
method: method,
|
35
46
|
uri: join(uri),
|
36
47
|
data: data,
|
37
|
-
headers:
|
48
|
+
headers: options.fetch(:headers, {})
|
38
49
|
|
39
|
-
|
50
|
+
adapter.call(request).then do |response|
|
40
51
|
if response.success?
|
41
52
|
process response
|
42
53
|
else
|
@@ -45,6 +56,12 @@ module Restify
|
|
45
56
|
end
|
46
57
|
end
|
47
58
|
|
59
|
+
private
|
60
|
+
|
61
|
+
def adapter
|
62
|
+
options[:adapter] || Restify.adapter
|
63
|
+
end
|
64
|
+
|
48
65
|
class << self
|
49
66
|
def raise_response_error(response)
|
50
67
|
case response.code
|
@@ -0,0 +1,32 @@
|
|
1
|
+
module Restify
|
2
|
+
module Global
|
3
|
+
extend self
|
4
|
+
|
5
|
+
def new(uri, **opts)
|
6
|
+
context = resolve_context uri, **opts
|
7
|
+
|
8
|
+
Relation.new context, context.uri
|
9
|
+
end
|
10
|
+
|
11
|
+
def adapter
|
12
|
+
@adapter ||= begin
|
13
|
+
require 'restify/adapter/em'
|
14
|
+
Restify::Adapter::EM.new
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
def adapter=(adapter)
|
19
|
+
@adapter = adapter
|
20
|
+
end
|
21
|
+
|
22
|
+
private
|
23
|
+
|
24
|
+
def resolve_context(uri, **opts)
|
25
|
+
if uri.is_a? Symbol
|
26
|
+
Restify::Registry.fetch(uri).inherit(nil, opts)
|
27
|
+
else
|
28
|
+
Context.new uri, opts
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
data/lib/restify/promise.rb
CHANGED
@@ -2,70 +2,66 @@ module Restify
|
|
2
2
|
#
|
3
3
|
class Promise < Concurrent::IVar
|
4
4
|
def initialize(*dependencies, &task)
|
5
|
-
@task = task
|
5
|
+
@task = task
|
6
6
|
@dependencies = dependencies.flatten
|
7
7
|
|
8
8
|
super(&nil)
|
9
9
|
end
|
10
10
|
|
11
11
|
def wait(timeout = nil)
|
12
|
-
if
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
12
|
+
execute if pending?
|
13
|
+
|
14
|
+
# if defined?(EventMachine)
|
15
|
+
# if incomplete?
|
16
|
+
# fiber = Fiber.current
|
17
|
+
|
18
|
+
# self.add_observer do
|
19
|
+
# EventMachine.next_tick { fiber.resume }
|
20
|
+
# end
|
21
|
+
|
22
|
+
# Fiber.yield
|
23
|
+
# else
|
24
|
+
# self
|
25
|
+
# end
|
26
|
+
# else
|
27
|
+
super
|
28
|
+
# end
|
17
29
|
end
|
18
30
|
|
19
31
|
def then(&block)
|
20
32
|
Promise.new([self], &block)
|
21
33
|
end
|
22
34
|
|
23
|
-
def execute
|
24
|
-
synchronize { ns_execute }
|
35
|
+
def execute(timeout = nil)
|
36
|
+
synchronize { ns_execute timeout }
|
25
37
|
end
|
26
38
|
|
27
39
|
protected
|
28
40
|
|
29
41
|
# @!visibility private
|
30
|
-
def ns_execute
|
31
|
-
return unless pending?
|
32
|
-
|
33
|
-
executor = Concurrent::SafeTaskExecutor.new \
|
34
|
-
method(:eval_dependencies), rescue_exception: true
|
35
|
-
success, value, reason = executor.execute(@dependencies)
|
36
|
-
|
37
|
-
if success
|
38
|
-
ns_execute_task(*value)
|
39
|
-
else
|
40
|
-
complete false, nil, reason
|
41
|
-
end
|
42
|
-
end
|
43
|
-
|
44
|
-
# @!visibility private
|
45
|
-
def ns_execute_task(*args)
|
42
|
+
def ns_execute(timeout)
|
46
43
|
if compare_and_set_state(:processing, :pending)
|
47
|
-
|
44
|
+
return unless @task || @dependencies.any?
|
45
|
+
|
46
|
+
executor = Concurrent::SafeTaskExecutor.new \
|
47
|
+
method(:ns_exec), rescue_exception: true
|
48
48
|
|
49
|
-
|
50
|
-
success, value, reason = value.wait, value.value, value.reason
|
51
|
-
end
|
49
|
+
success, value, reason = executor.execute
|
52
50
|
|
53
51
|
complete success, value, reason
|
54
52
|
end
|
55
53
|
end
|
56
54
|
|
57
55
|
# @!visibility private
|
58
|
-
def
|
59
|
-
dependencies.map(
|
60
|
-
|
56
|
+
def ns_exec
|
57
|
+
args = @dependencies.any? ? @dependencies.map(&:value!) : []
|
58
|
+
value = @task ? @task.call(*args) : args
|
61
59
|
|
62
|
-
|
63
|
-
|
64
|
-
if dependency.is_a? Concurrent::IVar
|
65
|
-
eval_dependency dependency.value!
|
66
|
-
else
|
67
|
-
dependency
|
60
|
+
while value.is_a? Restify::Promise
|
61
|
+
value = value.value!
|
68
62
|
end
|
63
|
+
|
64
|
+
value
|
69
65
|
end
|
70
66
|
|
71
67
|
class << self
|
@@ -0,0 +1,26 @@
|
|
1
|
+
module Restify
|
2
|
+
class Registry
|
3
|
+
def initialize
|
4
|
+
@registry = {}
|
5
|
+
end
|
6
|
+
|
7
|
+
def store(name, uri, **opts)
|
8
|
+
@registry[name] = Context.new uri, **opts
|
9
|
+
end
|
10
|
+
|
11
|
+
def fetch(name)
|
12
|
+
@registry.fetch name
|
13
|
+
end
|
14
|
+
|
15
|
+
class << self
|
16
|
+
extend Forwardable
|
17
|
+
|
18
|
+
def instance
|
19
|
+
@instance ||= new
|
20
|
+
end
|
21
|
+
|
22
|
+
delegate store: :instance
|
23
|
+
delegate fetch: :instance
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
data/lib/restify/relation.rb
CHANGED
@@ -1,11 +1,28 @@
|
|
1
1
|
module Restify
|
2
2
|
#
|
3
3
|
class Relation
|
4
|
+
|
5
|
+
# Relation context
|
6
|
+
#
|
7
|
+
# @return [Restify::Context] Context
|
8
|
+
#
|
9
|
+
attr_reader :context
|
10
|
+
|
11
|
+
# Relation URI template
|
12
|
+
#
|
13
|
+
# @return [Addressable::Template] URI template
|
14
|
+
#
|
15
|
+
attr_reader :template
|
16
|
+
|
4
17
|
def initialize(context, template)
|
5
18
|
@context = context
|
6
19
|
@template = Addressable::Template.new template
|
7
20
|
end
|
8
21
|
|
22
|
+
def request(method, data, params)
|
23
|
+
context.request method, expand(params), data
|
24
|
+
end
|
25
|
+
|
9
26
|
def get(params = {})
|
10
27
|
request :get, nil, params
|
11
28
|
end
|
@@ -27,25 +44,29 @@ module Restify
|
|
27
44
|
end
|
28
45
|
|
29
46
|
def ==(other)
|
30
|
-
super || (other.is_a?(String) &&
|
47
|
+
super || (other.is_a?(String) && template.pattern == other)
|
31
48
|
end
|
32
49
|
|
33
50
|
def expand(params)
|
34
51
|
params = convert params
|
35
52
|
variables = extract! params
|
36
53
|
|
37
|
-
uri =
|
54
|
+
uri = template.expand variables
|
38
55
|
uri.query_values = (uri.query_values || {}).merge params if params.any?
|
39
56
|
|
40
|
-
|
57
|
+
context.join uri
|
41
58
|
end
|
42
59
|
|
43
|
-
|
60
|
+
def pattern
|
61
|
+
template.pattern
|
62
|
+
end
|
44
63
|
|
45
|
-
def
|
46
|
-
|
64
|
+
def to_s
|
65
|
+
pattern
|
47
66
|
end
|
48
67
|
|
68
|
+
private
|
69
|
+
|
49
70
|
def convert(params)
|
50
71
|
params.each_pair.each_with_object({}) do |param, hash|
|
51
72
|
hash[param[0]] = convert_param param[1]
|
data/lib/restify/resource.rb
CHANGED
@@ -68,12 +68,24 @@ module Restify
|
|
68
68
|
|
69
69
|
# Follow a LOCATION or CONTEXT-LOCATION header.
|
70
70
|
#
|
71
|
-
# @return [Relation] Relation to follow resource.
|
72
|
-
# @raise RuntimeError If nothing to follow.
|
71
|
+
# @return [Relation] Relation to follow resource or nil.
|
73
72
|
#
|
74
73
|
def follow
|
75
74
|
if relation? :_restify_follow
|
76
75
|
relation :_restify_follow
|
76
|
+
else
|
77
|
+
nil
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
# Follow a LOCATION or CONTEXT-LOCATION header.
|
82
|
+
#
|
83
|
+
# @return [Relation] Relation to follow resource.
|
84
|
+
# @raise RuntimeError If nothing to follow.
|
85
|
+
#
|
86
|
+
def follow!
|
87
|
+
if (rel = follow)
|
88
|
+
rel
|
77
89
|
else
|
78
90
|
raise RuntimeError.new 'Nothing to follow'
|
79
91
|
end
|
data/lib/restify/version.rb
CHANGED
data/restify.gemspec
CHANGED
@@ -20,10 +20,10 @@ Gem::Specification.new do |spec|
|
|
20
20
|
|
21
21
|
spec.add_runtime_dependency 'concurrent-ruby', '~> 0.9.0'
|
22
22
|
spec.add_runtime_dependency 'addressable', '~> 2.3'
|
23
|
-
spec.add_runtime_dependency 'typhoeus'
|
24
|
-
spec.add_runtime_dependency 'net-http-persistent'
|
25
23
|
spec.add_runtime_dependency 'hashie', '~> 3.3'
|
26
24
|
spec.add_runtime_dependency 'rack'
|
25
|
+
spec.add_runtime_dependency 'eventmachine', '>= 1.2'
|
26
|
+
spec.add_runtime_dependency 'em-http-request', '~> 1.1.3'
|
27
27
|
|
28
28
|
spec.add_development_dependency 'bundler', '~> 1.5'
|
29
29
|
|
@@ -0,0 +1,39 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Restify::Global do
|
4
|
+
let(:global) { Restify }
|
5
|
+
|
6
|
+
describe '#new' do
|
7
|
+
context 'with string URI' do
|
8
|
+
let(:uri) { 'http://api.github.com/' }
|
9
|
+
let(:options) { {accept: 'application.vnd.github.v3+json'} }
|
10
|
+
|
11
|
+
subject { global.new uri, **options }
|
12
|
+
|
13
|
+
it 'returns relation for URI' do
|
14
|
+
expect(subject).to be_a Restify::Relation
|
15
|
+
expect(subject.pattern).to eq uri
|
16
|
+
expect(subject.context.uri.to_s).to eq uri
|
17
|
+
expect(subject.context.options).to eq options
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
context 'with registry symbol' do
|
22
|
+
let(:name) { :registry_item_name }
|
23
|
+
let(:uri) { 'http://api.github.com/' }
|
24
|
+
let(:options) { {accept: 'application.vnd.github.v3+json'} }
|
25
|
+
let(:context) { Restify::Context.new uri, **options }
|
26
|
+
|
27
|
+
subject { global.new name, options }
|
28
|
+
|
29
|
+
it 'returns relation for stored registry item' do
|
30
|
+
Restify::Registry.store name, uri, options
|
31
|
+
|
32
|
+
expect(subject).to be_a Restify::Relation
|
33
|
+
expect(subject.pattern).to eq uri
|
34
|
+
expect(subject.context.uri.to_s).to eq uri
|
35
|
+
expect(subject.context.options).to eq options
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,52 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Restify::Registry do
|
4
|
+
let(:registry) { described_class.instance }
|
5
|
+
|
6
|
+
describe 'class' do
|
7
|
+
describe '#instance' do
|
8
|
+
subject { described_class.instance }
|
9
|
+
|
10
|
+
it 'returns singleton instance' do
|
11
|
+
expect(subject).to be_a described_class
|
12
|
+
expect(subject).to be described_class.instance
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
describe '#fetch' do
|
17
|
+
it 'delegates to singleton instance' do
|
18
|
+
args = Object.new
|
19
|
+
expect(described_class.instance).to receive(:fetch).with(args)
|
20
|
+
|
21
|
+
described_class.fetch args
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
describe '#store' do
|
26
|
+
it 'delegates to singleton instance' do
|
27
|
+
arg1 = Object.new
|
28
|
+
arg2 = Object.new
|
29
|
+
expect(described_class.instance).to receive(:store).with(arg1, arg2)
|
30
|
+
|
31
|
+
described_class.store arg1, arg2
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
describe '#store / #fetch' do
|
37
|
+
let(:name) { 'remote' }
|
38
|
+
let(:uri) { 'http://remote/entry/point' }
|
39
|
+
let(:opts) { {accept: 'application/vnd.remote+json'} }
|
40
|
+
|
41
|
+
subject { registry.store name, uri, **opts }
|
42
|
+
|
43
|
+
it 'stores registry item' do
|
44
|
+
subject
|
45
|
+
|
46
|
+
item = registry.fetch name
|
47
|
+
|
48
|
+
expect(item.uri.to_s).to eq uri
|
49
|
+
expect(item.options).to eq opts
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
@@ -61,13 +61,40 @@ describe Restify::Resource do
|
|
61
61
|
end
|
62
62
|
end
|
63
63
|
|
64
|
-
|
64
|
+
describe '#follow' do
|
65
65
|
let(:relations) { {_restify_follow: 'http://localhost/10'} }
|
66
66
|
|
67
67
|
it 'returns follow relation' do
|
68
68
|
expect(subject.follow).to be_a Restify::Relation
|
69
69
|
expect(subject.follow).to eq 'http://localhost/10'
|
70
70
|
end
|
71
|
+
|
72
|
+
context 'when nil' do
|
73
|
+
let(:relations) { {} }
|
74
|
+
|
75
|
+
it 'returns nil' do
|
76
|
+
expect(subject.follow).to be nil
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
context '#follow!' do
|
82
|
+
let(:relations) { {_restify_follow: 'http://localhost/10'} }
|
83
|
+
|
84
|
+
it 'returns follow relation' do
|
85
|
+
expect(subject.follow!).to be_a Restify::Relation
|
86
|
+
expect(subject.follow!).to eq 'http://localhost/10'
|
87
|
+
end
|
88
|
+
|
89
|
+
context 'when nil' do
|
90
|
+
let(:relations) { {} }
|
91
|
+
|
92
|
+
it 'raise runtime error' do
|
93
|
+
expect { subject.follow! }.to raise_error RuntimeError do |err|
|
94
|
+
expect(err.message).to eq 'Nothing to follow'
|
95
|
+
end
|
96
|
+
end
|
97
|
+
end
|
71
98
|
end
|
72
99
|
end
|
73
100
|
|
data/spec/restify_spec.rb
CHANGED
@@ -99,17 +99,17 @@ describe Restify do
|
|
99
99
|
end
|
100
100
|
end
|
101
101
|
|
102
|
-
let(:c) do
|
103
|
-
Restify.new('http://localhost/base').get.value
|
104
|
-
end
|
105
|
-
|
106
102
|
context 'within threads' do
|
107
103
|
it 'should consume the API' do
|
108
104
|
# Let's get all users
|
109
105
|
|
106
|
+
# First request the entry resource usually the
|
107
|
+
# root using GET and wait for it.
|
108
|
+
root = Restify.new('http://localhost/base').get.value!
|
109
|
+
|
110
110
|
# Therefore we need the `users` relations of our root
|
111
111
|
# resource.
|
112
|
-
users_relation =
|
112
|
+
users_relation = root.rel(:users)
|
113
113
|
|
114
114
|
# The relation is a `Restify::Relation` and provides
|
115
115
|
# method to enqueue e.g. GET or POST requests with
|
@@ -142,7 +142,7 @@ describe Restify do
|
|
142
142
|
end
|
143
143
|
|
144
144
|
# Let's try again.
|
145
|
-
created_user = users_relation.post(name: 'John Smith').value
|
145
|
+
created_user = users_relation.post(name: 'John Smith').value!
|
146
146
|
|
147
147
|
# The server returns a 201 Created response with the created
|
148
148
|
# resource.
|
@@ -153,7 +153,7 @@ describe Restify do
|
|
153
153
|
expect(created_user.name).to eq 'John Smith'
|
154
154
|
|
155
155
|
# Let's follow the "Location" header.
|
156
|
-
followed_resource = created_user.follow.get.value
|
156
|
+
followed_resource = created_user.follow.get.value!
|
157
157
|
|
158
158
|
expect(followed_resource.response.status).to eq :ok
|
159
159
|
expect(followed_resource.response.code).to eq 200
|
@@ -162,7 +162,7 @@ describe Restify do
|
|
162
162
|
expect(followed_resource.name).to eq 'John Smith'
|
163
163
|
|
164
164
|
# Now we will fetch a list of all users.
|
165
|
-
users = users_relation.get.value
|
165
|
+
users = users_relation.get.value!
|
166
166
|
|
167
167
|
# We get a collection back (Restify::Collection).
|
168
168
|
expect(users).to have(2).items
|
@@ -178,7 +178,7 @@ describe Restify do
|
|
178
178
|
expect(user).to have_relation :blurb
|
179
179
|
|
180
180
|
# Let's get the blurb.
|
181
|
-
blurb = user.rel(:blurb).get.value
|
181
|
+
blurb = user.rel(:blurb).get.value!
|
182
182
|
|
183
183
|
expect(blurb).to have_key :title
|
184
184
|
expect(blurb).to have_key :image
|
@@ -187,5 +187,67 @@ describe Restify do
|
|
187
187
|
expect(blurb[:image]).to eq 'http://example.org/avatar.png'
|
188
188
|
end
|
189
189
|
end
|
190
|
+
|
191
|
+
context 'within EM-synchrony' do
|
192
|
+
it 'should consume the API' do
|
193
|
+
skip 'Seems to be impossible to detect EM scheduled fibers from within'
|
194
|
+
|
195
|
+
EM.synchrony do
|
196
|
+
root = Restify.new('http://localhost/base').get.value!
|
197
|
+
|
198
|
+
users_relation = root.rel(:users)
|
199
|
+
|
200
|
+
expect(users_relation).to be_a Restify::Relation
|
201
|
+
|
202
|
+
create_user_promise = users_relation.post
|
203
|
+
expect(create_user_promise).to be_a Restify::Promise
|
204
|
+
|
205
|
+
expect { create_user_promise.value! }.to \
|
206
|
+
raise_error(Restify::ClientError) do |e|
|
207
|
+
|
208
|
+
expect(e.status).to eq :unprocessable_entity
|
209
|
+
expect(e.code).to eq 422
|
210
|
+
expect(e.errors).to eq 'name' => ["can't be blank"]
|
211
|
+
end
|
212
|
+
|
213
|
+
created_user = users_relation.post(name: 'John Smith').value!
|
214
|
+
|
215
|
+
expect(created_user.response.status).to eq :created
|
216
|
+
expect(created_user.response.code).to eq 201
|
217
|
+
|
218
|
+
expect(created_user).to have_key :name
|
219
|
+
expect(created_user.name).to eq 'John Smith'
|
220
|
+
|
221
|
+
followed_resource = created_user.follow.get.value!
|
222
|
+
|
223
|
+
expect(followed_resource.response.status).to eq :ok
|
224
|
+
expect(followed_resource.response.code).to eq 200
|
225
|
+
|
226
|
+
expect(followed_resource).to have_key :name
|
227
|
+
expect(followed_resource.name).to eq 'John Smith'
|
228
|
+
|
229
|
+
users = users_relation.get.value!
|
230
|
+
|
231
|
+
expect(users).to have(2).items
|
232
|
+
|
233
|
+
user = users.first
|
234
|
+
|
235
|
+
expect(user).to have_key :name
|
236
|
+
expect(user[:name]).to eq 'John Smith'
|
237
|
+
expect(user).to have_relation :self
|
238
|
+
expect(user).to have_relation :blurb
|
239
|
+
|
240
|
+
blurb = user.rel(:blurb).get.value!
|
241
|
+
|
242
|
+
expect(blurb).to have_key :title
|
243
|
+
expect(blurb).to have_key :image
|
244
|
+
|
245
|
+
expect(blurb[:title]).to eq 'Prof. Dr. John Smith'
|
246
|
+
expect(blurb[:image]).to eq 'http://example.org/avatar.png'
|
247
|
+
|
248
|
+
EventMachine.stop
|
249
|
+
end
|
250
|
+
end
|
251
|
+
end
|
190
252
|
end
|
191
253
|
end
|
data/spec/spec_helper.rb
CHANGED
@@ -17,11 +17,16 @@ case ENV['ADAPTER'].to_s.downcase
|
|
17
17
|
when 'typhoeus'
|
18
18
|
require 'restify/adapter/typhoeus'
|
19
19
|
Restify.adapter = Restify::Adapter::Typhoeus.new
|
20
|
+
when 'typhoeus-sync'
|
21
|
+
require 'restify/adapter/typhoeus'
|
22
|
+
Restify.adapter = Restify::Adapter::Typhoeus.new sync: true
|
20
23
|
else
|
21
24
|
raise "Invalid adapter: #{ENV['ADAPTER']}"
|
22
25
|
end if ENV['ADAPTER']
|
23
26
|
|
27
|
+
require 'webmock/rspec'
|
24
28
|
require 'rspec/collection_matchers'
|
29
|
+
require 'em-synchrony'
|
25
30
|
|
26
31
|
Dir[File.expand_path('spec/support/**/*.rb')].each {|f| require f }
|
27
32
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: restify
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.5.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jan Graichen
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-
|
11
|
+
date: 2016-04-04 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: concurrent-ruby
|
@@ -39,21 +39,21 @@ dependencies:
|
|
39
39
|
- !ruby/object:Gem::Version
|
40
40
|
version: '2.3'
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
|
-
name:
|
42
|
+
name: hashie
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
44
44
|
requirements:
|
45
|
-
- - "
|
45
|
+
- - "~>"
|
46
46
|
- !ruby/object:Gem::Version
|
47
|
-
version: '
|
47
|
+
version: '3.3'
|
48
48
|
type: :runtime
|
49
49
|
prerelease: false
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
51
51
|
requirements:
|
52
|
-
- - "
|
52
|
+
- - "~>"
|
53
53
|
- !ruby/object:Gem::Version
|
54
|
-
version: '
|
54
|
+
version: '3.3'
|
55
55
|
- !ruby/object:Gem::Dependency
|
56
|
-
name:
|
56
|
+
name: rack
|
57
57
|
requirement: !ruby/object:Gem::Requirement
|
58
58
|
requirements:
|
59
59
|
- - ">="
|
@@ -67,33 +67,33 @@ dependencies:
|
|
67
67
|
- !ruby/object:Gem::Version
|
68
68
|
version: '0'
|
69
69
|
- !ruby/object:Gem::Dependency
|
70
|
-
name:
|
70
|
+
name: eventmachine
|
71
71
|
requirement: !ruby/object:Gem::Requirement
|
72
72
|
requirements:
|
73
|
-
- - "
|
73
|
+
- - ">="
|
74
74
|
- !ruby/object:Gem::Version
|
75
|
-
version: '
|
75
|
+
version: '1.2'
|
76
76
|
type: :runtime
|
77
77
|
prerelease: false
|
78
78
|
version_requirements: !ruby/object:Gem::Requirement
|
79
79
|
requirements:
|
80
|
-
- - "
|
80
|
+
- - ">="
|
81
81
|
- !ruby/object:Gem::Version
|
82
|
-
version: '
|
82
|
+
version: '1.2'
|
83
83
|
- !ruby/object:Gem::Dependency
|
84
|
-
name:
|
84
|
+
name: em-http-request
|
85
85
|
requirement: !ruby/object:Gem::Requirement
|
86
86
|
requirements:
|
87
|
-
- - "
|
87
|
+
- - "~>"
|
88
88
|
- !ruby/object:Gem::Version
|
89
|
-
version:
|
89
|
+
version: 1.1.3
|
90
90
|
type: :runtime
|
91
91
|
prerelease: false
|
92
92
|
version_requirements: !ruby/object:Gem::Requirement
|
93
93
|
requirements:
|
94
|
-
- - "
|
94
|
+
- - "~>"
|
95
95
|
- !ruby/object:Gem::Version
|
96
|
-
version:
|
96
|
+
version: 1.1.3
|
97
97
|
- !ruby/object:Gem::Dependency
|
98
98
|
name: bundler
|
99
99
|
requirement: !ruby/object:Gem::Requirement
|
@@ -124,18 +124,22 @@ files:
|
|
124
124
|
- lib/restify/adapter/typhoeus.rb
|
125
125
|
- lib/restify/context.rb
|
126
126
|
- lib/restify/error.rb
|
127
|
+
- lib/restify/global.rb
|
127
128
|
- lib/restify/link.rb
|
128
129
|
- lib/restify/processors/base.rb
|
129
130
|
- lib/restify/processors/json.rb
|
130
131
|
- lib/restify/promise.rb
|
132
|
+
- lib/restify/registry.rb
|
131
133
|
- lib/restify/relation.rb
|
132
134
|
- lib/restify/request.rb
|
133
135
|
- lib/restify/resource.rb
|
134
136
|
- lib/restify/response.rb
|
135
137
|
- lib/restify/version.rb
|
136
138
|
- restify.gemspec
|
139
|
+
- spec/restify/global_spec.rb
|
137
140
|
- spec/restify/link_spec.rb
|
138
141
|
- spec/restify/processors/json_spec.rb
|
142
|
+
- spec/restify/registry_spec.rb
|
139
143
|
- spec/restify/relation_spec.rb
|
140
144
|
- spec/restify/resource_spec.rb
|
141
145
|
- spec/restify_spec.rb
|
@@ -165,8 +169,10 @@ signing_key:
|
|
165
169
|
specification_version: 4
|
166
170
|
summary: An experimental hypermedia REST client.
|
167
171
|
test_files:
|
172
|
+
- spec/restify/global_spec.rb
|
168
173
|
- spec/restify/link_spec.rb
|
169
174
|
- spec/restify/processors/json_spec.rb
|
175
|
+
- spec/restify/registry_spec.rb
|
170
176
|
- spec/restify/relation_spec.rb
|
171
177
|
- spec/restify/resource_spec.rb
|
172
178
|
- spec/restify_spec.rb
|