Welcome to the "trac"-ing site of soap4r!
[soap4r] [httpclient] [openpgp4u] [pkcs1] [logger] [csv] [vtr]

root/trunk/lib/wsdl/operationBinding.rb

Revision 2005, 5.1 kB (checked in by nahi, 1 year ago)
  • introduce SOAP::RPC::MethodDef? and use it instead of complex Array structure.
  • param type 'in', 'out', 'retval' -> :in, :out, :retval
  • Property svn:eol-style set to native
  • Property svn:keywords set to author date id revision
Line 
1 # WSDL4R - WSDL bound operation definition.
2 # Copyright (C) 2000-2007  NAKAMURA, Hiroshi <nahi@ruby-lang.org>.
3
4 # This program is copyrighted free software by NAKAMURA, Hiroshi.  You can
5 # redistribute it and/or modify it under the same terms of Ruby's license;
6 # either the dual license version in 2003, or any later version.
7
8
9 require 'wsdl/info'
10
11
12 module WSDL
13
14
15 class OperationBinding < Info
16   attr_reader :name             # required
17   attr_reader :input
18   attr_reader :output
19   attr_reader :fault
20   attr_reader :soapoperation
21
22   class OperationInfo
23     attr_reader :boundid
24     attr_reader :qname
25     attr_reader :style
26     attr_accessor :inputuse
27     attr_accessor :outputuse
28     attr_reader :parts
29     attr_reader :faults
30
31     def initialize(boundid, qname, style, inputuse, outputuse)
32       @boundid = boundid
33       @qname = qname
34       @style = style
35       @inputuse = inputuse
36       @outputuse = outputuse
37       @parts = []
38       @faults = {}
39     end
40   end
41
42   class Part
43     attr_reader :io_type
44     attr_reader :name
45     attr_reader :type
46     attr_reader :element
47
48     def initialize(io_type, name, type, element)
49       @io_type = io_type
50       @name = name
51       @type = type
52       @element = element
53     end
54   end
55
56   class BoundId
57     attr_reader :name
58     attr_reader :soapaction
59
60     def initialize(name, soapaction)
61       @name = name
62       @soapaction = soapaction
63     end
64
65     def ==(rhs)
66       !rhs.nil? and @name == rhs.name and @soapaction == rhs.soapaction
67     end
68
69     def eql?(rhs)
70       (self == rhs)
71     end
72
73     def hash
74       @name.hash ^ @soapaction.hash
75     end
76   end
77
78   def initialize
79     super
80     @name = nil
81     @input = nil
82     @output = nil
83     @fault = []
84     @soapoperation = nil
85   end
86
87   def operation_info
88     qname = soapoperation_name()
89     style = soapoperation_style()
90     use_input = soapbody_use(@input)
91     use_output = soapbody_use(@output)
92     info = OperationInfo.new(boundid, qname, style, use_input, use_output)
93     op = find_operation()
94     if style == :rpc
95       info.parts.concat(collect_rpcparameter(op))
96     else
97       info.parts.concat(collect_documentparameter(op))
98     end
99     @fault.each do |fault|
100       op_fault = {}
101       soapfault = fault.soapfault
102       next if soapfault.nil?
103       op_fault[:ns] = fault.name.namespace
104       op_fault[:name] = fault.name.name
105       op_fault[:namespace] = soapfault.namespace
106       op_fault[:use] = soapfault.use || "literal"
107       op_fault[:encodingstyle] = soapfault.encodingstyle || "document"
108       info.faults[fault.name] = op_fault
109     end
110     info
111   end
112
113   def targetnamespace
114     parent.targetnamespace
115   end
116
117   def porttype
118     root.porttype(parent.type)
119   end
120
121   def boundid
122     BoundId.new(name, soapaction)
123   end
124
125   def find_operation
126     porttype.operations.each do |op|
127       next if op.name != @name
128       next if op.input and @input and op.input.name and @input.name and
129         op.input.name != @input.name
130       next if op.output and @output and op.output.name and @output.name and
131         op.output.name != @output.name
132       return op
133     end
134     raise RuntimeError.new("#{@name} not found")
135   end
136
137   def soapoperation_name
138     op_name = find_operation.operationname
139     if @input and @input.soapbody and @input.soapbody.namespace
140       op_name = XSD::QName.new(@input.soapbody.namespace, op_name.name)
141     end
142     op_name
143   end
144
145   def soapoperation_style
146     style = nil
147     if @soapoperation
148       style = @soapoperation.operation_style
149     elsif parent.soapbinding
150       style = parent.soapbinding.style
151     else
152       raise TypeError.new("operation style definition not found")
153     end
154     style || :document
155   end
156
157   def soapaction
158     if @soapoperation
159       @soapoperation.soapaction
160     else
161       nil
162     end
163   end
164
165   def parse_element(element)
166     case element
167     when InputName
168       o = Param.new
169       @input = o
170       o
171     when OutputName
172       o = Param.new
173       @output = o
174       o
175     when FaultName
176       o = Param.new
177       @fault << o
178       o
179     when SOAPOperationName
180       o = WSDL::SOAP::Operation.new
181       @soapoperation = o
182       o
183     when DocumentationName
184       o = Documentation.new
185       o
186     else
187       nil
188     end
189   end
190
191   def parse_attr(attr, value)
192     case attr
193     when NameAttrName
194       @name = value.source
195     else
196       nil
197     end
198   end
199
200 private
201
202   def soapbody_use(param)
203     param ? param.soapbody_use : nil
204   end
205
206   def collect_rpcparameter(operation)
207     result = operation.inputparts.collect { |part|
208       Part.new(:in, part.name, part.type, part.element)
209     }
210     outparts = operation.outputparts
211     if outparts.size > 0
212       retval = outparts[0]
213       result << Part.new(:retval, retval.name, retval.type, retval.element)
214       cdr(outparts).each { |part|
215         result << Part.new(:out, part.name, part.type, part.element)
216       }
217     end
218     result
219   end
220
221   def collect_documentparameter(operation)
222     param = []
223     operation.inputparts.each do |input|
224       param << Part.new(:in, input.name, input.type, input.element)
225     end
226     operation.outputparts.each do |output|
227       param << Part.new(:out, output.name, output.type, output.element)
228     end
229     param
230   end
231
232   def cdr(ary)
233     result = ary.dup
234     result.shift
235     result
236   end
237 end
238
239
240 end
Note: See TracBrowser for help on using the browser.