Added experimental version of pirsch for server side tracking.

This commit is contained in:
Marvin Blum
2020-06-21 16:01:42 +02:00
committed by Marvin Blum
parent a23faafc25
commit 186f1213a6
10 changed files with 106 additions and 7 deletions

View File

@@ -20,6 +20,8 @@ WORKDIR /app
ENV MB_LOGLEVEL=info ENV MB_LOGLEVEL=info
ENV MB_ALLOWED_ORIGINS=* ENV MB_ALLOWED_ORIGINS=*
ENV MB_HOST=0.0.0.0:80 ENV MB_HOST=0.0.0.0:80
ENV MB_DB_PORT=5432
ENV MB_DB_SSLMODE=disable
EXPOSE 80 EXPOSE 80
EXPOSE 443 EXPOSE 443

9
dev.sh
View File

@@ -10,5 +10,14 @@ export MB_HOT_RELOAD=true
export MB_EMVI_CLIENT_ID=3fBBn144yvSF9R3dPC8l export MB_EMVI_CLIENT_ID=3fBBn144yvSF9R3dPC8l
export MB_EMVI_CLIENT_SECRET=dw3FeshelTgdf1Gj13J7uF5FfdPDi40sQvvwqeFVKTTyIDuCdlAHhRY72csFL6yg export MB_EMVI_CLIENT_SECRET=dw3FeshelTgdf1Gj13J7uF5FfdPDi40sQvvwqeFVKTTyIDuCdlAHhRY72csFL6yg
export MB_EMVI_ORGA=marvin export MB_EMVI_ORGA=marvin
export MB_DB_HOST=localhost
export MB_DB_PORT=5432
export MB_DB_USER=postgres
export MB_DB_PASSWORD=postgres
export MB_DB_SCHEMA=marvinblum
export MB_DB_SSLMODE=disable
export MB_DB_SSLCERT=
export MB_DB_SSLKEY=
export MB_DB_SSLROOTCERT=
go run main.go go run main.go

View File

@@ -34,6 +34,10 @@ services:
- MB_EMVI_CLIENT_ID="3fBBn144yvSF9R3dPC8l" - MB_EMVI_CLIENT_ID="3fBBn144yvSF9R3dPC8l"
- MB_EMVI_CLIENT_SECRET="dw3FeshelTgdf1Gj13J7uF5FfdPDi40sQvvwqeFVKTTyIDuCdlAHhRY72csFL6yg" - MB_EMVI_CLIENT_SECRET="dw3FeshelTgdf1Gj13J7uF5FfdPDi40sQvvwqeFVKTTyIDuCdlAHhRY72csFL6yg"
- MB_EMVI_ORGA=marvin - MB_EMVI_ORGA=marvin
- MB_DB_HOST=postgres
- MB_DB_USER=
- MB_DB_PASSWORD=
- MB_DB_SCHEMA=
labels: labels:
- "traefik.enable=true" - "traefik.enable=true"
- "traefik.http.routers.marvinblum.entrypoints=web" - "traefik.http.routers.marvinblum.entrypoints=web"

2
go.mod
View File

@@ -7,7 +7,9 @@ require (
github.com/caddyserver/certmagic v0.10.13 github.com/caddyserver/certmagic v0.10.13
github.com/emvi/api-go v0.0.0-20191210194347-0a945446f6a8 github.com/emvi/api-go v0.0.0-20191210194347-0a945446f6a8
github.com/emvi/logbuch v0.0.0-20200214115750-61de9b6d5934 github.com/emvi/logbuch v0.0.0-20200214115750-61de9b6d5934
github.com/emvi/pirsch v0.0.0-20200621133222-e65f2459e5a3
github.com/gorilla/mux v1.7.4 github.com/gorilla/mux v1.7.4
github.com/gosimple/slug v1.9.0 github.com/gosimple/slug v1.9.0
github.com/lib/pq v1.7.0 // indirect
github.com/rs/cors v1.7.0 github.com/rs/cors v1.7.0
) )

4
go.sum
View File

@@ -77,6 +77,8 @@ github.com/emvi/api-go v0.0.0-20191210194347-0a945446f6a8 h1:DZJfRdvwlybLvHkyeN8
github.com/emvi/api-go v0.0.0-20191210194347-0a945446f6a8/go.mod h1:g9RdDC3s5ebCknAHQQ5PjoM2vRFSyyGoOUX3QkDKU+o= github.com/emvi/api-go v0.0.0-20191210194347-0a945446f6a8/go.mod h1:g9RdDC3s5ebCknAHQQ5PjoM2vRFSyyGoOUX3QkDKU+o=
github.com/emvi/logbuch v0.0.0-20200214115750-61de9b6d5934 h1:+G10WRp72llJuaW89QezNK8QU9SsOmd5Ja7ocrrUaI0= github.com/emvi/logbuch v0.0.0-20200214115750-61de9b6d5934 h1:+G10WRp72llJuaW89QezNK8QU9SsOmd5Ja7ocrrUaI0=
github.com/emvi/logbuch v0.0.0-20200214115750-61de9b6d5934/go.mod h1:J2Wgbr3BuSc1JO+D2MBVh6q3WPVSK5GzktwWz8pvkKw= github.com/emvi/logbuch v0.0.0-20200214115750-61de9b6d5934/go.mod h1:J2Wgbr3BuSc1JO+D2MBVh6q3WPVSK5GzktwWz8pvkKw=
github.com/emvi/pirsch v0.0.0-20200621133222-e65f2459e5a3 h1:Du+BjUUrCH7XptKBgsyTeLCPFOuYNArPfja53XFwzl4=
github.com/emvi/pirsch v0.0.0-20200621133222-e65f2459e5a3/go.mod h1:+YmBbltJ3feZz9L/QQyqwywltYvQKBfzrGD51TPKl5g=
github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4=
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
github.com/exoscale/egoscale v0.18.1/go.mod h1:Z7OOdzzTOz1Q1PjQXumlz9Wn/CddH0zSYdCF3rnBKXE= github.com/exoscale/egoscale v0.18.1/go.mod h1:Z7OOdzzTOz1Q1PjQXumlz9Wn/CddH0zSYdCF3rnBKXE=
@@ -169,6 +171,8 @@ github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
github.com/labbsr0x/bindman-dns-webhook v1.0.2/go.mod h1:p6b+VCXIR8NYKpDr8/dg1HKfQoRHCdcsROXKvmoehKA= github.com/labbsr0x/bindman-dns-webhook v1.0.2/go.mod h1:p6b+VCXIR8NYKpDr8/dg1HKfQoRHCdcsROXKvmoehKA=
github.com/labbsr0x/goh v1.0.1/go.mod h1:8K2UhVoaWXcCU7Lxoa2omWnC8gyW8px7/lmO61c027w= github.com/labbsr0x/goh v1.0.1/go.mod h1:8K2UhVoaWXcCU7Lxoa2omWnC8gyW8px7/lmO61c027w=
github.com/lib/pq v1.7.0 h1:h93mCPfUSkaul3Ka/VG8uZdmW1uMHDGxzu0NWHuJmHY=
github.com/lib/pq v1.7.0/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o=
github.com/linode/linodego v0.10.0/go.mod h1:cziNP7pbvE3mXIPneHj0oRY8L1WtGEIKlZ8LANE4eXA= github.com/linode/linodego v0.10.0/go.mod h1:cziNP7pbvE3mXIPneHj0oRY8L1WtGEIKlZ8LANE4eXA=
github.com/liquidweb/liquidweb-go v1.6.0/go.mod h1:UDcVnAMDkZxpw4Y7NOHkqoeiGacVLEIG/i5J9cyixzQ= github.com/liquidweb/liquidweb-go v1.6.0/go.mod h1:UDcVnAMDkZxpw4Y7NOHkqoeiGacVLEIG/i5J9cyixzQ=
github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4= github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4=

43
main.go
View File

@@ -1,17 +1,22 @@
package main package main
import ( import (
"database/sql"
"fmt"
"github.com/Kugelschieber/marvinblum.de/blog" "github.com/Kugelschieber/marvinblum.de/blog"
"github.com/Kugelschieber/marvinblum.de/tpl" "github.com/Kugelschieber/marvinblum.de/tpl"
"github.com/NYTimes/gziphandler" "github.com/NYTimes/gziphandler"
"github.com/caddyserver/certmagic" "github.com/caddyserver/certmagic"
emvi "github.com/emvi/api-go" emvi "github.com/emvi/api-go"
"github.com/emvi/logbuch" "github.com/emvi/logbuch"
"github.com/emvi/pirsch"
"github.com/gorilla/mux" "github.com/gorilla/mux"
_ "github.com/lib/pq"
"github.com/rs/cors" "github.com/rs/cors"
"html/template" "html/template"
"net/http" "net/http"
"os" "os"
"strconv"
"strings" "strings"
"time" "time"
) )
@@ -21,9 +26,11 @@ const (
staticDirPrefix = "/static/" staticDirPrefix = "/static/"
logTimeFormat = "2006-01-02_15:04:05" logTimeFormat = "2006-01-02_15:04:05"
envPrefix = "MB_" envPrefix = "MB_"
connectionString = `host=%s port=%s user=%s password=%s dbname=%s sslmode=%s sslcert=%s sslkey=%s sslrootcert=%s connectTimeout=%s timezone=%s`
) )
var ( var (
tracker *pirsch.Tracker
blogInstance *blog.Blog blogInstance *blog.Blog
) )
@@ -50,8 +57,37 @@ func logEnvConfig() {
} }
} }
func setupTracker() {
logbuch.Info("Connecting to database...")
host := os.Getenv("MB_DB_HOST")
port := os.Getenv("MB_DB_PORT")
user := os.Getenv("MB_DB_USER")
password := os.Getenv("MB_DB_PASSWORD")
schema := os.Getenv("MB_DB_SCHEMA")
sslMode := os.Getenv("MB_DB_SSLMODE")
sslCert := os.Getenv("MB_DB_SSLCERT")
sslKey := os.Getenv("MB_DB_SSLKEY")
sslRootCert := os.Getenv("MB_DB_SSLROOTCERT")
zone, offset := time.Now().Zone()
timezone := zone + strconv.Itoa(-offset/3600)
logbuch.Info("Setting time zone", logbuch.Fields{"timezone": timezone})
connectionStr := fmt.Sprintf(connectionString, host, port, user, password, schema, sslMode, sslCert, sslKey, sslRootCert, "30", timezone)
db, err := sql.Open("postgres", connectionStr)
if err != nil {
logbuch.Fatal("Error connecting to database", logbuch.Fields{"err": err})
}
if err := db.Ping(); err != nil {
logbuch.Fatal("Error pinging database", logbuch.Fields{"err": err})
}
tracker = pirsch.NewTracker(pirsch.NewPostgresStore(db))
}
func serveAbout() http.HandlerFunc { func serveAbout() http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) { return func(w http.ResponseWriter, r *http.Request) {
tracker.Hit(r)
data := struct { data := struct {
Articles []emvi.Article Articles []emvi.Article
}{ }{
@@ -67,6 +103,7 @@ func serveAbout() http.HandlerFunc {
func serveBlogPage() http.HandlerFunc { func serveBlogPage() http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) { return func(w http.ResponseWriter, r *http.Request) {
tracker.Hit(r)
data := struct { data := struct {
Articles map[int][]emvi.Article Articles map[int][]emvi.Article
}{ }{
@@ -82,6 +119,7 @@ func serveBlogPage() http.HandlerFunc {
func serveBlogArticle() http.HandlerFunc { func serveBlogArticle() http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) { return func(w http.ResponseWriter, r *http.Request) {
tracker.Hit(r)
vars := mux.Vars(r) vars := mux.Vars(r)
slug := strings.Split(vars["slug"], "-") slug := strings.Split(vars["slug"], "-")
@@ -119,9 +157,9 @@ func setupRouter() *mux.Router {
router.PathPrefix(staticDirPrefix).Handler(http.StripPrefix(staticDirPrefix, gziphandler.GzipHandler(http.FileServer(http.Dir(staticDir))))) router.PathPrefix(staticDirPrefix).Handler(http.StripPrefix(staticDirPrefix, gziphandler.GzipHandler(http.FileServer(http.Dir(staticDir)))))
router.Handle("/blog/{slug}", serveBlogArticle()) router.Handle("/blog/{slug}", serveBlogArticle())
router.Handle("/blog", serveBlogPage()) router.Handle("/blog", serveBlogPage())
router.Handle("/legal", tpl.ServeTemplate("legal.html")) router.Handle("/legal", tpl.ServeTemplate("legal.html", tracker))
router.Handle("/", serveAbout()) router.Handle("/", serveAbout())
router.NotFoundHandler = tpl.ServeTemplate("notfound.html") router.NotFoundHandler = tpl.ServeTemplate("notfound.html", tracker)
return router return router
} }
@@ -162,6 +200,7 @@ func main() {
configureLog() configureLog()
logEnvConfig() logEnvConfig()
tpl.LoadTemplate() tpl.LoadTemplate()
setupTracker()
blogInstance = blog.NewBlog() blogInstance = blog.NewBlog()
router := setupRouter() router := setupRouter()
corsConfig := configureCors(router) corsConfig := configureCors(router)

4
postgres/clear_logs.sh Normal file
View File

@@ -0,0 +1,4 @@
#!/bin/bash
echo "Clearing docker logs..."
echo "" > $(docker inspect --format='{{.LogPath}}' postgres)

View File

@@ -0,0 +1,22 @@
version: "3"
services:
postgres:
image: postgres:12-alpine
container_name: postgres
restart: always
command: -c ssl=on -c ssl_cert_file=/var/lib/postgresql/server.crt -c ssl_key_file=/var/lib/postgresql/server.key
networks:
- db-internal
environment:
POSTGRES_PASSWORD: #
ports:
- "5432:5432"
volumes:
- /root/postgres/data:/var/lib/postgresql/data
- /root/postgres/cert/server.crt:/var/lib/postgresql/server.crt
- /root/postgres/cert/server.key:/var/lib/postgresql/server.key
networks:
db-internal:
driver: bridge

10
postgres/gen_cert.sh Executable file
View File

@@ -0,0 +1,10 @@
#!/bin/bash
mkdir cert
cd cert
openssl req -new -text -passout pass:$1 -subj /CN=localhost -out server.req -keyout privkey.pem
openssl rsa -in privkey.pem -passin pass:$1 -out server.key
openssl req -x509 -in server.req -text -key server.key -out server.crt
chown 0:70 server.key
chmod 640 server.key
echo "done"

View File

@@ -3,6 +3,7 @@ package tpl
import ( import (
"bytes" "bytes"
"github.com/emvi/logbuch" "github.com/emvi/logbuch"
"github.com/emvi/pirsch"
"github.com/gosimple/slug" "github.com/gosimple/slug"
"html/template" "html/template"
"net/http" "net/http"
@@ -55,11 +56,13 @@ func Get() *template.Template {
return tpl return tpl
} }
func ServeTemplate(name string) http.HandlerFunc { func ServeTemplate(name string, tracker *pirsch.Tracker) http.HandlerFunc {
// render once so we have it in cache // render once so we have it in cache
renderTemplate(name) renderTemplate(name)
return func(w http.ResponseWriter, r *http.Request) { return func(w http.ResponseWriter, r *http.Request) {
tracker.Hit(r)
if hotReload { if hotReload {
LoadTemplate() LoadTemplate()
renderTemplate(name) renderTemplate(name)