aboutsummaryrefslogtreecommitdiffstats
path: root/actionwebservice/lib
diff options
context:
space:
mode:
Diffstat (limited to 'actionwebservice/lib')
-rw-r--r--actionwebservice/lib/action_web_service.rb6
-rw-r--r--actionwebservice/lib/action_web_service/client.rb4
-rw-r--r--actionwebservice/lib/action_web_service/client/soap_client.rb (renamed from actionwebservice/lib/action_web_service/client/soap.rb)0
-rw-r--r--actionwebservice/lib/action_web_service/client/xmlrpc_client.rb (renamed from actionwebservice/lib/action_web_service/client/xmlrpc.rb)0
-rw-r--r--actionwebservice/lib/action_web_service/container.rb147
-rw-r--r--actionwebservice/lib/action_web_service/dispatcher.rb2
-rw-r--r--actionwebservice/lib/action_web_service/dispatcher/abstract.rb158
-rw-r--r--actionwebservice/lib/action_web_service/dispatcher/action_controller_dispatcher.rb (renamed from actionwebservice/lib/action_web_service/router/wsdl.rb)109
-rw-r--r--actionwebservice/lib/action_web_service/invocation.rb61
-rw-r--r--actionwebservice/lib/action_web_service/protocol.rb4
-rw-r--r--actionwebservice/lib/action_web_service/protocol/soap_protocol.rb (renamed from actionwebservice/lib/action_web_service/protocol/soap.rb)0
-rw-r--r--actionwebservice/lib/action_web_service/protocol/xmlrpc_protocol.rb (renamed from actionwebservice/lib/action_web_service/protocol/xmlrpc.rb)15
-rw-r--r--actionwebservice/lib/action_web_service/router.rb2
-rw-r--r--actionwebservice/lib/action_web_service/router/action_controller.rb99
14 files changed, 274 insertions, 333 deletions
diff --git a/actionwebservice/lib/action_web_service.rb b/actionwebservice/lib/action_web_service.rb
index a55afc2244..5cf988a0f8 100644
--- a/actionwebservice/lib/action_web_service.rb
+++ b/actionwebservice/lib/action_web_service.rb
@@ -41,7 +41,7 @@ require 'action_web_service/api'
require 'action_web_service/struct'
require 'action_web_service/container'
require 'action_web_service/protocol'
-require 'action_web_service/router'
+require 'action_web_service/dispatcher'
ActionWebService::Base.class_eval do
include ActionWebService::API
@@ -55,6 +55,6 @@ ActionController::Base.class_eval do
include ActionWebService::Protocol::XmlRpc
include ActionWebService::API
include ActionWebService::API::ActionController
- include ActionWebService::Router::ActionController
- include ActionWebService::Router::Wsdl
+ include ActionWebService::Dispatcher
+ include ActionWebService::Dispatcher::ActionController
end
diff --git a/actionwebservice/lib/action_web_service/client.rb b/actionwebservice/lib/action_web_service/client.rb
index 77f934882c..2a1e33054d 100644
--- a/actionwebservice/lib/action_web_service/client.rb
+++ b/actionwebservice/lib/action_web_service/client.rb
@@ -1,3 +1,3 @@
require 'action_web_service/client/base'
-require 'action_web_service/client/soap'
-require 'action_web_service/client/xmlrpc'
+require 'action_web_service/client/soap_client'
+require 'action_web_service/client/xmlrpc_client'
diff --git a/actionwebservice/lib/action_web_service/client/soap.rb b/actionwebservice/lib/action_web_service/client/soap_client.rb
index 3557f88594..3557f88594 100644
--- a/actionwebservice/lib/action_web_service/client/soap.rb
+++ b/actionwebservice/lib/action_web_service/client/soap_client.rb
diff --git a/actionwebservice/lib/action_web_service/client/xmlrpc.rb b/actionwebservice/lib/action_web_service/client/xmlrpc_client.rb
index df51230b81..df51230b81 100644
--- a/actionwebservice/lib/action_web_service/client/xmlrpc.rb
+++ b/actionwebservice/lib/action_web_service/client/xmlrpc_client.rb
diff --git a/actionwebservice/lib/action_web_service/container.rb b/actionwebservice/lib/action_web_service/container.rb
index 6fa14def56..f02717579e 100644
--- a/actionwebservice/lib/action_web_service/container.rb
+++ b/actionwebservice/lib/action_web_service/container.rb
@@ -5,8 +5,6 @@ module ActionWebService # :nodoc:
def self.append_features(base) # :nodoc:
super
- base.class_inheritable_option(:web_service_dispatching_mode, :direct)
- base.class_inheritable_option(:web_service_exception_reporting, true)
base.extend(ClassMethods)
base.send(:include, ActionWebService::Container::InstanceMethods)
end
@@ -82,151 +80,6 @@ module ActionWebService # :nodoc:
service = info[:block]
service ? instance_eval(&service) : info[:object]
end
-
- private
- def dispatch_web_service_request(protocol_request)
- case web_service_dispatching_mode
- when :direct
- dispatch_direct_web_service_request(protocol_request)
- when :delegated
- dispatch_delegated_web_service_request(protocol_request)
- else
- raise(ContainerError, "unsupported dispatching mode :#{web_service_dispatching_mode}")
- end
- end
-
- def dispatch_direct_web_service_request(protocol_request)
- public_method_name = protocol_request.public_method_name
- api = self.class.web_service_api
- method_name = api.api_method_name(public_method_name)
- block = nil
- expects = nil
- if method_name
- signature = api.api_methods[method_name]
- expects = signature[:expects]
- protocol_request.type = Protocol::CheckedMessage
- protocol_request.signature = expects
- protocol_request.return_signature = signature[:returns]
- else
- protocol_request.type = Protocol::UncheckedMessage
- system_methods = self.class.read_inheritable_attribute('default_system_methods') || {}
- protocol = protocol_request.protocol
- block = system_methods[protocol.class]
- unless block
- method_name = api.default_api_method
- unless method_name && respond_to?(method_name)
- raise(ContainerError, "no such method ##{public_method_name}")
- end
- end
- end
-
- @method_params = protocol_request.unmarshal
- @params ||= {}
- if expects
- (1..@method_params.size).each do |i|
- i -= 1
- if expects[i].is_a?(Hash)
- @params[expects[i].keys.shift.to_s] = @method_params[i]
- else
- @params["param#{i}"] = @method_params[i]
- end
- end
- end
-
- if respond_to?(:before_action)
- @params['action'] = method_name.to_s
- return protocol_request.marshal(nil) if before_action == false
- end
-
- perform_invoke = lambda do
- if block
- block.call(public_method_name, self.class, *@method_params)
- else
- send(method_name)
- end
- end
- try_default = true
- result = nil
- catch(:try_default) do
- result = perform_invoke.call
- try_default = false
- end
- if try_default
- method_name = api.default_api_method
- if method_name
- protocol_request.type = Protocol::UncheckedMessage
- else
- raise(ContainerError, "no such method ##{public_method_name}")
- end
- result = perform_invoke.call
- end
- after_action if respond_to?(:after_action)
- protocol_request.marshal(result)
- end
-
- def dispatch_delegated_web_service_request(protocol_request)
- web_service_name = protocol_request.web_service_name
- service = web_service_object(web_service_name)
- api = service.class.web_service_api
- public_method_name = protocol_request.public_method_name
- method_name = api.api_method_name(public_method_name)
-
- invocation = ActionWebService::Invocation::InvocationRequest.new(
- ActionWebService::Invocation::ConcreteInvocation,
- public_method_name,
- method_name)
-
- if method_name
- protocol_request.type = Protocol::CheckedMessage
- signature = api.api_methods[method_name]
- protocol_request.signature = signature[:expects]
- protocol_request.return_signature = signature[:returns]
- invocation.params = protocol_request.unmarshal
- else
- protocol_request.type = Protocol::UncheckedMessage
- invocation.type = ActionWebService::Invocation::VirtualInvocation
- system_methods = self.class.read_inheritable_attribute('default_system_methods') || {}
- protocol = protocol_request.protocol
- block = system_methods[protocol.class]
- if block
- invocation.block = block
- invocation.block_params << service.class
- else
- method_name = api.default_api_method
- if method_name && service.respond_to?(method_name)
- invocation.params = protocol_request.unmarshal
- invocation.method_name = method_name.to_sym
- else
- raise(ContainerError, "no such method /#{web_service_name}##{public_method_name}")
- end
- end
- end
-
- canceled_reason = nil
- canceled_block = lambda{|r| canceled_reason = r}
- perform_invoke = lambda do
- service.perform_invocation(invocation, &canceled_block)
- end
- try_default = true
- result = nil
- catch(:try_default) do
- result = perform_invoke.call
- try_default = false
- end
- if try_default
- method_name = api.default_api_method
- if method_name
- protocol_request.type = Protocol::UncheckedMessage
- invocation.params = protocol_request.unmarshal
- invocation.method_name = method_name.to_sym
- invocation.type = ActionWebService::Invocation::UnpublishedConcreteInvocation
- else
- raise(ContainerError, "no such method /#{web_service_name}##{public_method_name}")
- end
- result = perform_invoke.call
- end
- protocol_request.marshal(result)
- end
end
end
end
diff --git a/actionwebservice/lib/action_web_service/dispatcher.rb b/actionwebservice/lib/action_web_service/dispatcher.rb
new file mode 100644
index 0000000000..601d831373
--- /dev/null
+++ b/actionwebservice/lib/action_web_service/dispatcher.rb
@@ -0,0 +1,2 @@
+require 'action_web_service/dispatcher/abstract'
+require 'action_web_service/dispatcher/action_controller_dispatcher'
diff --git a/actionwebservice/lib/action_web_service/dispatcher/abstract.rb b/actionwebservice/lib/action_web_service/dispatcher/abstract.rb
new file mode 100644
index 0000000000..e03446924a
--- /dev/null
+++ b/actionwebservice/lib/action_web_service/dispatcher/abstract.rb
@@ -0,0 +1,158 @@
+require 'benchmark'
+
+module ActionWebService # :nodoc:
+ module Dispatcher # :nodoc:
+ class DispatcherError < ActionWebService::ActionWebServiceError # :nodoc:
+ end
+
+ def self.append_features(base) # :nodoc:
+ super
+ base.class_inheritable_option(:web_service_dispatching_mode, :direct)
+ base.class_inheritable_option(:web_service_exception_reporting, true)
+ base.send(:include, ActionWebService::Dispatcher::InstanceMethods)
+ end
+
+ module InstanceMethods # :nodoc:
+ private
+ def dispatch_web_service_request(action_pack_request)
+ protocol_request = protocol_response = nil
+ bm = Benchmark.measure do
+ protocol_request = probe_request_protocol(action_pack_request)
+ protocol_response = dispatch_protocol_request(protocol_request)
+ end
+ [protocol_request, protocol_response, bm.real, nil]
+ rescue Exception => e
+ protocol_response = prepare_exception_response(protocol_request, e)
+ [protocol_request, prepare_exception_response(protocol_request, e), nil, e]
+ end
+
+ def dispatch_protocol_request(protocol_request)
+ case web_service_dispatching_mode
+ when :direct
+ dispatch_direct_request(protocol_request)
+ when :delegated
+ dispatch_delegated_request(protocol_request)
+ else
+ raise(ContainerError, "unsupported dispatching mode :#{web_service_dispatching_mode}")
+ end
+ end
+
+ def dispatch_direct_request(protocol_request)
+ request = prepare_dispatch_request(protocol_request)
+ return_value = direct_invoke(request)
+ protocol_request.marshal(return_value)
+ end
+
+ def dispatch_delegated_request(protocol_request)
+ request = prepare_dispatch_request(protocol_request)
+ return_value = delegated_invoke(request)
+ protocol_request.marshal(return_value)
+ end
+
+ def direct_invoke(request)
+ return nil unless before_direct_invoke(request)
+ return_value = send(request.method_name)
+ after_direct_invoke(request)
+ return_value
+ end
+
+ def before_direct_invoke(request)
+ @method_params = request.params
+ end
+
+ def after_direct_invoke(request)
+ end
+
+ def delegated_invoke(request)
+ cancellation_reason = nil
+ web_service = request.web_service
+ return_value = web_service.perform_invocation(request.method_name, request.params) do |x|
+ cancellation_reason = x
+ end
+ if cancellation_reason
+ raise(DispatcherError, "request canceled: #{cancellation_reason}")
+ end
+ return_value
+ end
+
+ def fallback_invoke(dispatch_request)
+ raise NotImplementedError
+ end
+
+ def prepare_dispatch_request(protocol_request)
+ api = method_name = web_service_name = web_service = params = nil
+ public_method_name = protocol_request.public_method_name
+ case web_service_dispatching_mode
+ when :direct
+ api = self.class.web_service_api
+ when :delegated
+ web_service_name = protocol_request.web_service_name
+ web_service = web_service_object(web_service_name)
+ api = web_service.class.web_service_api
+ end
+ method_name = api.api_method_name(public_method_name)
+ signature = nil
+ if method_name
+ signature = api.api_methods[method_name]
+ protocol_request.type = Protocol::CheckedMessage
+ protocol_request.signature = signature[:expects]
+ protocol_request.return_signature = signature[:returns]
+ else
+ method_name = api.default_api_method
+ if method_name
+ protocol_request.type = Protocol::UncheckedMessage
+ else
+ raise(DispatcherError, "no such method #{web_service_name}##{public_method_name}")
+ end
+ end
+ params = protocol_request.unmarshal
+ DispatchRequest.new(
+ :api => api,
+ :public_method_name => public_method_name,
+ :method_name => method_name,
+ :signature => signature,
+ :web_service_name => web_service_name,
+ :web_service => web_service,
+ :params => params)
+ end
+
+ def prepare_exception_response(protocol_request, exception)
+ if protocol_request && exception
+ case web_service_dispatching_mode
+ when :direct
+ if web_service_exception_reporting
+ return protocol_request.protocol.marshal_exception(exception)
+ else
+ raise exception
+ end
+ when :delegated
+ web_service = web_service_object(protocol_request.web_service_name)
+ if web_service && web_service.class.web_service_exception_reporting
+ return protocol_request.protocol.marshal_exception(exception)
+ else
+ raise exception
+ end
+ end
+ else
+ protocol_request.protocol.marshal_exception(RuntimeError.new("missing protocol request or exception"))
+ end
+ rescue Exception
+ nil
+ end
+
+ class DispatchRequest
+ attr :api
+ attr :public_method_name
+ attr :method_name
+ attr :signature
+ attr :web_service_name
+ attr :web_service
+ attr :params
+
+ def initialize(values={})
+ values.each{|k,v| instance_variable_set("@#{k.to_s}", v)}
+ end
+ end
+ end
+ end
+end
diff --git a/actionwebservice/lib/action_web_service/router/wsdl.rb b/actionwebservice/lib/action_web_service/dispatcher/action_controller_dispatcher.rb
index 6963334818..68c0f4ffb3 100644
--- a/actionwebservice/lib/action_web_service/router/wsdl.rb
+++ b/actionwebservice/lib/action_web_service/dispatcher/action_controller_dispatcher.rb
@@ -1,23 +1,114 @@
module ActionWebService # :nodoc:
- module Router # :nodoc:
- module Wsdl # :nodoc:
+ module Dispatcher # :nodoc:
+ module ActionController # :nodoc:
def self.append_features(base) # :nodoc:
- base.class_eval do
+ super
+ base.class_eval do
class << self
- alias_method :inherited_without_wsdl, :inherited
+ alias_method :inherited_without_action_controller, :inherited
+ end
+ end
+ base.class_eval do
+ alias_method :before_direct_invoke_without_action_controller, :before_direct_invoke
+ alias_method :after_direct_invoke_without_action_controller, :after_direct_invoke
+ end
+ base.add_web_service_api_callback do |klass, api|
+ if klass.web_service_dispatching_mode == :direct
+ klass.class_eval <<-EOS
+ def api
+ controller_dispatch_web_service_request
+ end
+ EOS
+ end
+ end
+ base.add_web_service_definition_callback do |klass, name, info|
+ if klass.web_service_dispatching_mode == :delegated
+ klass.class_eval <<-EOS
+ def #{name}
+ controller_dispatch_web_service_request
+ end
+ EOS
end
end
base.extend(ClassMethods)
+ base.send(:include, ActionWebService::Dispatcher::ActionController::Invocation)
end
- module ClassMethods
+ module ClassMethods # :nodoc:
def inherited(child)
- inherited_without_wsdl(child)
- child.send(:include, ActionWebService::Router::Wsdl::InstanceMethods)
+ inherited_without_action_controller(child)
+ child.send(:include, ActionWebService::Dispatcher::ActionController::WsdlGeneration)
end
end
- module InstanceMethods # :nodoc:
+ module Invocation # :nodoc:
+ private
+ def controller_dispatch_web_service_request
+ request, response, elapsed, exception = dispatch_web_service_request(@request)
+ if response
+ begin
+ log_request(request)
+ log_error(exception) if exception && logger
+ log_response(response, elapsed)
+ response_options = { :type => response.content_type, :disposition => 'inline' }
+ send_data(response.raw_body, response_options)
+ rescue Exception => e
+ log_error(e) unless logger.nil?
+ render_text("Internal protocol error", "500 Internal Server Error")
+ end
+ else
+ logger.error("No response available") unless logger.nil?
+ render_text("Internal protocol error", "500 Internal Server Error")
+ end
+ end
+
+ def before_direct_invoke(request)
+ before_direct_invoke_without_action_controller(request)
+ @params ||= {}
+ signature = request.signature
+ if signature && (expects = request.signature[:expects])
+ (0..(@method_params.size-1)).each do |i|
+ if expects[i].is_a?(Hash)
+ @params[expects[i].keys[0].to_s] = @method_params[i]
+ else
+ @params['param%d' % i] = @method_params[i]
+ end
+ end
+ end
+ @params['action'] = request.method_name.to_s
+ @session ||= {}
+ @assigns ||= {}
+ return nil if before_action == false
+ true
+ end
+
+ def after_direct_invoke(request)
+ after_direct_invoke_without_action_controller(request)
+ after_action
+ end
+
+ def log_request(request)
+ unless logger.nil? || request.nil?
+ logger.debug("\nWeb Service Request:")
+ indented = request.raw_body.split(/\n/).map{|x| " #{x}"}.join("\n")
+ logger.debug(indented)
+ end
+ end
+
+ def log_response(response, elapsed)
+ unless logger.nil? || response.nil?
+ logger.debug("\nWeb Service Response (%f):" % elapsed)
+ indented = response.raw_body.split(/\n/).map{|x| " #{x}"}.join("\n")
+ logger.debug(indented)
+ end
+ end
+
+ unless method_defined?(:logger)
+ def logger; @logger; end
+ end
+ end
+
+ module WsdlGeneration # :nodoc:
XsdNs = 'http://www.w3.org/2001/XMLSchema'
WsdlNs = 'http://schemas.xmlsoap.org/wsdl/'
SoapNs = 'http://schemas.xmlsoap.org/wsdl/soap/'
@@ -28,7 +119,7 @@ module ActionWebService # :nodoc:
case @request.method
when :get
begin
- host_name = @request.env['HTTP_HOST']||@request.env['SERVER_NAME']
+ host_name = @request.env['HTTP_HOST'] || @request.env['SERVER_NAME']
uri = "http://#{host_name}/#{controller_name}/"
soap_action_base = "/#{controller_name}"
xml = to_wsdl(self, uri, soap_action_base)
diff --git a/actionwebservice/lib/action_web_service/invocation.rb b/actionwebservice/lib/action_web_service/invocation.rb
index 64d3e8d524..62f38b8ecd 100644
--- a/actionwebservice/lib/action_web_service/invocation.rb
+++ b/actionwebservice/lib/action_web_service/invocation.rb
@@ -1,9 +1,5 @@
module ActionWebService # :nodoc:
module Invocation # :nodoc:
- ConcreteInvocation = :concrete
- VirtualInvocation = :virtual
- UnpublishedConcreteInvocation = :unpublished_concrete
-
class InvocationError < ActionWebService::ActionWebServiceError # :nodoc:
end
@@ -137,31 +133,15 @@ module ActionWebService # :nodoc:
end
end
- def perform_invocation_with_interception(invocation, &block)
- return if before_invocation(invocation.method_name, invocation.params, &block) == false
- result = perform_invocation_without_interception(invocation)
- after_invocation(invocation.method_name, invocation.params, result)
- result
+ def perform_invocation_with_interception(method_name, params, &block)
+ return if before_invocation(method_name, params, &block) == false
+ return_value = perform_invocation_without_interception(method_name, params)
+ after_invocation(method_name, params, return_value)
+ return_value
end
- def perform_invocation(invocation)
- if invocation.concrete?
- unless self.respond_to?(invocation.method_name) && \
- self.class.web_service_api.has_api_method?(invocation.method_name)
- raise InvocationError, "no such web service method '#{invocation.method_name}' on service object"
- end
- end
- params = invocation.params
- if invocation.concrete? || invocation.unpublished_concrete?
- self.send(invocation.method_name, *params)
- else
- if invocation.block
- params = invocation.block_params + params
- invocation.block.call(invocation.public_method_name, *params)
- else
- self.send(invocation.method_name, *params)
- end
- end
+ def perform_invocation(method_name, params)
+ send(method_name, *params)
end
def before_invocation(name, args, &block)
@@ -221,32 +201,5 @@ module ActionWebService # :nodoc:
end
end
end
-
- class InvocationRequest # :nodoc:
- attr_accessor :type
- attr :public_method_name
- attr_accessor :method_name
- attr_accessor :params
- attr_accessor :block
- attr :block_params
-
- def initialize(type, public_method_name, method_name, params=nil)
- @type = type
- @public_method_name = public_method_name
- @method_name = method_name
- @params = params || []
- @block = nil
- @block_params = []
- end
-
- def concrete?
- @type == ConcreteInvocation ? true : false
- end
-
- def unpublished_concrete?
- @type == UnpublishedConcreteInvocation ? true : false
- end
- end
-
end
end
diff --git a/actionwebservice/lib/action_web_service/protocol.rb b/actionwebservice/lib/action_web_service/protocol.rb
index 733787136a..b15e850676 100644
--- a/actionwebservice/lib/action_web_service/protocol.rb
+++ b/actionwebservice/lib/action_web_service/protocol.rb
@@ -1,4 +1,4 @@
require 'action_web_service/protocol/abstract'
require 'action_web_service/protocol/registry'
-require 'action_web_service/protocol/soap'
-require 'action_web_service/protocol/xmlrpc'
+require 'action_web_service/protocol/soap_protocol'
+require 'action_web_service/protocol/xmlrpc_protocol'
diff --git a/actionwebservice/lib/action_web_service/protocol/soap.rb b/actionwebservice/lib/action_web_service/protocol/soap_protocol.rb
index 3c527fea93..3c527fea93 100644
--- a/actionwebservice/lib/action_web_service/protocol/soap.rb
+++ b/actionwebservice/lib/action_web_service/protocol/soap_protocol.rb
diff --git a/actionwebservice/lib/action_web_service/protocol/xmlrpc.rb b/actionwebservice/lib/action_web_service/protocol/xmlrpc_protocol.rb
index 414bcfdbf7..1addccba56 100644
--- a/actionwebservice/lib/action_web_service/protocol/xmlrpc.rb
+++ b/actionwebservice/lib/action_web_service/protocol/xmlrpc_protocol.rb
@@ -54,7 +54,6 @@ module ActionWebService # :nodoc:
def initialize(container_class)
super(container_class)
- container_class.write_inheritable_hash('default_system_methods', XmlRpcProtocol => method(:xmlrpc_default_system_handler))
end
def unmarshal_request(protocol_request)
@@ -153,20 +152,6 @@ module ActionWebService # :nodoc:
end
private
- def xmlrpc_default_system_handler(name, service_class, *args)
- case name
- when 'system.listMethods'
- methods = []
- api = service_class.web_service_api
- api.api_methods.each do |name, info|
- methods << api.public_api_method_name(name)
- end
- methods.sort
- else
- throw :try_default
- end
- end
-
def check_array_types(signature)
signature.map{|x| x.is_a?(Array) ? Array : x}
end
diff --git a/actionwebservice/lib/action_web_service/router.rb b/actionwebservice/lib/action_web_service/router.rb
deleted file mode 100644
index 4bfb0bc8b7..0000000000
--- a/actionwebservice/lib/action_web_service/router.rb
+++ /dev/null
@@ -1,2 +0,0 @@
-require 'action_web_service/router/action_controller'
-require 'action_web_service/router/wsdl'
diff --git a/actionwebservice/lib/action_web_service/router/action_controller.rb b/actionwebservice/lib/action_web_service/router/action_controller.rb
deleted file mode 100644
index 591fe4e232..0000000000
--- a/actionwebservice/lib/action_web_service/router/action_controller.rb
+++ /dev/null
@@ -1,99 +0,0 @@
-module ActionWebService # :nodoc:
- module Router # :nodoc:
- module ActionController # :nodoc:
- def self.append_features(base) # :nodoc:
- base.add_web_service_api_callback do |container_class, api|
- if container_class.web_service_dispatching_mode == :direct
- container_class.class_eval <<-EOS
- def api
- process_action_service_request
- end
- EOS
- end
- end
- base.add_web_service_definition_callback do |klass, name, info|
- if klass.web_service_dispatching_mode == :delegated
- klass.class_eval <<-EOS
- def #{name}
- process_action_service_request
- end
- EOS
- end
- end
- base.send(:include, ActionWebService::Router::ActionController::InstanceMethods)
- end
-
- module InstanceMethods # :nodoc:
- private
- def process_action_service_request
- protocol_request = nil
- begin
- begin
- protocol_request = probe_request_protocol(self.request)
- rescue Exception => e
- unless logger.nil?
- logger.error "Invalid request: #{e.message}"
- logger.error self.request.raw_post
- end
- raise
- end
- if protocol_request
- log_request(protocol_request)
- protocol_response = dispatch_web_service_request(protocol_request)
- log_response(protocol_response)
- response_options = {
- :type => protocol_response.content_type,
- :disposition => 'inline'
- }
- send_data(protocol_response.raw_body, response_options)
- else
- logger.fatal "Invalid Action Web Service service or method requested" unless logger.nil?
- render_text 'Internal protocol error', "500 Invalid service/method"
- end
- rescue Exception => e
- log_error e unless logger.nil?
- exc_response = nil
- case web_service_dispatching_mode
- when :direct
- if self.class.web_service_exception_reporting
- exc_response = protocol_request.protocol.marshal_exception(e)
- end
- when :delegated
- web_service = web_service_object(protocol_request.service_name) rescue nil
- if web_service && web_service.class.web_service_exception_reporting
- exc_response = protocol_request.protocol.marshal_exception(e) rescue nil
- end
- end
- if exc_response
- response_options = {
- :type => exc_response.content_type,
- :disposition => 'inline'
- }
- log_response exc_response
- send_data(exc_response.raw_body, response_options)
- else
- render_text 'Internal protocol error', "500 #{e.message}"
- end
- end
- end
-
- def log_request(protocol_request)
- unless logger.nil?
- web_service_name = protocol_request.web_service_name
- method_name = protocol_request.public_method_name
- logger.info "\nProcessing Action Web Service Request: #{web_service_name}##{method_name}"
- logger.info "Raw Request Body:"
- logger.info protocol_request.raw_body
- end
- end
-
- def log_response(protocol_response)
- unless logger.nil?
- logger.info "\nRaw Response Body:"
- logger.info protocol_response.raw_body
- end
- end
- end
- end
- end
-end