activeresource_csi 2.3.5.p6

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.
@@ -0,0 +1,122 @@
1
+ require 'abstract_unit'
2
+
3
+ class AuthorizationTest < Test::Unit::TestCase
4
+ Response = Struct.new(:code)
5
+
6
+ def setup
7
+ @conn = ActiveResource::Connection.new('http://localhost')
8
+ @matz = { :id => 1, :name => 'Matz' }.to_xml(:root => 'person')
9
+ @david = { :id => 2, :name => 'David' }.to_xml(:root => 'person')
10
+ @authenticated_conn = ActiveResource::Connection.new("http://david:test123@localhost")
11
+ @authorization_request_header = { 'Authorization' => 'Basic ZGF2aWQ6dGVzdDEyMw==' }
12
+
13
+ ActiveResource::HttpMock.respond_to do |mock|
14
+ mock.get "/people/2.xml", @authorization_request_header, @david
15
+ mock.put "/people/2.xml", @authorization_request_header, nil, 204
16
+ mock.delete "/people/2.xml", @authorization_request_header, nil, 200
17
+ mock.post "/people/2/addresses.xml", @authorization_request_header, nil, 201, 'Location' => '/people/1/addresses/5'
18
+ end
19
+ end
20
+
21
+ def test_authorization_header
22
+ authorization_header = @authenticated_conn.__send__(:authorization_header)
23
+ assert_equal @authorization_request_header['Authorization'], authorization_header['Authorization']
24
+ authorization = authorization_header["Authorization"].to_s.split
25
+
26
+ assert_equal "Basic", authorization[0]
27
+ assert_equal ["david", "test123"], ActiveSupport::Base64.decode64(authorization[1]).split(":")[0..1]
28
+ end
29
+
30
+ def test_authorization_header_with_username_but_no_password
31
+ @conn = ActiveResource::Connection.new("http://david:@localhost")
32
+ authorization_header = @conn.__send__(:authorization_header)
33
+ authorization = authorization_header["Authorization"].to_s.split
34
+
35
+ assert_equal "Basic", authorization[0]
36
+ assert_equal ["david"], ActiveSupport::Base64.decode64(authorization[1]).split(":")[0..1]
37
+ end
38
+
39
+ def test_authorization_header_with_password_but_no_username
40
+ @conn = ActiveResource::Connection.new("http://:test123@localhost")
41
+ authorization_header = @conn.__send__(:authorization_header)
42
+ authorization = authorization_header["Authorization"].to_s.split
43
+
44
+ assert_equal "Basic", authorization[0]
45
+ assert_equal ["", "test123"], ActiveSupport::Base64.decode64(authorization[1]).split(":")[0..1]
46
+ end
47
+
48
+ def test_authorization_header_with_decoded_credentials_from_url
49
+ @conn = ActiveResource::Connection.new("http://my%40email.com:%31%32%33@localhost")
50
+ authorization_header = @conn.__send__(:authorization_header)
51
+ authorization = authorization_header["Authorization"].to_s.split
52
+
53
+ assert_equal "Basic", authorization[0]
54
+ assert_equal ["my@email.com", "123"], ActiveSupport::Base64.decode64(authorization[1]).split(":")[0..1]
55
+ end
56
+
57
+ def test_authorization_header_explicitly_setting_username_and_password
58
+ @authenticated_conn = ActiveResource::Connection.new("http://@localhost")
59
+ @authenticated_conn.user = 'david'
60
+ @authenticated_conn.password = 'test123'
61
+ authorization_header = @authenticated_conn.__send__(:authorization_header)
62
+ assert_equal @authorization_request_header['Authorization'], authorization_header['Authorization']
63
+ authorization = authorization_header["Authorization"].to_s.split
64
+
65
+ assert_equal "Basic", authorization[0]
66
+ assert_equal ["david", "test123"], ActiveSupport::Base64.decode64(authorization[1]).split(":")[0..1]
67
+ end
68
+
69
+ def test_authorization_header_explicitly_setting_username_but_no_password
70
+ @conn = ActiveResource::Connection.new("http://@localhost")
71
+ @conn.user = "david"
72
+ authorization_header = @conn.__send__(:authorization_header)
73
+ authorization = authorization_header["Authorization"].to_s.split
74
+
75
+ assert_equal "Basic", authorization[0]
76
+ assert_equal ["david"], ActiveSupport::Base64.decode64(authorization[1]).split(":")[0..1]
77
+ end
78
+
79
+ def test_authorization_header_explicitly_setting_password_but_no_username
80
+ @conn = ActiveResource::Connection.new("http://@localhost")
81
+ @conn.password = "test123"
82
+ authorization_header = @conn.__send__(:authorization_header)
83
+ authorization = authorization_header["Authorization"].to_s.split
84
+
85
+ assert_equal "Basic", authorization[0]
86
+ assert_equal ["", "test123"], ActiveSupport::Base64.decode64(authorization[1]).split(":")[0..1]
87
+ end
88
+
89
+ def test_get
90
+ david = @authenticated_conn.get("/people/2.xml")
91
+ assert_equal "David", david["name"]
92
+ end
93
+
94
+ def test_post
95
+ response = @authenticated_conn.post("/people/2/addresses.xml")
96
+ assert_equal "/people/1/addresses/5", response["Location"]
97
+ end
98
+
99
+ def test_put
100
+ response = @authenticated_conn.put("/people/2.xml")
101
+ assert_equal 204, response.code
102
+ end
103
+
104
+ def test_delete
105
+ response = @authenticated_conn.delete("/people/2.xml")
106
+ assert_equal 200, response.code
107
+ end
108
+
109
+ def test_raises_invalid_request_on_unauthorized_requests
110
+ assert_raise(ActiveResource::InvalidRequestError) { @conn.post("/people/2.xml") }
111
+ assert_raise(ActiveResource::InvalidRequestError) { @conn.post("/people/2/addresses.xml") }
112
+ assert_raise(ActiveResource::InvalidRequestError) { @conn.put("/people/2.xml") }
113
+ assert_raise(ActiveResource::InvalidRequestError) { @conn.delete("/people/2.xml") }
114
+ end
115
+
116
+ protected
117
+ def assert_response_raises(klass, code)
118
+ assert_raise(klass, "Expected response code #{code} to raise #{klass}") do
119
+ @conn.__send__(:handle_response, Response.new(code))
120
+ end
121
+ end
122
+ end
@@ -0,0 +1,100 @@
1
+ require 'abstract_unit'
2
+ require 'fixtures/person'
3
+ require 'fixtures/street_address'
4
+
5
+ class CustomMethodsTest < Test::Unit::TestCase
6
+ def setup
7
+ @matz = { :id => 1, :name => 'Matz' }.to_xml(:root => 'person')
8
+ @matz_deep = { :id => 1, :name => 'Matz', :other => 'other' }.to_xml(:root => 'person')
9
+ @matz_array = [{ :id => 1, :name => 'Matz' }].to_xml(:root => 'people')
10
+ @ryan = { :name => 'Ryan' }.to_xml(:root => 'person')
11
+ @addy = { :id => 1, :street => '12345 Street' }.to_xml(:root => 'address')
12
+ @addy_deep = { :id => 1, :street => '12345 Street', :zip => "27519" }.to_xml(:root => 'address')
13
+
14
+ ActiveResource::HttpMock.respond_to do |mock|
15
+ mock.get "/people/1.xml", {}, @matz
16
+ mock.get "/people/1/shallow.xml", {}, @matz
17
+ mock.get "/people/1/deep.xml", {}, @matz_deep
18
+ mock.get "/people/retrieve.xml?name=Matz", {}, @matz_array
19
+ mock.get "/people/managers.xml", {}, @matz_array
20
+ mock.post "/people/hire.xml?name=Matz", {}, nil, 201
21
+ mock.put "/people/1/promote.xml?position=Manager", {}, nil, 204
22
+ mock.put "/people/promote.xml?name=Matz", {}, nil, 204, {}
23
+ mock.put "/people/sort.xml?by=name", {}, nil, 204
24
+ mock.delete "/people/deactivate.xml?name=Matz", {}, nil, 200
25
+ mock.delete "/people/1/deactivate.xml", {}, nil, 200
26
+ mock.post "/people/new/register.xml", {}, @ryan, 201, 'Location' => '/people/5.xml'
27
+ mock.post "/people/1/register.xml", {}, @matz, 201
28
+ mock.get "/people/1/addresses/1.xml", {}, @addy
29
+ mock.get "/people/1/addresses/1/deep.xml", {}, @addy_deep
30
+ mock.put "/people/1/addresses/1/normalize_phone.xml?locale=US", {}, nil, 204
31
+ mock.put "/people/1/addresses/sort.xml?by=name", {}, nil, 204
32
+ mock.post "/people/1/addresses/new/link.xml", {}, { :street => '12345 Street' }.to_xml(:root => 'address'), 201, 'Location' => '/people/1/addresses/2.xml'
33
+ end
34
+
35
+ Person.user = nil
36
+ Person.password = nil
37
+ end
38
+
39
+ def teardown
40
+ ActiveResource::HttpMock.reset!
41
+ end
42
+
43
+ def test_custom_collection_method
44
+ # GET
45
+ assert_equal([{ "id" => 1, "name" => 'Matz' }], Person.get(:retrieve, :name => 'Matz'))
46
+
47
+ # POST
48
+ assert_equal(ActiveResource::Response.new("", 201, {}), Person.post(:hire, :name => 'Matz'))
49
+
50
+ # PUT
51
+ assert_equal ActiveResource::Response.new("", 204, {}),
52
+ Person.put(:promote, {:name => 'Matz'}, 'atestbody')
53
+ assert_equal ActiveResource::Response.new("", 204, {}), Person.put(:sort, :by => 'name')
54
+
55
+ # DELETE
56
+ Person.delete :deactivate, :name => 'Matz'
57
+
58
+ # Nested resource
59
+ assert_equal ActiveResource::Response.new("", 204, {}), StreetAddress.put(:sort, :person_id => 1, :by => 'name')
60
+ end
61
+
62
+ def test_custom_element_method
63
+ # Test GET against an element URL
64
+ assert_equal Person.find(1).get(:shallow), {"id" => 1, "name" => 'Matz'}
65
+ assert_equal Person.find(1).get(:deep), {"id" => 1, "name" => 'Matz', "other" => 'other'}
66
+
67
+ # Test PUT against an element URL
68
+ assert_equal ActiveResource::Response.new("", 204, {}), Person.find(1).put(:promote, {:position => 'Manager'}, 'body')
69
+
70
+ # Test DELETE against an element URL
71
+ assert_equal ActiveResource::Response.new("", 200, {}), Person.find(1).delete(:deactivate)
72
+
73
+ # With nested resources
74
+ assert_equal StreetAddress.find(1, :params => { :person_id => 1 }).get(:deep),
75
+ { "id" => 1, "street" => '12345 Street', "zip" => "27519" }
76
+ assert_equal ActiveResource::Response.new("", 204, {}),
77
+ StreetAddress.find(1, :params => { :person_id => 1 }).put(:normalize_phone, :locale => 'US')
78
+ end
79
+
80
+ def test_custom_new_element_method
81
+ # Test POST against a new element URL
82
+ ryan = Person.new(:name => 'Ryan')
83
+ assert_equal ActiveResource::Response.new(@ryan, 201, {'Location' => '/people/5.xml'}), ryan.post(:register)
84
+ expected_request = ActiveResource::Request.new(:post, '/people/new/register.xml', @ryan)
85
+ assert_equal expected_request.body, ActiveResource::HttpMock.requests.first.body
86
+
87
+ # Test POST against a nested collection URL
88
+ addy = StreetAddress.new(:street => '123 Test Dr.', :person_id => 1)
89
+ assert_equal ActiveResource::Response.new({ :street => '12345 Street' }.to_xml(:root => 'address'),
90
+ 201, {'Location' => '/people/1/addresses/2.xml'}),
91
+ addy.post(:link)
92
+
93
+ matz = Person.new(:id => 1, :name => 'Matz')
94
+ assert_equal ActiveResource::Response.new(@matz, 201), matz.post(:register)
95
+ end
96
+
97
+ def test_find_custom_resources
98
+ assert_equal 'Matz', Person.find(:all, :from => :managers).first.name
99
+ end
100
+ end
@@ -0,0 +1,52 @@
1
+ require 'abstract_unit'
2
+ require "fixtures/person"
3
+ require "fixtures/street_address"
4
+
5
+ class BaseEqualityTest < Test::Unit::TestCase
6
+ def setup
7
+ @new = Person.new
8
+ @one = Person.new(:id => 1)
9
+ @two = Person.new(:id => 2)
10
+ @street = StreetAddress.new(:id => 2)
11
+ end
12
+
13
+ def test_should_equal_self
14
+ assert @new == @new, '@new == @new'
15
+ assert @one == @one, '@one == @one'
16
+ end
17
+
18
+ def test_shouldnt_equal_new_resource
19
+ assert @new != @one, '@new != @one'
20
+ assert @one != @new, '@one != @new'
21
+ end
22
+
23
+ def test_shouldnt_equal_different_class
24
+ assert @two != @street, 'person != street_address with same id'
25
+ assert @street != @two, 'street_address != person with same id'
26
+ end
27
+
28
+ def test_eql_should_alias_equals_operator
29
+ assert_equal @new == @new, @new.eql?(@new)
30
+ assert_equal @new == @one, @new.eql?(@one)
31
+
32
+ assert_equal @one == @one, @one.eql?(@one)
33
+ assert_equal @one == @new, @one.eql?(@new)
34
+
35
+ assert_equal @one == @street, @one.eql?(@street)
36
+ end
37
+
38
+ def test_hash_should_be_id_hash
39
+ [@new, @one, @two, @street].each do |resource|
40
+ assert_equal resource.id.hash, resource.hash
41
+ end
42
+ end
43
+
44
+ def test_with_prefix_options
45
+ assert_equal @one == @one, @one.eql?(@one)
46
+ assert_equal @one == @one.dup, @one.eql?(@one.dup)
47
+ new_one = @one.dup
48
+ new_one.prefix_options = {:foo => 'bar'}
49
+ assert_not_equal @one, new_one
50
+ end
51
+
52
+ end
@@ -0,0 +1,161 @@
1
+ require 'abstract_unit'
2
+ require "fixtures/person"
3
+ require "fixtures/street_address"
4
+
5
+ module Highrise
6
+ class Note < ActiveResource::Base
7
+ self.site = "http://37s.sunrise.i:3000"
8
+ end
9
+
10
+ class Comment < ActiveResource::Base
11
+ self.site = "http://37s.sunrise.i:3000"
12
+ end
13
+
14
+ module Deeply
15
+ module Nested
16
+
17
+ class Note < ActiveResource::Base
18
+ self.site = "http://37s.sunrise.i:3000"
19
+ end
20
+
21
+ class Comment < ActiveResource::Base
22
+ self.site = "http://37s.sunrise.i:3000"
23
+ end
24
+
25
+ module TestDifferentLevels
26
+
27
+ class Note < ActiveResource::Base
28
+ self.site = "http://37s.sunrise.i:3000"
29
+ end
30
+
31
+ end
32
+
33
+ end
34
+ end
35
+
36
+ end
37
+
38
+
39
+ class BaseLoadTest < Test::Unit::TestCase
40
+ def setup
41
+ @matz = { :id => 1, :name => 'Matz' }
42
+
43
+ @first_address = { :id => 1, :street => '12345 Street' }
44
+ @addresses = [@first_address, { :id => 2, :street => '67890 Street' }]
45
+ @addresses_from_xml = { :street_addresses => @addresses }
46
+ @addresses_from_xml_single = { :street_addresses => [ @first_address ] }
47
+
48
+ @deep = { :id => 1, :street => {
49
+ :id => 1, :state => { :id => 1, :name => 'Oregon',
50
+ :notable_rivers => [
51
+ { :id => 1, :name => 'Willamette' },
52
+ { :id => 2, :name => 'Columbia', :rafted_by => @matz }],
53
+ :postal_codes => [ 97018, 1234567890 ],
54
+ :places => [ "Columbia City", "Unknown" ]}}}
55
+
56
+ @person = Person.new
57
+ end
58
+
59
+ def test_load_expects_hash
60
+ assert_raise(ArgumentError) { @person.load nil }
61
+ assert_raise(ArgumentError) { @person.load '<person id="1"/>' }
62
+ end
63
+
64
+ def test_load_simple_hash
65
+ assert_equal Hash.new, @person.attributes
66
+ assert_equal @matz.stringify_keys, @person.load(@matz).attributes
67
+ end
68
+
69
+ def test_load_one_with_existing_resource
70
+ address = @person.load(:street_address => @first_address).street_address
71
+ assert_kind_of StreetAddress, address
72
+ assert_equal @first_address.stringify_keys, address.attributes
73
+ end
74
+
75
+ def test_load_one_with_unknown_resource
76
+ address = silence_warnings { @person.load(:address => @first_address).address }
77
+ assert_kind_of Person::Address, address
78
+ assert_equal @first_address.stringify_keys, address.attributes
79
+ end
80
+
81
+ def test_load_collection_with_existing_resource
82
+ addresses = @person.load(@addresses_from_xml).street_addresses
83
+ assert_kind_of Array, addresses
84
+ addresses.each { |address| assert_kind_of StreetAddress, address }
85
+ assert_equal @addresses.map(&:stringify_keys), addresses.map(&:attributes)
86
+ end
87
+
88
+ def test_load_collection_with_unknown_resource
89
+ Person.__send__(:remove_const, :Address) if Person.const_defined?(:Address)
90
+ assert !Person.const_defined?(:Address), "Address shouldn't exist until autocreated"
91
+ addresses = silence_warnings { @person.load(:addresses => @addresses).addresses }
92
+ assert Person.const_defined?(:Address), "Address should have been autocreated"
93
+ addresses.each { |address| assert_kind_of Person::Address, address }
94
+ assert_equal @addresses.map(&:stringify_keys), addresses.map(&:attributes)
95
+ end
96
+
97
+ def test_load_collection_with_single_existing_resource
98
+ addresses = @person.load(@addresses_from_xml_single).street_addresses
99
+ assert_kind_of Array, addresses
100
+ addresses.each { |address| assert_kind_of StreetAddress, address }
101
+ assert_equal [ @first_address ].map(&:stringify_keys), addresses.map(&:attributes)
102
+ end
103
+
104
+ def test_load_collection_with_single_unknown_resource
105
+ Person.__send__(:remove_const, :Address) if Person.const_defined?(:Address)
106
+ assert !Person.const_defined?(:Address), "Address shouldn't exist until autocreated"
107
+ addresses = silence_warnings { @person.load(:addresses => [ @first_address ]).addresses }
108
+ assert Person.const_defined?(:Address), "Address should have been autocreated"
109
+ addresses.each { |address| assert_kind_of Person::Address, address }
110
+ assert_equal [ @first_address ].map(&:stringify_keys), addresses.map(&:attributes)
111
+ end
112
+
113
+ def test_recursively_loaded_collections
114
+ person = @person.load(@deep)
115
+ assert_equal @deep[:id], person.id
116
+
117
+ street = person.street
118
+ assert_kind_of Person::Street, street
119
+ assert_equal @deep[:street][:id], street.id
120
+
121
+ state = street.state
122
+ assert_kind_of Person::Street::State, state
123
+ assert_equal @deep[:street][:state][:id], state.id
124
+
125
+ rivers = state.notable_rivers
126
+ assert_kind_of Array, rivers
127
+ assert_kind_of Person::Street::State::NotableRiver, rivers.first
128
+ assert_equal @deep[:street][:state][:notable_rivers].first[:id], rivers.first.id
129
+ assert_equal @matz[:id], rivers.last.rafted_by.id
130
+
131
+ postal_codes = state.postal_codes
132
+ assert_kind_of Array, postal_codes
133
+ assert_equal 2, postal_codes.size
134
+ assert_kind_of Fixnum, postal_codes.first
135
+ assert_equal @deep[:street][:state][:postal_codes].first, postal_codes.first
136
+ assert_kind_of Numeric, postal_codes.last
137
+ assert_equal @deep[:street][:state][:postal_codes].last, postal_codes.last
138
+
139
+ places = state.places
140
+ assert_kind_of Array, places
141
+ assert_kind_of String, places.first
142
+ assert_equal @deep[:street][:state][:places].first, places.first
143
+ end
144
+
145
+ def test_nested_collections_within_the_same_namespace
146
+ n = Highrise::Note.new(:comments => [{ :name => "1" }])
147
+ assert_kind_of Highrise::Comment, n.comments.first
148
+ end
149
+
150
+ def test_nested_collections_within_deeply_nested_namespace
151
+ n = Highrise::Deeply::Nested::Note.new(:comments => [{ :name => "1" }])
152
+ assert_kind_of Highrise::Deeply::Nested::Comment, n.comments.first
153
+ end
154
+
155
+ def test_nested_collections_in_different_levels_of_namespaces
156
+ n = Highrise::Deeply::Nested::TestDifferentLevels::Note.new(:comments => [{ :name => "1" }])
157
+ assert_kind_of Highrise::Deeply::Nested::Comment, n.comments.first
158
+ end
159
+
160
+
161
+ end
@@ -0,0 +1,85 @@
1
+ require 'abstract_unit'
2
+ require "fixtures/person"
3
+
4
+ class BaseErrorsTest < Test::Unit::TestCase
5
+ def setup
6
+ ActiveResource::HttpMock.respond_to do |mock|
7
+ mock.post "/people.xml", {}, %q(<?xml version="1.0" encoding="UTF-8"?><errors><error>Age can't be blank</error><error>Name can't be blank</error><error>Name must start with a letter</error><error>Person quota full for today.</error></errors>), 422, {'Content-Type' => 'application/xml; charset=utf-8'}
8
+ mock.post "/people.json", {}, %q({"errors":["Age can't be blank","Name can't be blank","Name must start with a letter","Person quota full for today."]}), 422, {'Content-Type' => 'application/json; charset=utf-8'}
9
+ end
10
+ @person = Person.new(:name => '', :age => '')
11
+ assert_equal @person.save, false
12
+ end
13
+
14
+ def test_should_mark_as_invalid
15
+ [ :json, :xml ].each do |format|
16
+ invalid_user_using_format(format) do
17
+ assert !@person.valid?
18
+ end
19
+ end
20
+ end
21
+
22
+ def test_should_parse_xml_errors
23
+ [ :json, :xml ].each do |format|
24
+ invalid_user_using_format(format) do
25
+ assert_kind_of ActiveResource::Errors, @person.errors
26
+ assert_equal 4, @person.errors.size
27
+ end
28
+ end
29
+ end
30
+
31
+ def test_should_parse_errors_to_individual_attributes
32
+ [ :json, :xml ].each do |format|
33
+ invalid_user_using_format(format) do
34
+ assert @person.errors[:name].any?
35
+ assert_equal "can't be blank", @person.errors[:age]
36
+ assert_equal ["can't be blank", "must start with a letter"], @person.errors[:name]
37
+ assert_equal "Person quota full for today.", @person.errors[:base]
38
+ end
39
+ end
40
+ end
41
+
42
+ def test_should_iterate_over_errors
43
+ [ :json, :xml ].each do |format|
44
+ invalid_user_using_format(format) do
45
+ errors = []
46
+ @person.errors.each { |attribute, message| errors << [attribute, message] }
47
+ assert errors.include?(['name', "can't be blank"])
48
+ end
49
+ end
50
+ end
51
+
52
+ def test_should_iterate_over_full_errors
53
+ [ :json, :xml ].each do |format|
54
+ invalid_user_using_format(format) do
55
+ errors = []
56
+ @person.errors.to_a.each { |message| errors << message }
57
+ assert errors.include?(["name", "can't be blank"])
58
+ end
59
+ end
60
+ end
61
+
62
+ def test_should_format_full_errors
63
+ [ :json, :xml ].each do |format|
64
+ invalid_user_using_format(format) do
65
+ full = @person.errors.full_messages
66
+ assert full.include?("Age can't be blank")
67
+ assert full.include?("Name can't be blank")
68
+ assert full.include?("Name must start with a letter")
69
+ assert full.include?("Person quota full for today.")
70
+ end
71
+ end
72
+ end
73
+
74
+ private
75
+ def invalid_user_using_format(mime_type_reference)
76
+ previous_format = Person.format
77
+ Person.format = mime_type_reference
78
+ @person = Person.new(:name => '', :age => '')
79
+ assert_equal false, @person.save
80
+
81
+ yield
82
+ ensure
83
+ Person.format = previous_format
84
+ end
85
+ end