Protocol::GRPCSourceProtocolGRPCMiddleware

class Middleware

Represents server middleware for handling gRPC requests. Implements Protocol::HTTP::Middleware interface. Subclasses should implement Protocol::GRPC::Middleware#dispatch to handle service routing and protocol details.

Definitions

def initialize(app = nil)

Initialize a new middleware instance.

Signature

parameter app #call | Nil

The next middleware in the chain

Implementation

def initialize(app = nil)
	super(app)
end

def call(request)

Handle incoming HTTP request.

Signature

parameter request Protocol::HTTP::Request
returns Protocol::HTTP::Response

Implementation

def call(request)
	return super unless grpc_request?(request)
	
	begin
		dispatch(request)
	rescue Error => error
		make_response(error.status_code, error.message, error: error)
	rescue StandardError => error
		make_response(Status::INTERNAL, error.message, error: error)
	end
end

def dispatch(request)

Dispatch the request to the service handler. Subclasses should implement this method to handle routing and protocol details.

Signature

parameter request Protocol::HTTP::Request
returns Protocol::HTTP::Response
raises NotImplementedError

If not implemented by subclass

Implementation

def dispatch(request)
	raise NotImplementedError, "Subclasses must implement #dispatch"
end

def grpc_request?(request)

Check if the request is a gRPC request.

Signature

parameter request Protocol::HTTP::Request
returns Boolean

true if the request is a gRPC request, false otherwise

Implementation

def grpc_request?(request)
	content_type = request.headers["content-type"]
	content_type&.start_with?("application/grpc")
end

def make_response(status_code, message, error: nil)

Make a gRPC error response with status and optional message.

Signature

parameter status_code Integer

gRPC status code

parameter message String

Error message

parameter error Exception

Optional error object (used to extract backtrace)

returns Protocol::HTTP::Response

Implementation

def make_response(status_code, message, error: nil)
	headers = Protocol::HTTP::Headers.new([], nil, policy: HEADER_POLICY)
	headers["content-type"] = "application/grpc+proto"
	
	Metadata.add_status!(headers, status: status_code, message: message, error: error)
	
	Protocol::HTTP::Response[200, headers, nil]
end