Exception handling is driving me nuts.

I am utterly unable to control how exceptions are handled in my
application and it's driving me nuts

The idea is simple. I have a SOAP handler like this.

class RtiController < ApplicationController

  begin
     wsdl_service_name 'Rti'
     web_service_scaffold :invoke
     web_service_api RtiApi

     before_invocation :authenticate

     include SoapMethods

     protected

     def authenticate (name, args)
        #the first two arguments are always username and password
        generic_login(args[0], args[1])
        unless logged_in?
           raise Exceptions::LoginFailedError , "LoginFailedError:
Invalid user name or password"
        end
     end

  rescue Exception => e
     n = e.exception "#{e.inspect}: #{e.message}"
     n.set_backtrace []
     raise n
  end
end

Simple right?

If any error gets raised either in the authenticate function or any of
the functions in the included module I want to catch them and re-raise
a new error.

The rescue block never gets called no matter where the error happens.

Next I try this.

def rescue_action
do the same thing above
end

Nope it never gets called either.

So I try this

rescue_from Exception do |e|
        n = e.exception "#{e.inspect}: #{e.message}"
       n.set_backtrace []
       raise n
end

I also tried rescue_from SomeSpecificException and that doesn't work either.

I also tried putting a begin rescue block in the included module and
that doesn't do anything either.

Why is this so complicated? I just want a error handler for
this controller. Is actionwebservice messing with the controller or
what?

P.S. I am using the datanoise actionwebservice.

I'm new to Rails, so I'll preface this by saying that I might be
wrong, but you can give it a shot. I believe you have to have a
"begin" and "rescue" within your methods, not surrounding them as you
illustrated above. So your authenticate method might look like this:

def authenticate (name, args)
  begin
  #the first two arguments are always username and password
  generic_login(args[0], args[1])
  unless logged_in?
    raise Exceptions::LoginFailedError , "LoginFailedError:
    Invalid user name or password"
  end
  rescue Exception => e
     n = e.exception "#{e.inspect}: #{e.message}"
     n.set_backtrace []
     raise n
  end
end

Since you'll probably have multiple methods that require error
handling, I think you can define an error handling method outside of
each of your other methods. Instead of processing the exception
separately within each method's rescue function, your rescue functions
would instead call the error handling method. See below. Not 100%
sure this is kosher, but it's worth a shot...and let me know if it
works, I'm going to be building error handling into my app fairly
soon :slight_smile:

def method_1
  begin
    #code
  rescue Exception => e
    process_exception(e)
  end
end

def process_exception(e)
  #code for handling exception
end

end

I am utterly unable to control how exceptions are handled in my
application and it's driving me nuts

The idea is simple. I have a SOAP handler like this.

class RtiController < ApplicationController

begin
    wsdl_service_name 'Rti'
    web_service_scaffold :invoke
    web_service_api RtiApi

    before_invocation :authenticate

    include SoapMethods

    protected

    def authenticate (name, args)
       #the first two arguments are always username and password
       generic_login(args[0], args[1])
       unless logged_in?
          raise Exceptions::LoginFailedError , "LoginFailedError:
Invalid user name or password"
       end
    end

rescue Exception => e
    n = e.exception "#{e.inspect}: #{e.message}"
    n.set_backtrace []
    raise n
end
end

Simple right?

If any error gets raised either in the authenticate function or any of
the functions in the included module I want to catch them and re-raise
a new error.

The rescue block never gets called no matter where the error happens.

That rescue block doesn't do what you think. The way you need to think
about it is after the interpreter hits that begin, what code does it
execute before it hits the rescue clause?
It does not for example execute the authenticate method. It does
however call the web_service_api method, so if that raised an
exception then it would catch it

Next I try this.

def rescue_action
do the same thing above
end

Nope it never gets called either.

So I try this

rescue_from Exception do |e|
       n = e.exception "#{e.inspect}: #{e.message}"
      n.set_backtrace []
      raise n
end

I also tried rescue_from SomeSpecificException and that doesn't
work either.

I also tried putting a begin rescue block in the included module and
that doesn't do anything either.

Why is this so complicated? I just want a error handler for
this controller. Is actionwebservice messing with the controller or
what?

If you look at the actionwebservice code it is rescuing exceptions
before you get to them (see dispatch_web_service_request in http://github.com/datanoise/actionwebservice/tree/master/lib/action_web_service/dispatcher/action_controller_dispatcher.rb)

Fred