Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Have a way to render an error page when there's an exception in a hook (e.g. handle) #2824

Closed
tomyan opened this issue Nov 17, 2021 · 5 comments · Fixed by #3239
Closed

Have a way to render an error page when there's an exception in a hook (e.g. handle) #2824

tomyan opened this issue Nov 17, 2021 · 5 comments · Fixed by #3239
Milestone

Comments

@tomyan
Copy link

tomyan commented Nov 17, 2021

Describe the problem

When an exception occurs in handle you get the exception and stack trace in the response to the user.

Describe the proposed solution

It would be great if there was a way to render an error page.

Alternatives considered

No response

Importance

nice to have

Additional Information

No response

@benmccann benmccann added this to the 1.0 milestone Nov 19, 2021
@dreitzner
Copy link
Contributor

It might be nice to extend handleError.

There could be an optional return response with

{
  status: 301,
  redirect: 'error/some-special-page'
}

similar to https://kit.svelte.dev/docs#loading-output-redirect

@nhe23
Copy link
Contributor

nhe23 commented Dec 29, 2021

I like the idea of extending handleError, as this is the logical place for that. However I think this would create an infinite redirect loop in some cases because the handle hook would be executed again after the redirect (and potentially throw an exception again).

@nhe23
Copy link
Contributor

nhe23 commented Dec 30, 2021

After playing around a bit I came up with a working solution. I changed the handleError implementation in Sveltekit to optionally return a status and a redirect value (just as @dreitzner proposed). Then I changed the index.js in the server runtime in order to consider the redirect value if provided. The code looks like this:

const handleErrorOutput = await options.handle_error(e, request);
if (handleErrorOutput && handleErrorOutput.redirect) {
	return handleErrorOutput.redirect !== request.path
		? {
			status: handleErrorOutput.status ? handleErrorOutput.status : 301,
			headers: {
				location: handleErrorOutput.redirect
			}
		  }
		: await render_response({
		        options,
		        $session: await options.hooks.getSession(request),
		        page_config: { ssr: false, router: true, hydrate: true },
		        status: 200,
		        branch: []
		  });
}

This way a redirect loop is prevented and the provided error page is rendered as desired. If this is a feasible solution I can create a PR for my changes. Before I do that it would be nice if @benmccann or one of the other maintainers could provide some feedback on this solution.

@tomyan
Copy link
Author

tomyan commented Jan 6, 2022

I'd prefer not to redirect if possible. For one thing a redirect is a successful status and if there's an error then I think a 500 should be returned so a non-human client can see that it wasn't successful. Furthermore if the error is transient I would like a user to be able to reload the page to retry, rather than be redirect away from what they were looking for.

@nhe23
Copy link
Contributor

nhe23 commented Jan 6, 2022

Those are some valid points. Maybe handleError could optionally return something like this:

{
    renderError: true
}

If this flag is set the nearest __error.svelte component would be rendered. This solution would be consistent with the error handling of exceptions in load functions.

Rich-Harris added a commit that referenced this issue Jan 9, 2022
* render error page if error happens in handle hook - fixes #2824

* changeset
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment