diff --git a/src/auth/session.go b/src/auth/session.go
index fb8e1307..4a9c9e45 100644
--- a/src/auth/session.go
+++ b/src/auth/session.go
@@ -64,6 +64,17 @@ func CreateSession(ctx context.Context, conn *pgxpool.Pool, username string) (*m
return &session, nil
}
+// Deletes a session by id. If no session with that id exists, no
+// error is returned.
+func DeleteSession(ctx context.Context, conn *pgxpool.Pool, id string) error {
+ _, err := conn.Exec(ctx, "DELETE FROM sessions WHERE id = $1", id)
+ if err != nil {
+ return oops.New(err, "failed to delete session")
+ }
+
+ return nil
+}
+
func NewSessionCookie(session *models.Session) *http.Cookie {
return &http.Cookie{
Name: SessionCookieName,
@@ -77,3 +88,9 @@ func NewSessionCookie(session *models.Session) *http.Cookie {
SameSite: http.SameSiteDefaultMode,
}
}
+
+var DeleteSessionCookie = &http.Cookie{
+ Name: SessionCookieName,
+ Domain: config.Config.Auth.CookieDomain,
+ MaxAge: -1,
+}
diff --git a/src/templates/src/include/header.html b/src/templates/src/include/header.html
index d4c295ef..83677be1 100644
--- a/src/templates/src/include/header.html
+++ b/src/templates/src/include/header.html
@@ -6,7 +6,7 @@
Admin
{{ end }}
{{ .User.Username }}
- Logout
+ Logout
{{ else }}
Register
Log in
diff --git a/src/website/routes.go b/src/website/routes.go
index 4201fd6d..be500ca6 100644
--- a/src/website/routes.go
+++ b/src/website/routes.go
@@ -38,6 +38,7 @@ func NewWebsiteRoutes(conn *pgxpool.Pool) http.Handler {
mainRoutes.GET("/assets/project.css", routes.ProjectCSS)
routes.POST("/login", routes.Login)
+ routes.GET("/logout", routes.Logout)
routes.ServeFiles("/public/*filepath", http.Dir("public"))
@@ -197,6 +198,20 @@ func (s *websiteRoutes) Login(c *RequestContext, p httprouter.Params) {
}
}
+func (s *websiteRoutes) Logout(c *RequestContext, p httprouter.Params) {
+ sessionCookie, err := c.Req.Cookie(auth.SessionCookieName)
+ if err == nil {
+ // clear the session from the db immediately, no expiration
+ err := auth.DeleteSession(c.Context(), s.conn, sessionCookie.Value)
+ if err != nil {
+ logging.Error().Err(err).Msg("failed to delete session on logout")
+ }
+ }
+
+ c.SetCookie(auth.DeleteSessionCookie)
+ c.Redirect("/", http.StatusSeeOther) // TODO: Redirect to the page the user was currently on, or if not authorized to view that page, immediately to the home page.
+}
+
func ErrorLoggingWrapper(h HMNHandler) HMNHandler {
return func(c *RequestContext, p httprouter.Params) {
h(c, p)