For a Salesforce.com integration project, I need to create a SOAP server to accept messages from Salesforce. Seeing as there is no way directly import a wsdl into ActionWebService, I instead used wsdl2ruby from the soap4r distribution to generate server stubs. Then, I used ActionWebService to emulate the same service. I had problems with using the default layout, so I changed my structure to use a delegated structure:
class NotificationServiceController < ApplicationController web_service_dispatching_mode :delegated web_service_scaffold :invoke web_service :notifications, NotificationService.new end
class NotificationServiceApi < ActionWebService::API::Base inflect_names false require_soap_action_header false api_method :notifications, :expects => [Notifications], :returns => [:bool] end
class NotificationService < ActionWebService::Base web_service_api NotificationServiceApi def logger RAILS_DEFAULT_LOGGER end def notifications(organization_id, action_id, session_id, enterprise_url, partner_url, notification) my_object_id = notification.sObject.id ack = false begin ack = so_something(my_object_id) rescue Exception => e logger.error("Error processing payment: #{e.message}") end ack end end
But STILL SOMETHING WAS WRONG. I was getting "No valid method call - missing method name" with the Salesforce outbound message queue reporting "org.xml.sax.SAXParseException: Content is not allowed in prolog." MMmmmmm helpful. The stack trace was showing that rails was trying to process the request as XMLRPC not SOAP, which was all wrong.
The stack trace looked something like this:
RuntimeError (No valid method call - missing method name!): /usr/lib/ruby/1.8/xmlrpc/parser.rb:476:in `parseMethodCall' /usr/lib/ruby/1.8/xmlrpc/marshal.rb:63:in `load_call' /usr/lib/ruby/1.8/xmlrpc/marshal.rb:32:in `load_call' /vendor/rails/actionwebservice/lib/action_web_service/protocol/xmlrpc_protocol.rb:36:in `decode_request' /vendor/rails/actionwebservice/lib/action_web_service/protocol/xmlrpc_protocol.rb:32:in `decode_action_pack_request' /vendor/rails/actionwebservice/lib/action_web_service/protocol/discovery.rb:20:in `discover_web_service_request' /vendor/rails/actionwebservice/lib/action_web_service/protocol/discovery.rb:18:in `discover_web_service_request' /vendor/rails/actionwebservice/lib/action_web_service/dispatcher/action_controller_dispatcher.rb:49:in `dispatch_web_service_request' (eval):1:in `notifications' ..........
Then, I came across patch 7077 (indirectly via this and then this), so, using my new best friend Piston I checked out Rails 1.2.3 into vendor/rails, and patched with the diff in the change. It was not entirely smooth - the xmlrpc.rb file could not be patched, but I merged the change manually.
All done! Works!
One thing I did discover the hard way though is that you need to have the whole stack of definitions with the same naming scheme for this to work. That is, if you've got a NotificationServiceController, you need to ensure that you have a NotificationService and a NotificationServiceApi defined and in use - no other class names will work. No Reuse of API Definitions, which is a bit of a bugger.
3 replies on “Rails ActionWebService SOAP error “No valid method call – missing method name””
Hi Dan,
I’m going through the exact same thing right now, but I still get the no valid method call runtime error even after freezing rails-1.2.3 in vendor/, applying patch7077 and ensuring that I’ve used a uniform naming scheme for the stack of definitions.
Is there something I’m missing out?
Alvin
Hi Alvin – are you using it from a SalesForce client as well?
To be honest, after I got that patch in, things started working… do you have another error you are getting now? Was the stack trace the same?
Hey Dan,
I am trying to do exactly what you have done with the listener. For me to perform the patch, I would need to freeze rails, which bring a new set of problems when gems like ActiveSalesforce is installed. I couldn’t find your email address anywhere to discuss this further with you. What version of rails are you using? Did you freeze your rails?
Berry