tide icon indicating copy to clipboard operation
tide copied to clipboard

Request path in req.uri does not match full path of request for nested servers.

Open dcow opened this issue 4 years ago • 10 comments

I understand this may be by design due to the nature of nesting, etc. If so, then the issue is that for an application that implements something like signed requests, the full path of the incoming request needs to be known by the middleware so that it can generate the right digest. I tried querying req.param("--tide-path-rest") but it returns the same data as req.uri().path() even though there's an entry in the map that shows more of the path.

dcow avatar May 19 '21 08:05 dcow

This is due to using nest instead of all. However, when using all tide doesn't want to resolve any of my routes anymore.

dcow avatar May 21 '21 22:05 dcow

I'd also really like to know if this is by design or not. And if so, how do you get the full request path then? It's really annoying when you try to do some URL generation using req.url().join("...") inside a nested middleware or endpoint.

jasontheiler avatar Jun 08 '21 09:06 jasontheiler

This sounds like a bug but I think it may be tricky to fix.

Fishrock123 avatar Jun 09 '21 17:06 Fishrock123

@Fishrock123 I may have some time to look into fixing this. What is tricky about the issue, in your opinion? And what should the correct behavior be? Should nested middleware req.uri contain the full path? Or should a public param be added that contains the original req uri? Or is all broken?

dcow avatar Aug 31 '21 20:08 dcow

@jbr would routefinder help this? I think so, right?

Fishrock123 avatar Sep 01 '21 17:09 Fishrock123

I'm not entirely sure, but I don't think so. I think this is a tide design issue, where it's intended that the request url is rewritten inside of nested apps, but there isn't an alternative api for the inner app to find out the actual full url. In my opinion, there should be two distinct apis: One is "what's my relative path from my mount point, which I might not know as a nested app author" and the other is "what is the full request path, untouched"

jbr avatar Sep 04 '21 21:09 jbr

I agree with that, yeah.

Fishrock123 avatar Sep 07 '21 19:09 Fishrock123

I'm working around this problem by using the Route::at method.

let mut server = tide::new();
server.at("/foo").get(foo_handler);

// "nested" server
let mut api = server.at("/api");
api.with(auth).with(cors).with(JsonApi);

api.at("/endpoint1").get(something);
api.at("/endpoint2").get(somethingelse);

It seems to behave as I expected a nested server to behave.

sorcix avatar Oct 10 '21 10:10 sorcix

When I do this the application crashes for reasons I can’t discern. I’ll give it another shot and report back.

dcow avatar Oct 10 '21 11:10 dcow

I've found a single difference between nested servers and this workaround with routes since I've started using it: the moment at which middleware is executed.

Middleware on a Server seems to execute before the routing, so my auth middleware returns 403 for unauthenticated requests even when the requested route does not exist. When using this workaround middleware only executes for routes that do exist, as they are set on the routes themselves.

In the example for my previous post:

let mut api = server.at("/api");
api.with(auth).with(cors).with(JsonApi);

api.at("/endpoint1").get(something);

This means that /api/endpoint returns 403 but /api/bar or /api/endpoint/foo returns 404. When using a nested server they would all return 403.

But it works for now. :-)

sorcix avatar Oct 10 '21 14:10 sorcix