dahlia / fedify

ActivityPub server framework in TypeScript
https://fedify.dev/
MIT License
493 stars 19 forks source link

Using the Fresh integration, visiting a non-existing actor in the browser produces a short 406 response instead of showing Fresh's 404 error page #34

Closed jfietkau closed 6 months ago

jfietkau commented 6 months ago

Using Fedify and Fresh on Deno, all up to date versions. Whenever HTML is requested, the Federation object should let Fresh render the output, including error pages.

If I request a URI in the browser (or via curl with Accept: text/html) whose Fresh route returns a 404 error, and the URL maps to the registered actor dispatcher, the Federation handler appears to return a plain text 406 error in place of Fresh's 404 page. This should not happen.

Fresh middleware:

export const handler = integrateHandler(
  federation,
  (req, ctx) => undefined, // context data
);

Fresh handler:

export default async function UserPage(req: Request, ctx: RouteContext) {
  return ctx.renderNotFound();
}

Actor dispatcher:

federation.setActorDispatcher("/{handle}", async (ctx, handle, key) => {
  console.log("Invoked for:", handle);
  return null;
}

Testing shows that if application/activity+json is requested, the actor dispatcher is correctly invoked, returns null, and the client receives the HTML error page. If text/html is requested, the actor dispatcher is apparently not invoked, and the client receives a plain 406 Not acceptable error.

I hope the source of the problem is not some other part of my project, but this is the issue I am seeing.

dahlia commented 6 months ago

The root cause is that the federation object negotiates the content before determining if the resource exists or not. It was a slight optimization, but I think it should be considered a bug. I'll fix it.

dahlia commented 6 months ago

Fixed in 0.5.1!