aboutsummaryrefslogtreecommitdiff
path: root/pkg/ext/middleware.go
blob: 771c0ac6cf729661c1a6c33967910d908c1411bc (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
package ext

import (
	"encoding/base64"
	"time"

	"github.com/sirupsen/logrus"
	"github.com/valyala/fasthttp"
)

func HTML(next fasthttp.RequestHandler) fasthttp.RequestHandler {
	return func(ctx *fasthttp.RequestCtx) {
		ctx.Response.Header.SetContentType("text/html")
		next(ctx)
	}
}

type LogMiddleware struct {
	entry *logrus.Entry
}

func NewLogMiddleare(log *logrus.Entry) *LogMiddleware {
	return &LogMiddleware{
		entry: log,
	}
}

func (l *LogMiddleware) HTTP(next fasthttp.RequestHandler) fasthttp.RequestHandler {
	return func(ctx *fasthttp.RequestCtx) {
		start := time.Now()
		next(ctx)
		elapsed := time.Since(start)
		l.entry.
			WithField("time", elapsed).
			WithField("code", ctx.Response.StatusCode()).
			WithField("path", string(ctx.Path())).
			WithField("bytes", len(ctx.Response.Body())).
			Info(string(ctx.Request.Header.Method()))
	}
}

type AuthMiddleware struct {
	key   []byte
	entry *logrus.Entry
}

func NewAuthMiddleware(key []byte, log *logrus.Entry) *AuthMiddleware {
	return &AuthMiddleware{
		key:   key,
		entry: log.WithField("context", "auth"),
	}
}

func (a *AuthMiddleware) LoggedIn(next fasthttp.RequestHandler) fasthttp.RequestHandler {
	return func(ctx *fasthttp.RequestCtx) {
		path := string(ctx.Path())
		if path == "/login" {
			next(ctx)
			return
		}

		redirectLogin := "/login?redirect=" + path
		authBase64 := ctx.Request.Header.Cookie("auth")
		if authBase64 == nil {
			a.entry.Info("No auth provided")
			ctx.Redirect(redirectLogin, 307)
			return
		}

		auth, err := base64.StdEncoding.DecodeString(string(authBase64))
		if err != nil {
			a.entry.Error(err)
			return
		}

		token, err := ReadToken(auth, a.key)
		if err != nil {
			a.entry.Error(err)
			ctx.Redirect(redirectLogin, 307)
			return
		}
		ctx.SetUserValue("token", token)
		a.entry.
			WithField("userID", token.UserID).
			WithField("username", token.Username).
			Info("user recognized")
		next(ctx)
	}
}