From 71fe2a5e460bf7696d1fed947658f770115c6998 Mon Sep 17 00:00:00 2001 From: Alex Date: Fri, 14 May 2021 22:34:47 +0200 Subject: [PATCH] start with login sessions --- config.toml | 1 + example.http | 8 +++--- go.mod | 2 ++ go.sum | 14 ++++++++++ main.go | 11 ++++---- modules/config/config.go | 5 ++-- routers/api/v1/user/user.go | 52 ++++++++++++++++++++++++++++++++----- routers/router/router.go | 28 ++++++++++++++++++-- scheme.sql | 2 +- 9 files changed, 104 insertions(+), 19 deletions(-) diff --git a/config.toml b/config.toml index 770dc56..d39c283 100644 --- a/config.toml +++ b/config.toml @@ -1,6 +1,7 @@ [server] debug = true host = "127.0.0.1:3000" +secret = "KAWXQHtKaz8BmWksXsQFPrdE78ptBuwBsaUNt8XcKGZt44QbUp" [database] host = "127.0.0.1:3306" diff --git a/example.http b/example.http index 0b63620..7c96c52 100644 --- a/example.http +++ b/example.http @@ -1,7 +1,9 @@ ### GET http://localhost:3000/api/v1/users - +Content-Type: application/xml +# Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE2MjEyNTAxODcsInVzZXJfaGFzaHRhZyI6IjRIUVQ3NSIsInVzZXJfaWQiOiJhZDAyYzY2NzRmYjI0OWY0YWI4NWU1MjYzZDUyMzAwZiIsInVzZXJuYW1lIjoicnVpc3BpcGUxIn0.wJJO_2maGG_1h2hingzZm3VmNJnmQnpzknU4dnw-8IE +Cookie: session_id=b81aedb75b084d01945ee45134ddbc39; ### @@ -9,7 +11,7 @@ POST http://localhost:3000/api/v1/users Content-Type: application/json { - "username": "151", - "email": "151@roese.dev", + "username": "183", + "email": "183@roese.dev", "password": "teksmkamsdkasd- a , ' . + * maskdmaskdm" } \ No newline at end of file diff --git a/go.mod b/go.mod index 83594a2..8669bed 100644 --- a/go.mod +++ b/go.mod @@ -5,8 +5,10 @@ go 1.16 require ( github.com/BurntSushi/toml v0.3.1 github.com/andybalholm/brotli v1.0.2 // indirect + github.com/form3tech-oss/jwt-go v3.2.3+incompatible // indirect github.com/go-sql-driver/mysql v1.6.0 github.com/gofiber/fiber/v2 v2.8.0 + github.com/gofiber/jwt/v2 v2.2.1 // indirect github.com/google/uuid v1.2.0 github.com/klauspost/compress v1.12.2 // indirect github.com/kr/text v0.2.0 // indirect diff --git a/go.sum b/go.sum index dd74847..19d06e7 100644 --- a/go.sum +++ b/go.sum @@ -1,17 +1,25 @@ github.com/BurntSushi/toml v0.3.1 h1:WXkYYl6Yr3qBf1K79EBnL4mak0OimBfB0XUf9Vl28OQ= github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= +github.com/andybalholm/brotli v1.0.0/go.mod h1:loMXtMfwqflxFJPmdbJO0a3KNoPuLBgiu3qAvBg8x/Y= github.com/andybalholm/brotli v1.0.1/go.mod h1:loMXtMfwqflxFJPmdbJO0a3KNoPuLBgiu3qAvBg8x/Y= github.com/andybalholm/brotli v1.0.2 h1:JKnhI/XQ75uFBTiuzXpzFrUriDPiZjlOSzh6wXogP0E= github.com/andybalholm/brotli v1.0.2/go.mod h1:loMXtMfwqflxFJPmdbJO0a3KNoPuLBgiu3qAvBg8x/Y= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/form3tech-oss/jwt-go v3.2.2+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= +github.com/form3tech-oss/jwt-go v3.2.3+incompatible h1:7ZaBxOI7TMoYBfyA3cQHErNNyAWIKUMIwqxEtgHOs5c= +github.com/form3tech-oss/jwt-go v3.2.3+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= github.com/go-sql-driver/mysql v1.6.0 h1:BCTh4TKNUYmOmMUcQ3IipzF5prigylS7XXjEkfCHuOE= github.com/go-sql-driver/mysql v1.6.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg= +github.com/gofiber/fiber/v2 v2.7.1/go.mod h1:f8BRRIMjMdRyt2qmJ/0Sea3j3rwwfufPrh9WNBRiVZ0= github.com/gofiber/fiber/v2 v2.8.0 h1:BdWvZmg/WY/Vjtjm38aXOp1Lks1BhuyS2b7lSWSPAzk= github.com/gofiber/fiber/v2 v2.8.0/go.mod h1:Ah3IJikrKNRepl/HuVawppS25X7FWohwfCSRn7kJG28= +github.com/gofiber/jwt/v2 v2.2.1 h1:nphRrLNB3t0b7Y2IgHOwv5HXggO1/GBsDSBysCTatHo= +github.com/gofiber/jwt/v2 v2.2.1/go.mod h1:PC746ApJVpoQH3I98kmnLGjUM08b8qYVMlaTiNlV0Ao= github.com/golang/snappy v0.0.3/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= github.com/google/uuid v1.2.0 h1:qJYtXnJRWmpe7m/3XlyhrsLrEURqHRM2kxzoxXqyUDs= github.com/google/uuid v1.2.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/klauspost/compress v1.10.7/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdYsUV+/s2qKfXs= github.com/klauspost/compress v1.11.8/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdYsUV+/s2qKfXs= github.com/klauspost/compress v1.11.13/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdYsUV+/s2qKfXs= github.com/klauspost/compress v1.12.2 h1:2KCfW3I9M7nSc5wOqXAlW2v2U6v+w6cbjvbfp+OykW8= @@ -30,6 +38,7 @@ github.com/sirupsen/logrus v1.8.1/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/valyala/bytebufferpool v1.0.0 h1:GqA5TC/0021Y/b9FG4Oi9Mr3q7XYx6KllzawFIhcdPw= github.com/valyala/bytebufferpool v1.0.0/go.mod h1:6bBcMArwyJ5K/AmCkWv1jt77kVWyCJ6HpOuEn7z0Csc= +github.com/valyala/fasthttp v1.18.0/go.mod h1:jjraHZVbKOXftJfsOYoAjaeygpj5hr8ermTRJNroD7A= github.com/valyala/fasthttp v1.23.0/go.mod h1:0mw2RjXGOzxf4NL2jni3gUQ7LfjjUSiG5sskOUUSEpU= github.com/valyala/fasthttp v1.24.0 h1:AAiG4oLDUArTb7rYf9oO2bkGooOqCaUF6a2u8asBP3I= github.com/valyala/fasthttp v1.24.0/go.mod h1:0mw2RjXGOzxf4NL2jni3gUQ7LfjjUSiG5sskOUUSEpU= @@ -39,15 +48,20 @@ github.com/valyala/tcplisten v1.0.0/go.mod h1:T0xQ8SeCZGxckz9qRXTfG43PvQ/mcWh7Fw github.com/zhengxiaowai/shortuuid v0.0.0-20181208145701-0c38c76c12b3 h1:03r8Xo0XhTGIMuyJ9x3yrYCumC+T4ycXShfW+Le3Sts= github.com/zhengxiaowai/shortuuid v0.0.0-20181208145701-0c38c76c12b3/go.mod h1:bxh5+Ghwiy6UJxDAPpoOB/L+dq0To9dky7x92nWeSKU= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20210220033148-5ea612d1eb83/go.mod h1:jdWPYTVW3xRLrWPugEBEK3UY2ZEsg3UU495nc5E+M+I= golang.org/x/crypto v0.0.0-20210506145944-38f3c27a63bf h1:B2n+Zi5QeYRDAEodEu72OS36gmTWjgpXr2+cWcBW90o= golang.org/x/crypto v0.0.0-20210506145944-38f3c27a63bf/go.mod h1:P+XmwS30IXTQdn5tA2iutPOUgjI07+tq3H3K9MVA1s8= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20201016165138-7b1cca2348c0/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20210226101413-39120d07d75e/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20201210223839-7e3030f88018/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210225134936-a50acf3fe073/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210507161434-a76c4d0a0096 h1:5PbJGn5Sp3GEUjJ61aYbUP6RIo3Z3r2E4Tv9y2z8UHo= golang.org/x/sys v0.0.0-20210507161434-a76c4d0a0096/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= diff --git a/main.go b/main.go index 1017fe2..dddc6fe 100644 --- a/main.go +++ b/main.go @@ -34,17 +34,18 @@ import ( func main() { app := fiber.New() - router.SetupRoutes(app) - config.LoadConfig() - if config.GetConfig().Server.Debug { + cfg := config.GetConfig() + + if cfg.Server.Debug { log.SetLevel(log.DebugLevel) } - database.InitDatabase() + router.SetupRoutes(app) - app.Listen(config.GetConfig().Server.Host) + database.InitDatabase() + app.Listen(cfg.Server.Host) } /* diff --git a/modules/config/config.go b/modules/config/config.go index 3b5f13f..efe8f24 100644 --- a/modules/config/config.go +++ b/modules/config/config.go @@ -13,8 +13,9 @@ type Config struct { } type server struct { - Debug bool - Host string + Debug bool + Host string + Secret string } type database struct { diff --git a/routers/api/v1/user/user.go b/routers/api/v1/user/user.go index e0524b1..9192b02 100644 --- a/routers/api/v1/user/user.go +++ b/routers/api/v1/user/user.go @@ -2,6 +2,7 @@ package user import ( "database/sql" + "encoding/base64" "fmt" "regexp" "strings" @@ -19,6 +20,13 @@ import ( //err = bcrypt.CompareHashAndPassword(hashedPassword, []byte("hello wolrd")) //fmt.Println(err) +type LoginInput struct { + Username string `json:"username"` + Email string `json:"email"` + Password string `json:"password"` + Hashtag string `json:"hashtag"` +} + func NewUser(c *fiber.Ctx) error { // swagger:operation POST /users user usersNewUser // --- @@ -60,12 +68,6 @@ func NewUser(c *fiber.Ctx) error { // description: format is not correct // '422': // description: username, email or/and hashtag already assigned - type LoginInput struct { - Username string `json:"username"` - Email string `json:"email"` - Password string `json:"password"` - Hashtag string `json:"hashtag"` - } var input LoginInput @@ -111,8 +113,26 @@ func NewUser(c *fiber.Ctx) error { stmt.Close() + expires := time.Now().Add(time.Hour * 72) + session_id := strings.Replace(uuid.New().String(), "-", "", -1) + + //h := sha256.New() + //h.Write([]byte(config.GetConfig().Server.Secret)) + //b := h.Sum([]byte(session_id)) + + //log.Infoln("sha256", h, base64.StdEncoding.EncodeToString(b)) + + stmt2, err := db.Prepare("INSERT INTO sessions (user_id, session_id, expires) VALUES (?, ?, ?);") + stmt2.Exec(user_id, session_id, expires) + + stmt2.Close() + log.Debugln("user created", user_id, input.Hashtag, input.Username, input.Email) + c.Cookie(&fiber.Cookie{Name: "session_id", Value: base64.StdEncoding.EncodeToString(b), Secure: true, HTTPOnly: true, Expires: expires}) + c.Cookie(&fiber.Cookie{Name: "username", Value: input.Username, Secure: true, Expires: expires}) + c.Cookie(&fiber.Cookie{Name: "user_hashtag", Value: input.Hashtag, Secure: true, Expires: expires}) + return c.SendStatus(fiber.StatusCreated) } @@ -192,11 +212,31 @@ func isEmailAvailable(db *sql.DB, e string) bool { return false } +func SessionIdCheck(c *fiber.Ctx) error { + session_id := c.Cookies("session_id") + + log.Infoln("session_id", session_id) + + db, err := database.GetDatabase() + + if db == nil || err != nil { + return c.SendStatus(fiber.StatusInternalServerError) + } + + defer db.Close() + + return fiber.ErrUnauthorized +} + func GetUser(c *fiber.Ctx) error { return c.SendString("user") } func GetUsers(c *fiber.Ctx) error { + cookie := c.Cookies("session_id") + + log.Infoln("cookies", cookie) + db, err := database.GetDatabase() // c.Params("id") diff --git a/routers/router/router.go b/routers/router/router.go index 3a769cb..4fe8ee9 100644 --- a/routers/router/router.go +++ b/routers/router/router.go @@ -3,16 +3,40 @@ package router import ( "git.umbach.dev/app-idea/rest-api/routers/api/v1/user" + jwt "github.com/form3tech-oss/jwt-go" "github.com/gofiber/fiber/v2" ) +/* +func Protected() fiber.Handler { + return jwtware.New(jwtware.Config{ + SigningKey: []byte(config.GetConfig().Server.Secret), + ErrorHandler: jwtError, + }) +} + +func jwtError(c *fiber.Ctx, err error) error { + if err.Error() == "Missing or malformed JWT" { + return c.Status(fiber.StatusBadRequest).JSON(fiber.Map{"message": "Missing or malformed JWT"}) + } + return c.Status(fiber.StatusUnauthorized).JSON(fiber.Map{"message": "Invalid or expired JWT"}) +} */ + +func Test(c *fiber.Ctx) error { + usert := c.Locals("user").(*jwt.Token) + claims := usert.Claims.(jwt.MapClaims) + name := claims["username"].(string) + return c.SendString("Welcome" + name) +} + func SetupRoutes(app *fiber.App) { api := app.Group("/api/v1") + /* Unauthenticated routes */ + app.Get("/user", user.GetUser) - // Users users := api.Group("/users") - users.Get("/", user.GetUsers) users.Post("/", user.NewUser) + users.Get("/", user.SessionIdCheck, user.GetUsers) } diff --git a/scheme.sql b/scheme.sql index d0838c1..8361f35 100644 --- a/scheme.sql +++ b/scheme.sql @@ -9,7 +9,7 @@ -- CREATE TABLE `users` ( - `user_id` varchar(36) NOT NULL, + `user_id` varchar(32) NOT NULL, `user_hashtag` varchar(6) NOT NULL, `username` varchar(30) NOT NULL, `email` varchar(200) NOT NULL,