Class: Arachni::RPC::Server::Handler

Inherits:
Reactor::Connection
  • Object
show all
Includes:
Protocol, Reactor::Connection::PeerInfo
Defined in:
lib/arachni/rpc/server/handler.rb

Overview

Receives Request objects and transmits Response objects.

Author:

Instance Attribute Summary collapse

Instance Method Summary collapse

Methods included from Protocol

#on_connect, #on_read, #send_message

Constructor Details

#initialize(server) ⇒ Handler

Returns a new instance of Handler.

Parameters:

  • server (Server)

    RPC server.



26
27
28
29
30
# File 'lib/arachni/rpc/server/handler.rb', line 26

def initialize( server )
    @server  = server
    @opts    = server.opts.dup
    @request = nil
end

Instance Attribute Details

#requestRequest (readonly)

Returns Working RPC request.

Returns:

  • (Request)

    Working RPC request.



22
23
24
# File 'lib/arachni/rpc/server/handler.rb', line 22

def request
  @request
end

Instance Method Details

#on_close(_) ⇒ Object

Handles closed connections and cleans up the SSL session.



35
36
37
# File 'lib/arachni/rpc/server/handler.rb', line 35

def on_close( _ )
    @server = nil
end

#receive_request(req) ⇒ Object

Parameters:



44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
# File 'lib/arachni/rpc/server/handler.rb', line 44

def receive_request( req )
    @request = req

    # Create an empty response to be filled in little by little.
    res  = Response.new
    peer = peer_ip_address

    begin
        # Make sure the client is allowed to make RPC calls.
        authenticate!

        # Grab the partially filled in response which includes the result
        # of the RPC call and merge it with out prepared response.
        res.merge!( @server.call( self ) )

    # Handle exceptions and convert them to a simple hash, ready to be
    # passed to the client.
    rescue Exception => e
        type = ''

        # If it's an RPC exception pass the type along as is...
        if e.rpc_exception?
            type = e.class.name.split( ':' )[-1]

        # ...otherwise set it to a RemoteException.
        else
            type = 'RemoteException'
        end

        # RPC conventions for exception transmission.
        res.exception = {
            'type'      => type,
            'message'   => e.to_s,
            'backtrace' => e.backtrace
        }

        msg = "#{e.to_s}\n#{e.backtrace.join( "\n" )}"
        @server.logger.error( 'Exception' ){ msg + " [on behalf of #{peer}]" }
    end

    # Pass the result of the RPC call back to the client but *only* if it
    # wasn't async, otherwise {Server#call} will have already taken care of it.
    send_response( res ) if !res.async?
end