savon 0.9.3 → 0.9.4
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.md +5 -0
- data/lib/savon/client.rb +11 -15
- data/lib/savon/version.rb +1 -1
- data/lib/savon/wasabi/document.rb +41 -0
- data/savon.gemspec +1 -0
- data/spec/savon/client_spec.rb +14 -14
- data/spec/savon/wasabi/document_spec.rb +45 -0
- metadata +91 -23
- data/lib/savon/wsdl/document.rb +0 -112
- data/lib/savon/wsdl/parser.rb +0 -96
- data/lib/savon/wsdl/request.rb +0 -41
- data/spec/savon/wsdl/document_spec.rb +0 -132
- data/spec/savon/wsdl/parser_spec.rb +0 -107
- data/spec/savon/wsdl/request_spec.rb +0 -23
data/CHANGELOG.md
CHANGED
@@ -1,3 +1,8 @@
|
|
1
|
+
## 0.9.4 (2011-07-03)
|
2
|
+
|
3
|
+
* Refactoring: Extracted the WSDL parser out into the [wasabi](http://rubygems.org/gems/wasabi) gem.
|
4
|
+
This should isolate upcoming improvements to the parser.
|
5
|
+
|
1
6
|
## 0.9.3 (2011-06-30)
|
2
7
|
|
3
8
|
* Fix: [issue 138](https://github.com/rubiii/savon/issues/138) -
|
data/lib/savon/client.rb
CHANGED
@@ -1,16 +1,15 @@
|
|
1
1
|
require "httpi/request"
|
2
|
+
require "savon/wasabi/document"
|
2
3
|
require "savon/soap/xml"
|
3
4
|
require "savon/soap/request"
|
4
5
|
require "savon/soap/response"
|
5
|
-
require "savon/wsdl/document"
|
6
6
|
require "savon/wsse"
|
7
7
|
|
8
8
|
module Savon
|
9
9
|
|
10
10
|
# = Savon::Client
|
11
11
|
#
|
12
|
-
# Savon::Client is the main object for connecting to a SOAP service.
|
13
|
-
# both the Savon::WSDL::Document and HTTPI::Request object.
|
12
|
+
# Savon::Client is the main object for connecting to a SOAP service.
|
14
13
|
class Client
|
15
14
|
|
16
15
|
# Initializes the Savon::Client for a SOAP service. Accepts a +block+ which is evaluated in the
|
@@ -19,13 +18,10 @@ module Savon
|
|
19
18
|
# == Examples
|
20
19
|
#
|
21
20
|
# # Using a remote WSDL
|
22
|
-
# client = Savon::Client.new
|
21
|
+
# client = Savon::Client.new("http://example.com/UserService?wsdl")
|
23
22
|
#
|
24
23
|
# # Using a local WSDL
|
25
|
-
# client = Savon::Client.new
|
26
|
-
#
|
27
|
-
# # Shortcut for setting the WSDL
|
28
|
-
# client = Savon::Client.new "http://example.com/UserService?wsdl"
|
24
|
+
# client = Savon::Client.new File.expand_path("../wsdl/service.xml", __FILE__)
|
29
25
|
#
|
30
26
|
# # Directly accessing a SOAP endpoint
|
31
27
|
# client = Savon::Client.new do
|
@@ -38,9 +34,9 @@ module Savon
|
|
38
34
|
wsdl.request = http
|
39
35
|
end
|
40
36
|
|
41
|
-
# Returns the <tt>Savon::
|
37
|
+
# Returns the <tt>Savon::Wasabi::Document</tt>.
|
42
38
|
def wsdl
|
43
|
-
@wsdl ||=
|
39
|
+
@wsdl ||= Wasabi::Document.new
|
44
40
|
end
|
45
41
|
|
46
42
|
# Returns the <tt>HTTPI::Request</tt>.
|
@@ -112,7 +108,7 @@ module Savon
|
|
112
108
|
soap.endpoint = wsdl.endpoint
|
113
109
|
soap.namespace_identifier = options[0]
|
114
110
|
soap.namespace = wsdl.namespace
|
115
|
-
soap.element_form_default = wsdl.element_form_default if wsdl.
|
111
|
+
soap.element_form_default = wsdl.element_form_default if wsdl.document?
|
116
112
|
soap.body = options[2].delete(:body)
|
117
113
|
|
118
114
|
set_soap_action options[1]
|
@@ -121,16 +117,16 @@ module Savon
|
|
121
117
|
|
122
118
|
# Expects an +input+ and sets the +SOAPAction+ HTTP headers.
|
123
119
|
def set_soap_action(input)
|
124
|
-
soap_action = wsdl.soap_action
|
120
|
+
soap_action = wsdl.soap_action(input.to_sym) if wsdl.document?
|
125
121
|
soap_action ||= Gyoku::XMLKey.create(input).to_sym
|
126
122
|
http.headers["SOAPAction"] = %{"#{soap_action}"}
|
127
123
|
end
|
128
124
|
|
129
125
|
# Expects a +namespace+, +input+ and +attributes+ and sets the SOAP input.
|
130
126
|
def set_soap_input(namespace, input, attributes)
|
131
|
-
new_input = wsdl.soap_input
|
132
|
-
new_input ||= Gyoku::XMLKey.create(input)
|
133
|
-
soap.input = [namespace, new_input, attributes].compact
|
127
|
+
new_input = wsdl.soap_input(input.to_sym) if wsdl.document?
|
128
|
+
new_input ||= Gyoku::XMLKey.create(input)
|
129
|
+
soap.input = [namespace, new_input.to_sym, attributes].compact
|
134
130
|
end
|
135
131
|
|
136
132
|
# Processes a given +block+. Yields objects if the block expects any arguments.
|
data/lib/savon/version.rb
CHANGED
@@ -0,0 +1,41 @@
|
|
1
|
+
require "wasabi"
|
2
|
+
require "httpi/request"
|
3
|
+
|
4
|
+
module Savon
|
5
|
+
module Wasabi
|
6
|
+
|
7
|
+
# = Savon::Wasabi::Document
|
8
|
+
#
|
9
|
+
# Extends the <tt>Wasabi::Document</tt> to extend its document handling by
|
10
|
+
# adding support for remote and local WSDL documents.
|
11
|
+
class Document < ::Wasabi::Document
|
12
|
+
|
13
|
+
# Hooks into Wasabi and extends its document handling.
|
14
|
+
def xml
|
15
|
+
@xml ||= document.kind_of?(String) ? resolve_document : document
|
16
|
+
end
|
17
|
+
|
18
|
+
# Sets up and returns the <tt>HTTPI::Request</tt>.
|
19
|
+
def request
|
20
|
+
@request ||= HTTPI::Request.new
|
21
|
+
@request.url = document
|
22
|
+
@request
|
23
|
+
end
|
24
|
+
|
25
|
+
# Sets the <tt>HTTPI::Request</tt> for remote WSDL documents.
|
26
|
+
attr_writer :request
|
27
|
+
|
28
|
+
private
|
29
|
+
|
30
|
+
# Resolves and returns the raw WSDL document.
|
31
|
+
def resolve_document
|
32
|
+
case document
|
33
|
+
when /^http[s]?:/ then HTTPI.get(request).body
|
34
|
+
when /^</ then document
|
35
|
+
else File.read(document)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
data/savon.gemspec
CHANGED
@@ -17,6 +17,7 @@ Gem::Specification.new do |s|
|
|
17
17
|
s.add_dependency "builder", ">= 2.1.2"
|
18
18
|
s.add_dependency "nori", "~> 1.0"
|
19
19
|
s.add_dependency "httpi", "~> 0.9"
|
20
|
+
s.add_dependency "wasabi", "~> 1.0"
|
20
21
|
s.add_dependency "gyoku", ">= 0.4.0"
|
21
22
|
s.add_dependency "nokogiri", ">= 1.4.0"
|
22
23
|
|
data/spec/savon/client_spec.rb
CHANGED
@@ -7,21 +7,21 @@ describe Savon::Client do
|
|
7
7
|
context "with a String" do
|
8
8
|
it "should set the WSDL document" do
|
9
9
|
wsdl = "http://example.com/UserService?wsdl"
|
10
|
-
client = Savon::Client.new
|
10
|
+
client = Savon::Client.new(wsdl)
|
11
11
|
client.wsdl.instance_variable_get("@document").should == wsdl
|
12
12
|
end
|
13
13
|
end
|
14
14
|
|
15
15
|
context "with a block expecting one argument" do
|
16
16
|
it "should yield the WSDL object" do
|
17
|
-
Savon::Client.new { |wsdl| wsdl.should be_a(Savon::
|
17
|
+
Savon::Client.new { |wsdl| wsdl.should be_a(Savon::Wasabi::Document) }
|
18
18
|
end
|
19
19
|
end
|
20
20
|
|
21
21
|
context "with a block expecting two arguments" do
|
22
22
|
it "should yield the WSDL and HTTP objects" do
|
23
23
|
Savon::Client.new do |wsdl, http|
|
24
|
-
wsdl.should be_an(Savon::
|
24
|
+
wsdl.should be_an(Savon::Wasabi::Document)
|
25
25
|
http.should be_an(HTTPI::Request)
|
26
26
|
end
|
27
27
|
end
|
@@ -30,7 +30,7 @@ describe Savon::Client do
|
|
30
30
|
context "with a block expecting three arguments" do
|
31
31
|
it "should yield the WSDL, HTTP and WSSE objects" do
|
32
32
|
Savon::Client.new do |wsdl, http, wsse|
|
33
|
-
wsdl.should be_an(Savon::
|
33
|
+
wsdl.should be_an(Savon::Wasabi::Document)
|
34
34
|
http.should be_an(HTTPI::Request)
|
35
35
|
wsse.should be_an(Savon::WSSE)
|
36
36
|
end
|
@@ -39,7 +39,7 @@ describe Savon::Client do
|
|
39
39
|
|
40
40
|
context "with a block expecting no arguments" do
|
41
41
|
it "should let you access the WSDL object" do
|
42
|
-
Savon::Client.new { wsdl.should be_a(Savon::
|
42
|
+
Savon::Client.new { wsdl.should be_a(Savon::Wasabi::Document) }
|
43
43
|
end
|
44
44
|
|
45
45
|
it "should let you access the HTTP object" do
|
@@ -53,8 +53,8 @@ describe Savon::Client do
|
|
53
53
|
end
|
54
54
|
|
55
55
|
describe "#wsdl" do
|
56
|
-
it "should return the Savon::
|
57
|
-
client.wsdl.should be_a(Savon::
|
56
|
+
it "should return the Savon::Wasabi::Document" do
|
57
|
+
client.wsdl.should be_a(Savon::Wasabi::Document)
|
58
58
|
end
|
59
59
|
end
|
60
60
|
|
@@ -150,7 +150,7 @@ describe Savon::Client do
|
|
150
150
|
it "should yield the SOAP and WSDL objects" do
|
151
151
|
client.request(:authenticate) do |soap, wsdl|
|
152
152
|
soap.should be_a(Savon::SOAP::XML)
|
153
|
-
wsdl.should be_an(Savon::
|
153
|
+
wsdl.should be_an(Savon::Wasabi::Document)
|
154
154
|
end
|
155
155
|
end
|
156
156
|
end
|
@@ -159,7 +159,7 @@ describe Savon::Client do
|
|
159
159
|
it "should yield the SOAP, WSDL and HTTP objects" do
|
160
160
|
client.request(:authenticate) do |soap, wsdl, http|
|
161
161
|
soap.should be_a(Savon::SOAP::XML)
|
162
|
-
wsdl.should be_an(Savon::
|
162
|
+
wsdl.should be_an(Savon::Wasabi::Document)
|
163
163
|
http.should be_an(HTTPI::Request)
|
164
164
|
end
|
165
165
|
end
|
@@ -169,7 +169,7 @@ describe Savon::Client do
|
|
169
169
|
it "should yield the SOAP, WSDL, HTTP and WSSE objects" do
|
170
170
|
client.request(:authenticate) do |soap, wsdl, http, wsse|
|
171
171
|
soap.should be_a(Savon::SOAP::XML)
|
172
|
-
wsdl.should be_a(Savon::
|
172
|
+
wsdl.should be_a(Savon::Wasabi::Document)
|
173
173
|
http.should be_an(HTTPI::Request)
|
174
174
|
wsse.should be_a(Savon::WSSE)
|
175
175
|
end
|
@@ -190,7 +190,7 @@ describe Savon::Client do
|
|
190
190
|
end
|
191
191
|
|
192
192
|
it "should let you access the WSDL object" do
|
193
|
-
client.request(:authenticate) { wsdl.should be_a(Savon::
|
193
|
+
client.request(:authenticate) { wsdl.should be_a(Savon::Wasabi::Document) }
|
194
194
|
end
|
195
195
|
end
|
196
196
|
|
@@ -262,7 +262,7 @@ describe Savon::Client do
|
|
262
262
|
|
263
263
|
it "should get #element_form_default from the WSDL" do
|
264
264
|
HTTPI.stubs(:post).returns(new_response)
|
265
|
-
Savon::
|
265
|
+
Savon::Wasabi::Document.any_instance.expects(:element_form_default).returns(:qualified)
|
266
266
|
|
267
267
|
client.request :authenticate
|
268
268
|
end
|
@@ -287,7 +287,7 @@ describe Savon::Client do
|
|
287
287
|
before { HTTPI.expects(:get).never }
|
288
288
|
|
289
289
|
it "raise an ArgumentError when trying to access the WSDL" do
|
290
|
-
lambda { client.wsdl.soap_actions }.should raise_error(ArgumentError)
|
290
|
+
lambda { client.wsdl.soap_actions }.should raise_error(ArgumentError, /Wasabi/)
|
291
291
|
end
|
292
292
|
|
293
293
|
it "adds a SOAPAction header containing the SOAP action name" do
|
@@ -300,7 +300,7 @@ describe Savon::Client do
|
|
300
300
|
|
301
301
|
it "should not get #element_form_default from the WSDL" do
|
302
302
|
HTTPI.stubs(:post).returns(new_response)
|
303
|
-
Savon::
|
303
|
+
Savon::Wasabi::Document.any_instance.expects(:element_form_default).never
|
304
304
|
|
305
305
|
client.request :authenticate
|
306
306
|
end
|
@@ -0,0 +1,45 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Savon::Wasabi::Document do
|
4
|
+
|
5
|
+
context "with a remote document" do
|
6
|
+
before do
|
7
|
+
response = HTTPI::Response.new 200, {}, Fixture.wsdl(:authentication)
|
8
|
+
HTTPI.stubs(:get).returns(response)
|
9
|
+
end
|
10
|
+
|
11
|
+
it "should resolve via HTTP" do
|
12
|
+
wsdl = Savon::Wasabi::Document.new("http://example.com?wsdl")
|
13
|
+
wsdl.xml.should == Fixture.wsdl(:authentication)
|
14
|
+
end
|
15
|
+
|
16
|
+
it "should resolve via HTTPS" do
|
17
|
+
wsdl = Savon::Wasabi::Document.new("https://example.com?wsdl")
|
18
|
+
wsdl.xml.should == Fixture.wsdl(:authentication)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
context "with a local document" do
|
23
|
+
before do
|
24
|
+
HTTPI.expects(:get).never
|
25
|
+
end
|
26
|
+
|
27
|
+
it "should read the file" do
|
28
|
+
wsdl = Savon::Wasabi::Document.new("spec/fixtures/wsdl/authentication.xml")
|
29
|
+
wsdl.xml.should == Fixture.wsdl(:authentication)
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
context "with raw XML" do
|
34
|
+
before do
|
35
|
+
HTTPI.expects(:get).never
|
36
|
+
File.expects(:read).never
|
37
|
+
end
|
38
|
+
|
39
|
+
it "should use the raw XML" do
|
40
|
+
wsdl = Savon::Wasabi::Document.new Fixture.wsdl(:authentication)
|
41
|
+
wsdl.xml.should == Fixture.wsdl(:authentication)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
end
|
metadata
CHANGED
@@ -1,8 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: savon
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
+
hash: 51
|
4
5
|
prerelease:
|
5
|
-
|
6
|
+
segments:
|
7
|
+
- 0
|
8
|
+
- 9
|
9
|
+
- 4
|
10
|
+
version: 0.9.4
|
6
11
|
platform: ruby
|
7
12
|
authors:
|
8
13
|
- Daniel Harrington
|
@@ -10,7 +15,7 @@ autorequire:
|
|
10
15
|
bindir: bin
|
11
16
|
cert_chain: []
|
12
17
|
|
13
|
-
date: 2011-
|
18
|
+
date: 2011-07-03 00:00:00 Z
|
14
19
|
dependencies:
|
15
20
|
- !ruby/object:Gem::Dependency
|
16
21
|
name: builder
|
@@ -20,6 +25,11 @@ dependencies:
|
|
20
25
|
requirements:
|
21
26
|
- - ">="
|
22
27
|
- !ruby/object:Gem::Version
|
28
|
+
hash: 15
|
29
|
+
segments:
|
30
|
+
- 2
|
31
|
+
- 1
|
32
|
+
- 2
|
23
33
|
version: 2.1.2
|
24
34
|
type: :runtime
|
25
35
|
version_requirements: *id001
|
@@ -31,6 +41,10 @@ dependencies:
|
|
31
41
|
requirements:
|
32
42
|
- - ~>
|
33
43
|
- !ruby/object:Gem::Version
|
44
|
+
hash: 15
|
45
|
+
segments:
|
46
|
+
- 1
|
47
|
+
- 0
|
34
48
|
version: "1.0"
|
35
49
|
type: :runtime
|
36
50
|
version_requirements: *id002
|
@@ -42,86 +56,138 @@ dependencies:
|
|
42
56
|
requirements:
|
43
57
|
- - ~>
|
44
58
|
- !ruby/object:Gem::Version
|
59
|
+
hash: 25
|
60
|
+
segments:
|
61
|
+
- 0
|
62
|
+
- 9
|
45
63
|
version: "0.9"
|
46
64
|
type: :runtime
|
47
65
|
version_requirements: *id003
|
48
66
|
- !ruby/object:Gem::Dependency
|
49
|
-
name:
|
67
|
+
name: wasabi
|
50
68
|
prerelease: false
|
51
69
|
requirement: &id004 !ruby/object:Gem::Requirement
|
70
|
+
none: false
|
71
|
+
requirements:
|
72
|
+
- - ~>
|
73
|
+
- !ruby/object:Gem::Version
|
74
|
+
hash: 15
|
75
|
+
segments:
|
76
|
+
- 1
|
77
|
+
- 0
|
78
|
+
version: "1.0"
|
79
|
+
type: :runtime
|
80
|
+
version_requirements: *id004
|
81
|
+
- !ruby/object:Gem::Dependency
|
82
|
+
name: gyoku
|
83
|
+
prerelease: false
|
84
|
+
requirement: &id005 !ruby/object:Gem::Requirement
|
52
85
|
none: false
|
53
86
|
requirements:
|
54
87
|
- - ">="
|
55
88
|
- !ruby/object:Gem::Version
|
89
|
+
hash: 15
|
90
|
+
segments:
|
91
|
+
- 0
|
92
|
+
- 4
|
93
|
+
- 0
|
56
94
|
version: 0.4.0
|
57
95
|
type: :runtime
|
58
|
-
version_requirements: *
|
96
|
+
version_requirements: *id005
|
59
97
|
- !ruby/object:Gem::Dependency
|
60
98
|
name: nokogiri
|
61
99
|
prerelease: false
|
62
|
-
requirement: &
|
100
|
+
requirement: &id006 !ruby/object:Gem::Requirement
|
63
101
|
none: false
|
64
102
|
requirements:
|
65
103
|
- - ">="
|
66
104
|
- !ruby/object:Gem::Version
|
105
|
+
hash: 7
|
106
|
+
segments:
|
107
|
+
- 1
|
108
|
+
- 4
|
109
|
+
- 0
|
67
110
|
version: 1.4.0
|
68
111
|
type: :runtime
|
69
|
-
version_requirements: *
|
112
|
+
version_requirements: *id006
|
70
113
|
- !ruby/object:Gem::Dependency
|
71
114
|
name: rake
|
72
115
|
prerelease: false
|
73
|
-
requirement: &
|
116
|
+
requirement: &id007 !ruby/object:Gem::Requirement
|
74
117
|
none: false
|
75
118
|
requirements:
|
76
119
|
- - ~>
|
77
120
|
- !ruby/object:Gem::Version
|
121
|
+
hash: 49
|
122
|
+
segments:
|
123
|
+
- 0
|
124
|
+
- 8
|
125
|
+
- 7
|
78
126
|
version: 0.8.7
|
79
127
|
type: :development
|
80
|
-
version_requirements: *
|
128
|
+
version_requirements: *id007
|
81
129
|
- !ruby/object:Gem::Dependency
|
82
130
|
name: rspec
|
83
131
|
prerelease: false
|
84
|
-
requirement: &
|
132
|
+
requirement: &id008 !ruby/object:Gem::Requirement
|
85
133
|
none: false
|
86
134
|
requirements:
|
87
135
|
- - ~>
|
88
136
|
- !ruby/object:Gem::Version
|
137
|
+
hash: 27
|
138
|
+
segments:
|
139
|
+
- 2
|
140
|
+
- 5
|
141
|
+
- 0
|
89
142
|
version: 2.5.0
|
90
143
|
type: :development
|
91
|
-
version_requirements: *
|
144
|
+
version_requirements: *id008
|
92
145
|
- !ruby/object:Gem::Dependency
|
93
146
|
name: mocha
|
94
147
|
prerelease: false
|
95
|
-
requirement: &
|
148
|
+
requirement: &id009 !ruby/object:Gem::Requirement
|
96
149
|
none: false
|
97
150
|
requirements:
|
98
151
|
- - ~>
|
99
152
|
- !ruby/object:Gem::Version
|
153
|
+
hash: 43
|
154
|
+
segments:
|
155
|
+
- 0
|
156
|
+
- 9
|
157
|
+
- 8
|
100
158
|
version: 0.9.8
|
101
159
|
type: :development
|
102
|
-
version_requirements: *
|
160
|
+
version_requirements: *id009
|
103
161
|
- !ruby/object:Gem::Dependency
|
104
162
|
name: timecop
|
105
163
|
prerelease: false
|
106
|
-
requirement: &
|
164
|
+
requirement: &id010 !ruby/object:Gem::Requirement
|
107
165
|
none: false
|
108
166
|
requirements:
|
109
167
|
- - ~>
|
110
168
|
- !ruby/object:Gem::Version
|
169
|
+
hash: 25
|
170
|
+
segments:
|
171
|
+
- 0
|
172
|
+
- 3
|
173
|
+
- 5
|
111
174
|
version: 0.3.5
|
112
175
|
type: :development
|
113
|
-
version_requirements: *
|
176
|
+
version_requirements: *id010
|
114
177
|
- !ruby/object:Gem::Dependency
|
115
178
|
name: autotest
|
116
179
|
prerelease: false
|
117
|
-
requirement: &
|
180
|
+
requirement: &id011 !ruby/object:Gem::Requirement
|
118
181
|
none: false
|
119
182
|
requirements:
|
120
183
|
- - ">="
|
121
184
|
- !ruby/object:Gem::Version
|
185
|
+
hash: 3
|
186
|
+
segments:
|
187
|
+
- 0
|
122
188
|
version: "0"
|
123
189
|
type: :development
|
124
|
-
version_requirements: *
|
190
|
+
version_requirements: *id011
|
125
191
|
description: Ruby's heavy metal SOAP client
|
126
192
|
email: me@rubiii.com
|
127
193
|
executables: []
|
@@ -154,9 +220,7 @@ files:
|
|
154
220
|
- lib/savon/soap/response.rb
|
155
221
|
- lib/savon/soap/xml.rb
|
156
222
|
- lib/savon/version.rb
|
157
|
-
- lib/savon/
|
158
|
-
- lib/savon/wsdl/parser.rb
|
159
|
-
- lib/savon/wsdl/request.rb
|
223
|
+
- lib/savon/wasabi/document.rb
|
160
224
|
- lib/savon/wsse.rb
|
161
225
|
- savon.gemspec
|
162
226
|
- spec/fixtures/gzip/message.gz
|
@@ -184,9 +248,7 @@ files:
|
|
184
248
|
- spec/savon/soap/response_spec.rb
|
185
249
|
- spec/savon/soap/xml_spec.rb
|
186
250
|
- spec/savon/soap_spec.rb
|
187
|
-
- spec/savon/
|
188
|
-
- spec/savon/wsdl/parser_spec.rb
|
189
|
-
- spec/savon/wsdl/request_spec.rb
|
251
|
+
- spec/savon/wasabi/document_spec.rb
|
190
252
|
- spec/savon/wsse_spec.rb
|
191
253
|
- spec/spec_helper.rb
|
192
254
|
- spec/support/endpoint.rb
|
@@ -204,17 +266,23 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
204
266
|
requirements:
|
205
267
|
- - ">="
|
206
268
|
- !ruby/object:Gem::Version
|
269
|
+
hash: 3
|
270
|
+
segments:
|
271
|
+
- 0
|
207
272
|
version: "0"
|
208
273
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
209
274
|
none: false
|
210
275
|
requirements:
|
211
276
|
- - ">="
|
212
277
|
- !ruby/object:Gem::Version
|
278
|
+
hash: 3
|
279
|
+
segments:
|
280
|
+
- 0
|
213
281
|
version: "0"
|
214
282
|
requirements: []
|
215
283
|
|
216
284
|
rubyforge_project: savon
|
217
|
-
rubygems_version: 1.8.
|
285
|
+
rubygems_version: 1.8.5
|
218
286
|
signing_key:
|
219
287
|
specification_version: 3
|
220
288
|
summary: Heavy metal Ruby SOAP client
|
data/lib/savon/wsdl/document.rb
DELETED
@@ -1,112 +0,0 @@
|
|
1
|
-
require "nokogiri"
|
2
|
-
|
3
|
-
require "savon/wsdl/request"
|
4
|
-
require "savon/wsdl/parser"
|
5
|
-
|
6
|
-
module Savon
|
7
|
-
module WSDL
|
8
|
-
|
9
|
-
# = Savon::WSDL::Document
|
10
|
-
#
|
11
|
-
# Represents the WSDL of your service, including information like the namespace URI,
|
12
|
-
# the SOAP endpoint and available SOAP actions.
|
13
|
-
class Document
|
14
|
-
|
15
|
-
# Accepts an <tt>HTTPI::Request</tt> and a +document+.
|
16
|
-
def initialize(request = nil, document = nil)
|
17
|
-
self.request = request
|
18
|
-
self.document = document
|
19
|
-
end
|
20
|
-
|
21
|
-
# Accessor for the <tt>HTTPI::Request</tt> to use.
|
22
|
-
attr_accessor :request
|
23
|
-
|
24
|
-
def present?
|
25
|
-
!!@document
|
26
|
-
end
|
27
|
-
|
28
|
-
# Returns the namespace URI of the WSDL.
|
29
|
-
def namespace
|
30
|
-
@namespace ||= parser.namespace
|
31
|
-
end
|
32
|
-
|
33
|
-
# Sets the SOAP namespace.
|
34
|
-
attr_writer :namespace
|
35
|
-
|
36
|
-
# Returns the SOAP endpoint.
|
37
|
-
def endpoint
|
38
|
-
@endpoint ||= parser.endpoint
|
39
|
-
end
|
40
|
-
|
41
|
-
# Sets the SOAP endpoint.
|
42
|
-
attr_writer :endpoint
|
43
|
-
|
44
|
-
# Returns an Array of available SOAP actions.
|
45
|
-
def soap_actions
|
46
|
-
@soap_actions ||= parser.operations.keys
|
47
|
-
end
|
48
|
-
|
49
|
-
# Returns the SOAP action for a given +key+.
|
50
|
-
def soap_action(key)
|
51
|
-
operations[key][:action] if present? && operations[key]
|
52
|
-
end
|
53
|
-
|
54
|
-
# Returns the SOAP input for a given +key+.
|
55
|
-
def soap_input(key)
|
56
|
-
operations[key][:input].to_sym if present? && operations[key]
|
57
|
-
end
|
58
|
-
|
59
|
-
# Returns a Hash of SOAP operations.
|
60
|
-
def operations
|
61
|
-
@operations ||= parser.operations
|
62
|
-
end
|
63
|
-
|
64
|
-
# Returns the elementFormDefault value.
|
65
|
-
def element_form_default
|
66
|
-
@element_form_default ||= parser.element_form_default
|
67
|
-
end
|
68
|
-
|
69
|
-
# Sets the location of the WSDL document to use. This can either be a URL
|
70
|
-
# or a path to a local file.
|
71
|
-
attr_writer :document
|
72
|
-
|
73
|
-
# Returns the raw WSDL document.
|
74
|
-
def document
|
75
|
-
@wsdl_document ||= begin
|
76
|
-
raise ArgumentError, "No WSDL document given" if @document.blank?
|
77
|
-
remote? ? http_request : read_file
|
78
|
-
end
|
79
|
-
end
|
80
|
-
|
81
|
-
alias :to_xml :document
|
82
|
-
|
83
|
-
private
|
84
|
-
|
85
|
-
# Returns whether the WSDL document is located on the Web.
|
86
|
-
def remote?
|
87
|
-
@document =~ /^http/
|
88
|
-
end
|
89
|
-
|
90
|
-
# Executes an HTTP GET request to retrieve a remote WSDL document.
|
91
|
-
def http_request
|
92
|
-
request.url = @document
|
93
|
-
Request.execute(request).body
|
94
|
-
end
|
95
|
-
|
96
|
-
# Reads the WSDL document from a local file.
|
97
|
-
def read_file
|
98
|
-
File.read @document
|
99
|
-
end
|
100
|
-
|
101
|
-
# Parses the WSDL document and returns the <tt>Savon::WSDL::Parser</tt>.
|
102
|
-
def parser
|
103
|
-
@parser ||= begin
|
104
|
-
parser = Parser.new(Nokogiri::XML(document))
|
105
|
-
parser.parse
|
106
|
-
parser
|
107
|
-
end
|
108
|
-
end
|
109
|
-
|
110
|
-
end
|
111
|
-
end
|
112
|
-
end
|
data/lib/savon/wsdl/parser.rb
DELETED
@@ -1,96 +0,0 @@
|
|
1
|
-
require "savon/core_ext/object"
|
2
|
-
require "savon/core_ext/string"
|
3
|
-
|
4
|
-
module Savon
|
5
|
-
module WSDL
|
6
|
-
|
7
|
-
# = Savon::WSDL::Parser
|
8
|
-
#
|
9
|
-
# Parses WSDL documents and remembers the parts of them we care about.
|
10
|
-
class Parser
|
11
|
-
|
12
|
-
# The main sections of a WSDL document.
|
13
|
-
Sections = %w(definitions types message portType binding service)
|
14
|
-
|
15
|
-
def initialize(nokogiri_document)
|
16
|
-
@document = nokogiri_document
|
17
|
-
@path = []
|
18
|
-
@operations = {}
|
19
|
-
@namespaces = {}
|
20
|
-
@element_form_default = :unqualified
|
21
|
-
end
|
22
|
-
|
23
|
-
# Returns the namespace URI.
|
24
|
-
attr_reader :namespace
|
25
|
-
|
26
|
-
# Returns the SOAP operations.
|
27
|
-
attr_reader :operations
|
28
|
-
|
29
|
-
# Returns the SOAP endpoint.
|
30
|
-
attr_reader :endpoint
|
31
|
-
|
32
|
-
# Returns the elementFormDefault value.
|
33
|
-
attr_reader :element_form_default
|
34
|
-
|
35
|
-
def parse
|
36
|
-
parse_namespaces
|
37
|
-
parse_endpoint
|
38
|
-
parse_operations
|
39
|
-
end
|
40
|
-
|
41
|
-
def parse_namespaces
|
42
|
-
element_form_default = @document.at_xpath(
|
43
|
-
"s0:definitions/s0:types/xs:schema/@elementFormDefault",
|
44
|
-
"s0" => "http://schemas.xmlsoap.org/wsdl/",
|
45
|
-
"xs" => "http://www.w3.org/2001/XMLSchema")
|
46
|
-
@element_form_default = element_form_default.to_s.to_sym if element_form_default
|
47
|
-
|
48
|
-
namespace = @document.at_xpath(
|
49
|
-
"s0:definitions/@targetNamespace",
|
50
|
-
"s0" => "http://schemas.xmlsoap.org/wsdl/")
|
51
|
-
@namespace = namespace.to_s if namespace
|
52
|
-
end
|
53
|
-
|
54
|
-
def parse_endpoint
|
55
|
-
endpoint = @document.at_xpath(
|
56
|
-
"s0:definitions/s0:service//soap11:address/@location",
|
57
|
-
"s0" => "http://schemas.xmlsoap.org/wsdl/",
|
58
|
-
"soap11" => "http://schemas.xmlsoap.org/wsdl/soap/")
|
59
|
-
endpoint ||= @document.at_xpath(
|
60
|
-
"s0:definitions/s0:service//soap12:address/@location",
|
61
|
-
"s0" => "http://schemas.xmlsoap.org/wsdl/",
|
62
|
-
"soap12" => "http://schemas.xmlsoap.org/wsdl/soap12/")
|
63
|
-
@endpoint = URI(URI.escape(endpoint.to_s)) if endpoint
|
64
|
-
end
|
65
|
-
|
66
|
-
def parse_operations
|
67
|
-
operations = @document.xpath(
|
68
|
-
"s0:definitions/s0:binding/s0:operation",
|
69
|
-
"s0" => "http://schemas.xmlsoap.org/wsdl/")
|
70
|
-
operations.each do |operation|
|
71
|
-
name = operation.attribute("name").to_s
|
72
|
-
|
73
|
-
soap_action = operation.at_xpath(".//soap11:operation/@soapAction",
|
74
|
-
"soap11" => "http://schemas.xmlsoap.org/wsdl/soap/"
|
75
|
-
)
|
76
|
-
soap_action ||= operation.at_xpath(".//soap12:operation/@soapAction",
|
77
|
-
"soap12" => "http://schemas.xmlsoap.org/wsdl/soap12/"
|
78
|
-
)
|
79
|
-
if soap_action
|
80
|
-
soap_action = soap_action.to_s
|
81
|
-
|
82
|
-
action = !soap_action.blank? ? soap_action : name
|
83
|
-
input = (!name || name.empty?) ? action.split("/").last : name
|
84
|
-
|
85
|
-
@operations[input.snakecase.to_sym] =
|
86
|
-
{ :action => action, :input => input }
|
87
|
-
elsif !@operations[name.snakecase.to_sym]
|
88
|
-
@operations[name.snakecase.to_sym] =
|
89
|
-
{ :action => name, :input => name }
|
90
|
-
end
|
91
|
-
end
|
92
|
-
end
|
93
|
-
|
94
|
-
end
|
95
|
-
end
|
96
|
-
end
|
data/lib/savon/wsdl/request.rb
DELETED
@@ -1,41 +0,0 @@
|
|
1
|
-
require "httpi"
|
2
|
-
|
3
|
-
module Savon
|
4
|
-
module WSDL
|
5
|
-
|
6
|
-
# = Savon::WSDL::Request
|
7
|
-
#
|
8
|
-
# Executes WSDL requests.
|
9
|
-
class Request
|
10
|
-
|
11
|
-
# Expects an <tt>HTTPI::Request</tt> to execute a WSDL request
|
12
|
-
# and returns the response.
|
13
|
-
def self.execute(request)
|
14
|
-
new(request).response
|
15
|
-
end
|
16
|
-
|
17
|
-
# Expects an <tt>HTTPI::Request</tt>.
|
18
|
-
def initialize(request)
|
19
|
-
self.request = request
|
20
|
-
end
|
21
|
-
|
22
|
-
# Accessor for the <tt>HTTPI::Request</tt>.
|
23
|
-
attr_accessor :request
|
24
|
-
|
25
|
-
# Executes the request and returns the response.
|
26
|
-
def response
|
27
|
-
@response ||= with_logging { HTTPI.get request }
|
28
|
-
end
|
29
|
-
|
30
|
-
private
|
31
|
-
|
32
|
-
# Logs the HTTP request and yields to a given +block+.
|
33
|
-
def with_logging
|
34
|
-
Savon.log "Retrieving WSDL from: #{request.url}"
|
35
|
-
Savon.log "Using :#{request.auth.type} authentication" if request.auth?
|
36
|
-
yield
|
37
|
-
end
|
38
|
-
|
39
|
-
end
|
40
|
-
end
|
41
|
-
end
|
@@ -1,132 +0,0 @@
|
|
1
|
-
require "spec_helper"
|
2
|
-
|
3
|
-
describe Savon::WSDL::Document do
|
4
|
-
|
5
|
-
shared_examples_for "a WSDL document" do
|
6
|
-
it "should be present" do
|
7
|
-
wsdl.should be_present
|
8
|
-
end
|
9
|
-
|
10
|
-
describe "#namespace" do
|
11
|
-
it "should return the namespace URI" do
|
12
|
-
wsdl.namespace.should == "http://v1_0.ws.auth.order.example.com/"
|
13
|
-
end
|
14
|
-
end
|
15
|
-
|
16
|
-
describe "#soap_actions" do
|
17
|
-
it "should return an Array of available SOAP actions" do
|
18
|
-
wsdl.soap_actions.should == [:authenticate]
|
19
|
-
end
|
20
|
-
end
|
21
|
-
|
22
|
-
describe "#soap_action" do
|
23
|
-
it "should return the SOAP action for a given key" do
|
24
|
-
wsdl.soap_action(:authenticate).should == "authenticate"
|
25
|
-
end
|
26
|
-
|
27
|
-
it "should return nil if no SOAP action could be found" do
|
28
|
-
wsdl.soap_action(:unknown).should be_nil
|
29
|
-
end
|
30
|
-
end
|
31
|
-
|
32
|
-
describe "#soap_input" do
|
33
|
-
it "should return the SOAP input tag for a given key" do
|
34
|
-
wsdl.soap_input(:authenticate).should == :authenticate
|
35
|
-
end
|
36
|
-
|
37
|
-
it "should return nil if no SOAP input tag could be found" do
|
38
|
-
wsdl.soap_input(:unknown).should be_nil
|
39
|
-
end
|
40
|
-
end
|
41
|
-
|
42
|
-
describe "#operations" do
|
43
|
-
it "should return a Hash of SOAP operations" do
|
44
|
-
wsdl.operations.should == {
|
45
|
-
:authenticate => {
|
46
|
-
:input => "authenticate", :action => "authenticate"
|
47
|
-
}
|
48
|
-
}
|
49
|
-
end
|
50
|
-
end
|
51
|
-
|
52
|
-
describe "#document" do
|
53
|
-
it "should return the raw WSDL document" do
|
54
|
-
wsdl.document.should == Fixture.wsdl(:authentication)
|
55
|
-
end
|
56
|
-
|
57
|
-
it "should be memoized" do
|
58
|
-
wsdl.document.should equal(wsdl.document)
|
59
|
-
end
|
60
|
-
end
|
61
|
-
end
|
62
|
-
|
63
|
-
context "with a remote document" do
|
64
|
-
let(:wsdl) { Savon::WSDL::Document.new HTTPI::Request.new, Endpoint.wsdl }
|
65
|
-
|
66
|
-
before do
|
67
|
-
response = HTTPI::Response.new 200, {}, Fixture.wsdl(:authentication)
|
68
|
-
HTTPI.stubs(:get).returns(response)
|
69
|
-
end
|
70
|
-
|
71
|
-
it_should_behave_like "a WSDL document"
|
72
|
-
|
73
|
-
describe "#element_form_default" do
|
74
|
-
it "should return :unqualified" do
|
75
|
-
wsdl.element_form_default.should == :unqualified
|
76
|
-
end
|
77
|
-
end
|
78
|
-
end
|
79
|
-
|
80
|
-
context "with a local document" do
|
81
|
-
let(:wsdl) do
|
82
|
-
wsdl = "spec/fixtures/wsdl/authentication.xml"
|
83
|
-
Savon::WSDL::Document.new HTTPI::Request.new, wsdl
|
84
|
-
end
|
85
|
-
|
86
|
-
before { HTTPI.expects(:get).never }
|
87
|
-
|
88
|
-
it_should_behave_like "a WSDL document"
|
89
|
-
end
|
90
|
-
|
91
|
-
context "without a WSDL document" do
|
92
|
-
let(:wsdl) { Savon::WSDL::Document.new HTTPI::Request.new }
|
93
|
-
|
94
|
-
it "should not be present" do
|
95
|
-
wsdl.should_not be_present
|
96
|
-
end
|
97
|
-
|
98
|
-
describe "#soap_action" do
|
99
|
-
it "should return nil" do
|
100
|
-
wsdl.soap_action(:authenticate).should be_nil
|
101
|
-
end
|
102
|
-
end
|
103
|
-
|
104
|
-
describe "#soap_input" do
|
105
|
-
it "should return nil" do
|
106
|
-
wsdl.soap_input(:authenticate).should be_nil
|
107
|
-
end
|
108
|
-
end
|
109
|
-
|
110
|
-
describe "#document" do
|
111
|
-
it "should raise an ArgumentError" do
|
112
|
-
lambda { wsdl.document }.should raise_error(ArgumentError)
|
113
|
-
end
|
114
|
-
end
|
115
|
-
end
|
116
|
-
|
117
|
-
context "with a WSDL document containing elementFormDefault='qualified'" do
|
118
|
-
let(:wsdl) { Savon::WSDL::Document.new HTTPI::Request.new, Endpoint.wsdl }
|
119
|
-
|
120
|
-
before do
|
121
|
-
response = HTTPI::Response.new 200, {}, Fixture.wsdl(:geotrust)
|
122
|
-
HTTPI.stubs(:get).returns(response)
|
123
|
-
end
|
124
|
-
|
125
|
-
describe "#element_form_default" do
|
126
|
-
it "should return :qualified" do
|
127
|
-
wsdl.element_form_default.should == :qualified
|
128
|
-
end
|
129
|
-
end
|
130
|
-
end
|
131
|
-
|
132
|
-
end
|
@@ -1,107 +0,0 @@
|
|
1
|
-
require "spec_helper"
|
2
|
-
|
3
|
-
describe Savon::WSDL::Parser do
|
4
|
-
|
5
|
-
context "with namespaced_actions.xml" do
|
6
|
-
let(:parser) { new_parser :namespaced_actions }
|
7
|
-
|
8
|
-
it "should return the target namespace" do
|
9
|
-
parser.namespace.should == "http://api.example.com/api/"
|
10
|
-
end
|
11
|
-
|
12
|
-
it "should return the SOAP endpoint" do
|
13
|
-
parser.endpoint.should == URI("https://api.example.com/api/api.asmx")
|
14
|
-
end
|
15
|
-
|
16
|
-
it "should return the available SOAP operations" do
|
17
|
-
parser.operations.should match_operations(
|
18
|
-
:get_api_key => { :input => "GetApiKey", :action => "http://api.example.com/api/User.GetApiKey" },
|
19
|
-
:delete_client => { :input => "DeleteClient", :action => "http://api.example.com/api/Client.Delete" },
|
20
|
-
:get_clients => { :input => "GetClients", :action => "http://api.example.com/api/User.GetClients" }
|
21
|
-
)
|
22
|
-
end
|
23
|
-
|
24
|
-
it "should return that :element_form_default is set to :qualified" do
|
25
|
-
parser.element_form_default.should == :qualified
|
26
|
-
end
|
27
|
-
end
|
28
|
-
|
29
|
-
context "with no_namespace.xml" do
|
30
|
-
let(:parser) { new_parser :no_namespace }
|
31
|
-
|
32
|
-
it "should return the target namespace" do
|
33
|
-
parser.namespace.should == "urn:ActionWebService"
|
34
|
-
end
|
35
|
-
|
36
|
-
it "should return the SOAP endpoint" do
|
37
|
-
parser.endpoint.should == URI("http://example.com/api/api")
|
38
|
-
end
|
39
|
-
|
40
|
-
it "should return the available SOAP operations" do
|
41
|
-
parser.operations.should match_operations(
|
42
|
-
:search_user => { :input => "SearchUser", :action => "/api/api/SearchUser" },
|
43
|
-
:get_user_login_by_id => { :input => "GetUserLoginById", :action => "/api/api/GetUserLoginById" },
|
44
|
-
:get_all_contacts => { :input => "GetAllContacts", :action => "/api/api/GetAllContacts" }
|
45
|
-
)
|
46
|
-
end
|
47
|
-
|
48
|
-
it "should return that :element_form_default is set to :unqualified" do
|
49
|
-
parser.element_form_default.should == :unqualified
|
50
|
-
end
|
51
|
-
end
|
52
|
-
|
53
|
-
context "with geotrust.xml" do
|
54
|
-
let(:parser) { new_parser :geotrust }
|
55
|
-
|
56
|
-
it "should return the target namespace" do
|
57
|
-
parser.namespace.should == "http://api.geotrust.com/webtrust/query"
|
58
|
-
end
|
59
|
-
|
60
|
-
it "should return the SOAP endpoint" do
|
61
|
-
parser.endpoint.should == URI("https://test-api.geotrust.com/webtrust/query.jws")
|
62
|
-
end
|
63
|
-
|
64
|
-
it "should return the available SOAP operations" do
|
65
|
-
parser.operations.should match_operations(
|
66
|
-
:get_quick_approver_list => { :input => "GetQuickApproverList", :action => "GetQuickApproverList" },
|
67
|
-
:hello => { :input => "hello", :action => "hello" }
|
68
|
-
)
|
69
|
-
end
|
70
|
-
|
71
|
-
it "should return that :element_form_default is set to :qualified" do
|
72
|
-
parser.element_form_default.should == :qualified
|
73
|
-
end
|
74
|
-
end
|
75
|
-
|
76
|
-
context "with two_bindings.xml" do
|
77
|
-
let(:parser) { new_parser :two_bindings }
|
78
|
-
|
79
|
-
it "should merge operations from all binding sections (until we have an example where it makes sense to do otherwise)" do
|
80
|
-
parser.operations.keys.map(&:to_s).sort.should ==
|
81
|
-
%w{post post11only post12only}
|
82
|
-
end
|
83
|
-
end
|
84
|
-
|
85
|
-
context "with soap12.xml" do
|
86
|
-
let(:parser) { new_parser :soap12 }
|
87
|
-
|
88
|
-
it "should return the endpoint" do
|
89
|
-
parser.endpoint.should == URI("http://blogsite.example.com/endpoint12")
|
90
|
-
end
|
91
|
-
end
|
92
|
-
|
93
|
-
RSpec::Matchers.define :match_operations do |expected|
|
94
|
-
match do |actual|
|
95
|
-
actual.should have(expected.keys.size).items
|
96
|
-
actual.keys.should include(*expected.keys)
|
97
|
-
actual.each { |key, value| value.should == expected[key] }
|
98
|
-
end
|
99
|
-
end
|
100
|
-
|
101
|
-
def new_parser(fixture)
|
102
|
-
parser = Savon::WSDL::Parser.new(Nokogiri::XML(Fixture[:wsdl, fixture]))
|
103
|
-
parser.parse
|
104
|
-
parser
|
105
|
-
end
|
106
|
-
|
107
|
-
end
|
@@ -1,23 +0,0 @@
|
|
1
|
-
require "spec_helper"
|
2
|
-
|
3
|
-
describe Savon::WSDL::Request do
|
4
|
-
let(:http_request) { HTTPI::Request.new :url => Endpoint.wsdl }
|
5
|
-
let(:request) { Savon::WSDL::Request.new http_request }
|
6
|
-
|
7
|
-
describe ".execute" do
|
8
|
-
it "executes a WSDL request and returns the response" do
|
9
|
-
response = HTTPI::Response.new 200, {}, Fixture.response(:authentication)
|
10
|
-
HTTPI.expects(:get).with(http_request).returns(response)
|
11
|
-
Savon::WSDL::Request.execute(http_request).should == response
|
12
|
-
end
|
13
|
-
end
|
14
|
-
|
15
|
-
describe "#response" do
|
16
|
-
it "executes an HTTP GET request and returns the HTTPI::Response" do
|
17
|
-
response = HTTPI::Response.new 200, {}, Fixture.response(:authentication)
|
18
|
-
HTTPI.expects(:get).with(http_request).returns(response)
|
19
|
-
request.response.should == response
|
20
|
-
end
|
21
|
-
end
|
22
|
-
|
23
|
-
end
|