114 lines
3.1 KiB
Go
114 lines
3.1 KiB
Go
package web
|
|
|
|
import (
|
|
"fmt"
|
|
"net/http"
|
|
"os"
|
|
"time"
|
|
|
|
"github.com/gorilla/handlers"
|
|
"github.com/gorilla/mux"
|
|
"github.com/rs/zerolog/log"
|
|
|
|
"code.chrissexton.org/cws/cabinet/auth"
|
|
"code.chrissexton.org/cws/cabinet/db"
|
|
|
|
"github.com/stretchr/graceful"
|
|
)
|
|
|
|
type Web struct {
|
|
addr string
|
|
db *db.Database
|
|
salt string
|
|
static http.FileSystem
|
|
}
|
|
|
|
func New(addr string, db *db.Database, static http.FileSystem) *Web {
|
|
w := &Web{
|
|
addr: addr,
|
|
db: db,
|
|
static: static,
|
|
}
|
|
if err := db.MakeDB(); err != nil {
|
|
log.Fatal().
|
|
Err(err).
|
|
Msg("could not create database")
|
|
}
|
|
return w
|
|
}
|
|
|
|
type AuthMiddleware struct {
|
|
web *Web
|
|
db *db.Database
|
|
}
|
|
|
|
func NewAuthMiddleware(web *Web) AuthMiddleware {
|
|
return AuthMiddleware{
|
|
web: web,
|
|
db: web.db,
|
|
}
|
|
}
|
|
|
|
func (aw *AuthMiddleware) Middleware(next http.Handler) http.Handler {
|
|
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
|
if aw.web.AuthCheck(r) {
|
|
next.ServeHTTP(w, r)
|
|
return
|
|
}
|
|
w.WriteHeader(401)
|
|
fmt.Fprint(w, "invalid login")
|
|
})
|
|
}
|
|
|
|
func (web *Web) AuthCheck(r *http.Request) bool {
|
|
key := r.Header.Get("X-Auth-Key")
|
|
u, err := auth.GetByKey(web.db, key)
|
|
if key == "" || err != nil {
|
|
return false
|
|
}
|
|
log.Debug().Msgf("This shit is authed to user %s!", u.Name)
|
|
return true
|
|
}
|
|
|
|
func (web *Web) routeSetup() http.Handler {
|
|
r := mux.NewRouter()
|
|
api := r.PathPrefix("/v1/").Subrouter()
|
|
auth := NewAuthMiddleware(web)
|
|
|
|
authedApi := r.PathPrefix("/v1/").Subrouter()
|
|
authedApi.Use(auth.Middleware)
|
|
|
|
api.HandleFunc("/test", func(w http.ResponseWriter, r *http.Request) {
|
|
log.Debug().Msg("test json")
|
|
}).Methods(http.MethodPost).HeadersRegexp("Content-Type", `application/json.*`)
|
|
|
|
api.HandleFunc("/test", func(w http.ResponseWriter, r *http.Request) {
|
|
log.Debug().Msg("test markdown")
|
|
}).Methods(http.MethodPost).HeadersRegexp("Content-Type", `application/markdown.*`)
|
|
|
|
// curl 'http://127.0.0.1:8080/v1/test' -X POST -H 'Accept: application/json, text/plain, */*' --compressed -H 'Content-Type: application/json;charset=utf-8' --data '{ "test": 1 }'
|
|
|
|
authedApi.HandleFunc("/entries", web.newEntry).Methods(http.MethodPost)
|
|
authedApi.HandleFunc("/entries", web.newEntry).Methods(http.MethodPost).
|
|
HeadersRegexp("Content-Type", "application/(text|json).*")
|
|
authedApi.HandleFunc("/entries", web.newMarkdownEntry).Methods(http.MethodPost).
|
|
HeadersRegexp("Content-Type", "application/markdown.*")
|
|
authedApi.HandleFunc("/entries/{slug}", web.removeEntry).Methods(http.MethodDelete)
|
|
authedApi.HandleFunc("/entries/{slug}", web.editEntry).Methods(http.MethodPut)
|
|
|
|
api.HandleFunc("/entries/{slug}", web.getEntry).Methods(http.MethodGet)
|
|
api.HandleFunc("/entries", web.allEntries).Methods(http.MethodGet)
|
|
|
|
api.HandleFunc("/auth/new", web.newUser).Methods(http.MethodPost)
|
|
api.HandleFunc("/auth", web.auth).Methods(http.MethodPost)
|
|
r.PathPrefix("/").HandlerFunc(web.indexHandler("/index.html"))
|
|
loggedRouter := handlers.LoggingHandler(os.Stdout, r)
|
|
return loggedRouter
|
|
}
|
|
|
|
func (web *Web) Serve() {
|
|
middle := web.routeSetup()
|
|
log.Info().Str("addr", "http://"+web.addr).Msg("serving HTTP")
|
|
graceful.Run(web.addr, 10*time.Second, middle)
|
|
}
|