Possible to bypass authentication/sessions when using Gateway.Send?

I have certain processes that are conducted by components within my application and that make calls to service endpoints using Gateway.Send. I’d like to be able to have these calls to have full access to all elements of my API and to bypass authentication. Ideally this would happen in a way that I can tell within the service methods that the invocation came from Gateway.Send and not from a normal GET/POST/etc.

The hokey workaround I have is to have a hidden service endpoint that sets a flag indicating it’s an internal call, then use that to basically give that request an all-access pass to the data. It just results in a lot of duplication and I’m hoping there’s an easier way to determine the Gateway.Send source in the request somehow.

You can use the IRequest.IsInProcessRequest() API to determine if the Request is internal, e.g. made from an In Process Gateway.

Nice, that works in most situations. One scenario where it doesn’t work is when I have any kind of Authenticate or RequiresAnyRole attribute on the method instead of on the class. In that case, it will respond with my login page.

If I put those attributes at the class level, no issue – the method executes as expected and recognizes the IsInProcessRequest(). If I put the same attribute on the method, I get a prompt to login.

This is because Action-level attributes (i.e. on methods) are executed by in process requests like gateways whereas Service-level attributes are only executed as part of a HTTP Request pipeline. So you can move filters from action to service and vice-versa depending on if you want them executed in both in process requests or just in HTTP Requests.

Looks like this catches requests submitted using ResolveService<>. Is there any way to tell that a request is via Gateway.Send only?

IRequest.IsInProcessRequest() is how you can determine whether a Request was sent internally, using either the Gateway or ResolveService<T>. But if you want to execute a Service without marking it as an In Process Request you can just do what ResolveService does but without marking it as an In Process Request:

using (var service = HostContext.TryResolve<MyService>())
{
    (service as IRequiresRequest)?.Request = httpReq;
    var response = service.Any(new MyRequest());
}