9 Commits

8 changed files with 74 additions and 10 deletions

View File

@ -12,7 +12,9 @@ fine with getting your hands dirty, but I plan on having it ready to go for more
- Routing/controllers - Routing/controllers
- Templating - Templating
- Simple database migration system - Simple database migration system
- Built in REST client
- CSRF protection - CSRF protection
- Middleware
- Minimal user login/registration + sessions - Minimal user login/registration + sessions
- Config file handling - Config file handling
- Scheduled tasks - Scheduled tasks

2
go.mod
View File

@ -4,5 +4,5 @@ go 1.20
require ( require (
github.com/lib/pq v1.10.9 github.com/lib/pq v1.10.9
golang.org/x/crypto v0.8.0 golang.org/x/crypto v0.11.0
) )

4
go.sum
View File

@ -1,4 +1,4 @@
github.com/lib/pq v1.10.9 h1:YXG7RB+JIjhP29X+OtkiDnYaXQwpS4JEWq7dtCCRUEw= github.com/lib/pq v1.10.9 h1:YXG7RB+JIjhP29X+OtkiDnYaXQwpS4JEWq7dtCCRUEw=
github.com/lib/pq v1.10.9/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o= github.com/lib/pq v1.10.9/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o=
golang.org/x/crypto v0.8.0 h1:pd9TJtTueMTVQXzk8E2XESSMQDj/U7OUu0PqJqPXQjQ= golang.org/x/crypto v0.11.0 h1:6Ewdq3tDic1mg5xRO4milcWCfMVQhI4NkqWWvqejpuA=
golang.org/x/crypto v0.8.0/go.mod h1:mRqEX+O9/h5TFCrQhkgjo2yKi0yYA+9ecGkdQoHrywE= golang.org/x/crypto v0.11.0/go.mod h1:xgJhtzW8F9jGdVFWZESrid1U1bjeNy4zgy5cRr/CIio=

View File

@ -6,8 +6,8 @@ import (
"net/http" "net/http"
) )
// CsrfMiddleware validates the CSRF token and returns the handler function if it succeded // Csrf validates the CSRF token and returns the handler function if it succeded
func CsrfMiddleware(f func(w http.ResponseWriter, r *http.Request)) func(w http.ResponseWriter, r *http.Request) { func Csrf(f func(w http.ResponseWriter, r *http.Request)) func(w http.ResponseWriter, r *http.Request) {
return func(w http.ResponseWriter, r *http.Request) { return func(w http.ResponseWriter, r *http.Request) {
// Verify csrf token // Verify csrf token
_, err := security.VerifyCsrfToken(r) _, err := security.VerifyCsrfToken(r)

5
middleware/groups.go Normal file
View File

@ -0,0 +1,5 @@
package middleware
import "net/http"
type MiddlewareFunc func(f func(w http.ResponseWriter, r *http.Request)) func(w http.ResponseWriter, r *http.Request)

View File

@ -2,12 +2,12 @@ package middleware
import "net/http" import "net/http"
// ProcessMiddleware is a wrapper function for the http.HandleFunc function // ProcessGroup is a wrapper function for the http.HandleFunc function
// that takes the function you want to execute (f) and the middleware you want // that takes the function you want to execute (f) and the middleware you want
// to execute (m) this should be used when processing multiple groups of middleware at a time // to execute (m) this should be used when processing multiple groups of middleware at a time
func ProcessMiddleware(f func(w http.ResponseWriter, r *http.Request), m []func()) func(w http.ResponseWriter, r *http.Request) { func ProcessGroup(f func(w http.ResponseWriter, r *http.Request), m []MiddlewareFunc) func(w http.ResponseWriter, r *http.Request) {
for _, middleware := range m { for _, middleware := range m {
middleware() _ = middleware(f)
} }
return f return f

57
restclient/client.go Normal file
View File

@ -0,0 +1,57 @@
package restclient
import (
"bytes"
"encoding/json"
"mime/multipart"
"net/http"
)
// SendRequest sends an HTTP request to a URL and includes the specified headers and body.
// A body can be nil for GET requests, a map[string]string for multipart/form-data requests,
// or a struct for JSON requests
func SendRequest(url string, method string, headers map[string]string, body interface{}) (http.Response, error) {
var reqBody *bytes.Buffer
var contentType string
switch v := body.(type) {
case nil:
reqBody = bytes.NewBuffer([]byte(""))
case map[string]string:
reqBody = &bytes.Buffer{}
writer := multipart.NewWriter(reqBody)
for key, value := range v {
writer.WriteField(key, value)
}
writer.Close()
contentType = writer.FormDataContentType()
default:
jsonBody, err := json.Marshal(body)
if err != nil {
return http.Response{}, err
}
reqBody = bytes.NewBuffer(jsonBody)
contentType = "application/json"
}
req, err := http.NewRequest(method, url, reqBody)
if err != nil {
return http.Response{}, err
}
if contentType != "" {
req.Header.Set("Content-Type", contentType)
}
for key, value := range headers {
req.Header.Add(key, value)
}
client := &http.Client{}
resp, err := client.Do(req)
if err != nil {
return http.Response{}, err
}
return *resp, nil
}

View File

@ -15,6 +15,6 @@ func PostRoutes(app *app.App) {
} }
// User authentication // User authentication
http.HandleFunc("/register-handle", middleware.CsrfMiddleware(postController.Register)) http.HandleFunc("/register-handle", middleware.Csrf(postController.Register))
http.HandleFunc("/login-handle", middleware.CsrfMiddleware(postController.Login)) http.HandleFunc("/login-handle", middleware.Csrf(postController.Login))
} }