Signing in does not return to the page that was asked for #384

Open
opened 2026-10-01 22:06:18 +02:00 by clawbot · 2 comments
Collaborator

Owner's request, #377 (chat, 2026-10-01):

audit the whole app for stupid cases of missing functionality or basic things like this (like the stats panel at the top that i requested).

What is wrong: a signed-out operator who opens any admin page is sent to sign-in, and afterwards always lands on the webhook list, not on the page they asked for. That happens with a bookmarked event log, a link shared in chat, or a session that ended after SESSION_IDLE_TIMEOUT. In the audit, opening a webhook's event log while signed out and then signing in landed on /sources.

RequireAuth in internal/middleware/middleware.go redirects to /pages/login and keeps nothing of the original request, and HandleLoginSubmit in internal/handlers/auth.go always redirects to /. The sign-in page also shows a "Login" button in the navigation bar that links to the page it is already on (templates/navbar.html).

Definition of done:

  • After a redirect to sign-in from a GET request, signing in lands on the page originally asked for, path and query included.
  • Only a path on this site is accepted as that destination. An absolute URL, a //host value or anything else falls back to the webhook list, so the parameter cannot send anyone elsewhere.
  • Signing in without such a redirect lands on the webhook list, as today.
  • The navigation bar on the sign-in page has no link to the sign-in page.
  • Tests: a deep link through sign-in lands on that link, and an off-site or //host destination is ignored.

PRIORITY: from the owner's audit request of 1 October (#377), in the tier of #367 to #376.

Model: opus-5-5

Owner's request, https://git.eeqj.de/sneak/webhooker/issues/377 (chat, 2026-10-01): > audit the whole app for stupid cases of missing functionality or basic things like this (like the stats panel at the top that i requested). What is wrong: a signed-out operator who opens any admin page is sent to sign-in, and afterwards always lands on the webhook list, not on the page they asked for. That happens with a bookmarked event log, a link shared in chat, or a session that ended after `SESSION_IDLE_TIMEOUT`. In the audit, opening a webhook's event log while signed out and then signing in landed on `/sources`. `RequireAuth` in `internal/middleware/middleware.go` redirects to `/pages/login` and keeps nothing of the original request, and `HandleLoginSubmit` in `internal/handlers/auth.go` always redirects to `/`. The sign-in page also shows a "Login" button in the navigation bar that links to the page it is already on (`templates/navbar.html`). Definition of done: - After a redirect to sign-in from a GET request, signing in lands on the page originally asked for, path and query included. - Only a path on this site is accepted as that destination. An absolute URL, a `//host` value or anything else falls back to the webhook list, so the parameter cannot send anyone elsewhere. - Signing in without such a redirect lands on the webhook list, as today. - The navigation bar on the sign-in page has no link to the sign-in page. - Tests: a deep link through sign-in lands on that link, and an off-site or `//host` destination is ignored. PRIORITY: from the owner's audit request of 1 October (https://git.eeqj.de/sneak/webhooker/issues/377), in the tier of https://git.eeqj.de/sneak/webhooker/issues/367 to https://git.eeqj.de/sneak/webhooker/issues/376. Model: opus-5-5
clawbot self-assigned this 2026-10-01 22:06:18 +02:00
Author
Collaborator

Plan. The issue body is the brief. RequireAuth adds the requested path and query to the sign-in redirect as a parameter, for GET requests only; the sign-in form carries it as a hidden field; after a successful sign-in the handler redirects there only when the value is a path on this site (one leading /, not // or /\), and to the webhook list otherwise. The navigation bar on the sign-in page drops its sign-in link. It rebases onto #378's paths if that lands first.

Model: opus-5-5

Plan. The issue body is the brief. `RequireAuth` adds the requested path and query to the sign-in redirect as a parameter, for GET requests only; the sign-in form carries it as a hidden field; after a successful sign-in the handler redirects there only when the value is a path on this site (one leading `/`, not `//` or `/\`), and to the webhook list otherwise. The navigation bar on the sign-in page drops its sign-in link. It rebases onto https://git.eeqj.de/sneak/webhooker/pulls/378's paths if that lands first. Model: opus-5-5
Author
Collaborator

Built in #406. A logged-out GET of an admin page now carries its path and query to the login page as next, and logging in returns there. Only a path on this site is followed, checked after percent-decoding; an absolute URL, //host, /\host, their encoded forms, a control character or an empty value lands on the webhook list. The login page's navigation bar no longer links to itself.

  • Rule suppressed: gosec G710 (open redirect) on the two redirects that follow next, since its taint tracking cannot see the check.
  • Judgement call: a next longer than 2048 bytes falls back to the webhook list, since the login page writes it into its form.
  • Judgement call: an already logged-in visit to the login page also follows next.

Model: opus-5-5

Built in https://git.eeqj.de/sneak/webhooker/pulls/406. A logged-out `GET` of an admin page now carries its path and query to the login page as `next`, and logging in returns there. Only a path on this site is followed, checked after percent-decoding; an absolute URL, `//host`, `/\host`, their encoded forms, a control character or an empty value lands on the webhook list. The login page's navigation bar no longer links to itself. - Rule suppressed: gosec G710 (open redirect) on the two redirects that follow `next`, since its taint tracking cannot see the check. - Judgement call: a `next` longer than 2048 bytes falls back to the webhook list, since the login page writes it into its form. - Judgement call: an already logged-in visit to the login page also follows `next`. Model: opus-5-5
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: sneak/webhooker#384