restfully 0.5.2 → 0.5.3

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.
data/CHANGELOG CHANGED
@@ -1,3 +1,9 @@
1
+ 0.5.3
2
+ * can handle text/* content, useful when using low-level methods on a session object (session.{get,post,delete,put})
3
+ * can now find a collection item using collection[:symbol] even if item uid is an integer: collection[:'12345']
4
+ * default_headers no longer overwrite custom headers set by user
5
+ * fixed bug with latest version of rest-client
6
+
1
7
  0.5.2
2
8
  * support for DELETE requests. Use resource.delete(options)
3
9
  * fixed bug in resource.load(:reload => true)
data/Rakefile CHANGED
@@ -10,7 +10,7 @@ begin
10
10
  gem.email = "cyril.rohr@gmail.com"
11
11
  gem.homepage = "http://github.com/crohr/restfully"
12
12
  gem.authors = ["Cyril Rohr"]
13
- gem.add_dependency "rest-client", '>= 1.0'
13
+ gem.add_dependency "rest-client", '>= 1.3'
14
14
  gem.add_dependency "backports"
15
15
  gem.rubyforge_project = 'restfully'
16
16
  # gem is a Gem::Specification... see http://www.rubygems.org/read/chapter/20 for additional settings
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.5.2
1
+ 0.5.3
data/lib/restfully.rb CHANGED
@@ -14,7 +14,7 @@ require 'restfully/collection'
14
14
 
15
15
 
16
16
  module Restfully
17
- VERSION = "0.5.2"
17
+ VERSION = "0.5.3"
18
18
  class << self
19
19
  attr_accessor :adapter
20
20
  end
@@ -33,7 +33,7 @@ module Restfully
33
33
  # else, returns the result of calling <tt>[]</tt> on its superclass.
34
34
  def [](property)
35
35
  if property.kind_of?(Symbol)
36
- find{|i| i['uid'] == property.to_s}
36
+ find{|i| i['uid'] == property.to_s} || find{|i| i['uid'] == property.to_s.to_i}
37
37
  else
38
38
  super(property)
39
39
  end
@@ -77,15 +77,15 @@ module Restfully
77
77
 
78
78
 
79
79
  def pretty_print(pp)
80
- super(pp) do |pp|
80
+ super(pp) do |inner_pp|
81
81
  if @items.length > 0
82
- pp.breakable
83
- pp.text "ITEMS (#{self["offset"]}..#{self["offset"]+@items.length})/#{self["total"]}"
84
- pp.nest 2 do
82
+ inner_pp.breakable
83
+ inner_pp.text "ITEMS (#{self["offset"]}..#{self["offset"]+@items.length})/#{self["total"]}"
84
+ inner_pp.nest 2 do
85
85
  @items.each_with_index do |item, i|
86
- pp.breakable
87
- pp.text "#<#{item.class}:0x#{item.object_id.to_s(16)} uid=#{item['uid'].inspect}>"
88
- pp.text "," if i < @items.length-1
86
+ inner_pp.breakable
87
+ inner_pp.text "#<#{item.class}:0x#{item.object_id.to_s(16)} uid=#{item['uid'].inspect}>"
88
+ inner_pp.text "," if i < @items.length-1
89
89
  end
90
90
  end
91
91
  end
@@ -46,8 +46,8 @@ module Restfully
46
46
  headers.delete(:status)
47
47
  status = response.code
48
48
  rescue RestClient::ExceptionWithResponse => e
49
- body = e.http_body
50
- headers = e.response.to_hash
49
+ body = e.response.to_s
50
+ headers = e.response.headers
51
51
  status = e.http_code
52
52
  end
53
53
  Response.new(status, headers, body)
@@ -11,6 +11,8 @@ module Restfully
11
11
  case content_type
12
12
  when /^application\/.*?json/i
13
13
  JSON.parse(object)
14
+ when /^text\/.*?(plain|html)/i
15
+ object.to_s
14
16
  else
15
17
  raise ParserNotFound.new("Content-Type '#{content_type}' is not supported. Cannot parse the given object.")
16
18
  end
@@ -62,7 +62,9 @@ module Restfully
62
62
 
63
63
  protected
64
64
  def transmit(method, request)
65
- request.add_headers(default_headers) unless default_headers.empty?
65
+ default_headers.each do |header, value|
66
+ request.headers[header] ||= value
67
+ end
66
68
  logger.info "#{method.to_s.upcase} #{request.uri}" +
67
69
  "\nHeaders: #{request.headers.inspect}" +
68
70
  "#{request.body ? "\nBody: #{request.body.length} bytes" : ""}"
data/restfully.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{restfully}
8
- s.version = "0.5.2"
8
+ s.version = "0.5.3"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Cyril Rohr"]
12
- s.date = %q{2009-12-14}
12
+ s.date = %q{2010-02-05}
13
13
  s.default_executable = %q{restfully}
14
14
  s.description = %q{Experimental code for auto-generation of wrappers on top of RESTful APIs that follow HATEOAS principles and provide OPTIONS methods and/or Allow headers.}
15
15
  s.email = %q{cyril.rohr@gmail.com}
@@ -50,6 +50,7 @@ Gem::Specification.new do |s|
50
50
  "restfully.gemspec",
51
51
  "spec/collection_spec.rb",
52
52
  "spec/fixtures/configuration_file.yml",
53
+ "spec/fixtures/grid5000-rennes-jobs.json",
53
54
  "spec/fixtures/grid5000-sites.json",
54
55
  "spec/http/error_spec.rb",
55
56
  "spec/http/headers_spec.rb",
@@ -90,14 +91,14 @@ Gem::Specification.new do |s|
90
91
  s.specification_version = 3
91
92
 
92
93
  if Gem::Version.new(Gem::RubyGemsVersion) >= Gem::Version.new('1.2.0') then
93
- s.add_runtime_dependency(%q<rest-client>, [">= 1.0"])
94
+ s.add_runtime_dependency(%q<rest-client>, [">= 1.3"])
94
95
  s.add_runtime_dependency(%q<backports>, [">= 0"])
95
96
  else
96
- s.add_dependency(%q<rest-client>, [">= 1.0"])
97
+ s.add_dependency(%q<rest-client>, [">= 1.3"])
97
98
  s.add_dependency(%q<backports>, [">= 0"])
98
99
  end
99
100
  else
100
- s.add_dependency(%q<rest-client>, [">= 1.0"])
101
+ s.add_dependency(%q<rest-client>, [">= 1.3"])
101
102
  s.add_dependency(%q<backports>, [">= 0"])
102
103
  end
103
104
  end
@@ -6,6 +6,7 @@ describe Collection do
6
6
  before do
7
7
  @uri = URI.parse('http://api.local/x/y/z')
8
8
  @collection = Collection.new(@uri, session=mock('session')).load(:body => JSON.parse(fixture("grid5000-sites.json")))
9
+ @jobs_collection = Collection.new(@uri, session=mock('session')).load(:body => JSON.parse(fixture("grid5000-rennes-jobs.json")))
9
10
  end
10
11
  it "should be enumerable" do
11
12
  @collection.length.should == 9
@@ -26,6 +27,11 @@ describe Collection do
26
27
  rennes.class.should == Restfully::Resource
27
28
  rennes['uid'].should == 'rennes'
28
29
  end
30
+ it "should try to find the matching item in the collection when calling [] with a symbol" do
31
+ job = @jobs_collection[:'319482']
32
+ job.class.should == Restfully::Resource
33
+ job['uid'].should == 319482
34
+ end
29
35
  end
30
36
 
31
37
  describe "populating collection" do
@@ -0,0 +1,166 @@
1
+ {
2
+ "items": [
3
+ {
4
+ "name": "test",
5
+ "submitted_at": 1265359473,
6
+ "uid": 319482,
7
+ "user_uid": "crohr",
8
+ "links": [
9
+ {
10
+ "href": "/sid/grid5000/sites/rennes/jobs/319482",
11
+ "rel": "self",
12
+ "type": "application/vnd.fr.grid5000.api.Job+json;level=1"
13
+ },
14
+ {
15
+ "href": "/sid/grid5000/sites/rennes",
16
+ "rel": "parent",
17
+ "type": "application/vnd.fr.grid5000.api.Site+json;level=1"
18
+ }
19
+ ],
20
+ "queue": "default",
21
+ "state": "running"
22
+ },
23
+ {
24
+ "submitted_at": 1265359155,
25
+ "uid": 319481,
26
+ "user_uid": "rnou",
27
+ "links": [
28
+ {
29
+ "href": "/sid/grid5000/sites/rennes/jobs/319481",
30
+ "rel": "self",
31
+ "type": "application/vnd.fr.grid5000.api.Job+json;level=1"
32
+ },
33
+ {
34
+ "href": "/sid/grid5000/sites/rennes",
35
+ "rel": "parent",
36
+ "type": "application/vnd.fr.grid5000.api.Site+json;level=1"
37
+ }
38
+ ],
39
+ "queue": "default",
40
+ "state": "running"
41
+ },
42
+ {
43
+ "submitted_at": 1265359003,
44
+ "uid": 319480,
45
+ "user_uid": "ethome",
46
+ "links": [
47
+ {
48
+ "href": "/sid/grid5000/sites/rennes/jobs/319480",
49
+ "rel": "self",
50
+ "type": "application/vnd.fr.grid5000.api.Job+json;level=1"
51
+ },
52
+ {
53
+ "href": "/sid/grid5000/sites/rennes",
54
+ "rel": "parent",
55
+ "type": "application/vnd.fr.grid5000.api.Site+json;level=1"
56
+ }
57
+ ],
58
+ "queue": "default",
59
+ "state": "running"
60
+ },
61
+ {
62
+ "submitted_at": 1265354868,
63
+ "uid": 319479,
64
+ "user_uid": "jarnaud",
65
+ "links": [
66
+ {
67
+ "href": "/sid/grid5000/sites/rennes/jobs/319479",
68
+ "rel": "self",
69
+ "type": "application/vnd.fr.grid5000.api.Job+json;level=1"
70
+ },
71
+ {
72
+ "href": "/sid/grid5000/sites/rennes",
73
+ "rel": "parent",
74
+ "type": "application/vnd.fr.grid5000.api.Site+json;level=1"
75
+ }
76
+ ],
77
+ "queue": "default",
78
+ "state": "running"
79
+ },
80
+ {
81
+ "submitted_at": 1265312207,
82
+ "uid": 319462,
83
+ "user_uid": "acarpena",
84
+ "links": [
85
+ {
86
+ "href": "/sid/grid5000/sites/rennes/jobs/319462",
87
+ "rel": "self",
88
+ "type": "application/vnd.fr.grid5000.api.Job+json;level=1"
89
+ },
90
+ {
91
+ "href": "/sid/grid5000/sites/rennes",
92
+ "rel": "parent",
93
+ "type": "application/vnd.fr.grid5000.api.Site+json;level=1"
94
+ }
95
+ ],
96
+ "queue": "default",
97
+ "state": "waiting"
98
+ },
99
+ {
100
+ "submitted_at": 1265292999,
101
+ "uid": 319432,
102
+ "user_uid": "acarpena",
103
+ "links": [
104
+ {
105
+ "href": "/sid/grid5000/sites/rennes/jobs/319432",
106
+ "rel": "self",
107
+ "type": "application/vnd.fr.grid5000.api.Job+json;level=1"
108
+ },
109
+ {
110
+ "href": "/sid/grid5000/sites/rennes",
111
+ "rel": "parent",
112
+ "type": "application/vnd.fr.grid5000.api.Site+json;level=1"
113
+ }
114
+ ],
115
+ "queue": "default",
116
+ "state": "waiting"
117
+ },
118
+ {
119
+ "submitted_at": 1265218740,
120
+ "uid": 319355,
121
+ "user_uid": "bfnicola",
122
+ "links": [
123
+ {
124
+ "href": "/sid/grid5000/sites/rennes/jobs/319355",
125
+ "rel": "self",
126
+ "type": "application/vnd.fr.grid5000.api.Job+json;level=1"
127
+ },
128
+ {
129
+ "href": "/sid/grid5000/sites/rennes",
130
+ "rel": "parent",
131
+ "type": "application/vnd.fr.grid5000.api.Site+json;level=1"
132
+ }
133
+ ],
134
+ "queue": "default",
135
+ "state": "waiting"
136
+ },
137
+ {
138
+ "submitted_at": 1265148155,
139
+ "uid": 319332,
140
+ "user_uid": "akguyantoine",
141
+ "links": [
142
+ {
143
+ "href": "/sid/grid5000/sites/rennes/jobs/319332",
144
+ "rel": "self",
145
+ "type": "application/vnd.fr.grid5000.api.Job+json;level=1"
146
+ },
147
+ {
148
+ "href": "/sid/grid5000/sites/rennes",
149
+ "rel": "parent",
150
+ "type": "application/vnd.fr.grid5000.api.Site+json;level=1"
151
+ }
152
+ ],
153
+ "queue": "default",
154
+ "state": "waiting"
155
+ }
156
+ ],
157
+ "total": 8,
158
+ "links": [
159
+ {
160
+ "href": "/sid/grid5000/sites/rennes/jobs",
161
+ "rel": "self",
162
+ "type": "application/vnd.fr.grid5000.api.Collection+json;level=1"
163
+ }
164
+ ],
165
+ "offset": 0
166
+ }
@@ -22,7 +22,7 @@ describe Restfully::HTTP::Adapters::RestClientAdapter do
22
22
  lambda{adapter.put(mock("restfully request"))}.should raise_error NotImplementedError, "PUT is not supported by your adapter."
23
23
  end
24
24
  it "should rescue any RestClient::Exception and correctly populate the response" do
25
- res = mock(Net::HTTPResponse, :code => 404, :body => '{"message":"whatever"}', :to_hash => {'Content-Type' => 'application/json;charset=utf-8', 'Content-Length' => 22}, :[] => '')
25
+ res = mock(RestClient::Response, :code => 404, :to_s => '{"message":"whatever"}', :headers => {:content_type => 'application/json;charset=utf-8', :content_length => 22})
26
26
  RestClient::Resource.should_receive(:new).and_raise RestClient::ResourceNotFound.new(res)
27
27
  adapter = Restfully::HTTP::Adapters::RestClientAdapter.new("https://api.grid5000.fr", :username => 'crohr', :password => 'password')
28
28
  response = adapter.get(mock("request", :uri => "uri"))
data/spec/parsing_spec.rb CHANGED
@@ -22,4 +22,8 @@ describe Restfully::Parsing do
22
22
  object = {'p1' => 'v1'}
23
23
  serialize(object, :content_type => 'application/json;charset=utf-8').should == object.to_json
24
24
  end
25
+ it "should correctly unserialize text content" do
26
+ object = "anything"
27
+ unserialize(object, :content_type => 'text/plain;charset=utf-8').should == object
28
+ end
25
29
  end
data/spec/session_spec.rb CHANGED
@@ -83,7 +83,9 @@ describe Session do
83
83
  describe "Transmitting requests" do
84
84
  before do
85
85
  Session.send(:public, :transmit)
86
- @request.should_receive(:add_headers).with("User-Agent"=>"Restfully/#{restfully_version}", "Accept"=>"application/json")
86
+ @request.headers.stub!(:[]).and_return(nil)
87
+ @request.headers.should_receive(:[]=).with("User-Agent", "Restfully/#{restfully_version}")
88
+ @request.headers.should_receive(:[]=).with("Accept", "application/json")
87
89
  end
88
90
  it "should send a head" do
89
91
  @session.connection.should_receive(:head).with(@request).and_return(@response)
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: restfully
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.2
4
+ version: 0.5.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Cyril Rohr
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2009-12-14 00:00:00 +01:00
12
+ date: 2010-02-05 00:00:00 +01:00
13
13
  default_executable: restfully
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
@@ -20,7 +20,7 @@ dependencies:
20
20
  requirements:
21
21
  - - ">="
22
22
  - !ruby/object:Gem::Version
23
- version: "1.0"
23
+ version: "1.3"
24
24
  version:
25
25
  - !ruby/object:Gem::Dependency
26
26
  name: backports
@@ -73,6 +73,7 @@ files:
73
73
  - restfully.gemspec
74
74
  - spec/collection_spec.rb
75
75
  - spec/fixtures/configuration_file.yml
76
+ - spec/fixtures/grid5000-rennes-jobs.json
76
77
  - spec/fixtures/grid5000-sites.json
77
78
  - spec/http/error_spec.rb
78
79
  - spec/http/headers_spec.rb