From fec67b0e33f7f935aced90fc4dc772584574fc31 Mon Sep 17 00:00:00 2001 From: Tyrel Souza Date: Tue, 18 Jun 2024 00:37:32 -0400 Subject: [PATCH] Initial Project commit --- .gitignore | 1 + Dockerfile | 28 +++++++++++++ README.md | 0 controllers/author.go | 77 ++++++++++++++++++++++++++++++++++ controllers/format.go | 77 ++++++++++++++++++++++++++++++++++ controllers/order.go | 81 +++++++++++++++++++++++++++++++++++ create_database.sql | 1 + docker-compose.yaml | 29 +++++++++++++ entrypoint.sh | 15 +++++++ go.mod | 33 +++++++++++++++ go.sum | 98 +++++++++++++++++++++++++++++++++++++++++++ main.go | 33 +++++++++++++++ models/author.go | 15 +++++++ models/format.go | 15 +++++++ models/models.go | 26 ++++++++++++ models/order.go | 27 ++++++++++++ test.http | 3 ++ 17 files changed, 559 insertions(+) create mode 100644 .gitignore create mode 100644 Dockerfile create mode 100644 README.md create mode 100644 controllers/author.go create mode 100644 controllers/format.go create mode 100644 controllers/order.go create mode 100644 create_database.sql create mode 100644 docker-compose.yaml create mode 100755 entrypoint.sh create mode 100644 go.mod create mode 100644 go.sum create mode 100644 main.go create mode 100644 models/author.go create mode 100644 models/format.go create mode 100644 models/models.go create mode 100644 models/order.go create mode 100644 test.http diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..7d91189 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +preorder diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..b13ec72 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,28 @@ +# Dockerfile for building the preorder service image +FROM debian:latest + +# Update the package list and install MySQL client +RUN apt-get update && apt-get install -y \ + mariadb-client \ + && rm -rf /var/lib/apt/lists/* + +# Copy the preorder binary from the local directory into the container +COPY ./preorder /usr/local/bin/preorder + +# Set executable permissions on the binary +RUN chmod +x /usr/local/bin/preorder + + +# Copy the entrypoint script +#COPY entrypoint.sh /usr/local/bin/entrypoint.sh +#RUN chmod +x /usr/local/bin/entrypoint.sh +# +## Copy the SQL script to the container +#COPY create_database.sql /docker-entrypoint-initdb.d/create_database.sql +# +## Set the entrypoint script +#ENTRYPOINT ["/usr/local/bin/entrypoint.sh"] +# +# Specify the command to run when the container starts +CMD ["/usr/local/bin/preorder"] + diff --git a/README.md b/README.md new file mode 100644 index 0000000..e69de29 diff --git a/controllers/author.go b/controllers/author.go new file mode 100644 index 0000000..f02b07c --- /dev/null +++ b/controllers/author.go @@ -0,0 +1,77 @@ +package controllers + +import ( + "net/http" + "preorder/models" + + "github.com/gin-gonic/gin" +) + +func FindAuthors(c *gin.Context) { + var Authors []models.Author + models.DB.Find(&Authors) + + c.JSON(http.StatusOK, gin.H{"data": Authors}) +} + +func FindAuthor(c *gin.Context) { + var Author models.Author + + if err := models.DB.Where("id = ?", c.Param("id")).First(&Author).Error; err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": "Record not found!"}) + } + + c.JSON(http.StatusOK, gin.H{"data": Author}) +} + +func CreateAuthor(c *gin.Context) { + var input models.CreateAuthorInput + if err := c.ShouldBindJSON(&input); err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) + return + } + + Author := models.Author{ + ID: input.ID, + FullName: input.FullName, + } + models.DB.Create(&Author) + c.JSON(http.StatusOK, gin.H{"data": Author}) +} + +func UpdateAuthor(c *gin.Context) { + var Author models.Author + if err := models.DB.Where("id = ?", c.Param("id")).First(&Author).Error; err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": "Record not found!"}) + } + + var input models.UpdateAuthorInput + if err := c.ShouldBindJSON(&input); err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) + return + } + + models.DB.Model(&Author).Updates(input) + c.JSON(http.StatusOK, gin.H{"data": Author}) +} + +func DeleteAuthor(c *gin.Context) { + var Author models.Author + if err := models.DB.Where("id = ?", c.Param("id")).First(&Author).Error; err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": "Record not found!"}) + return + } + + models.DB.Delete(&Author) + + c.JSON(http.StatusOK, gin.H{"data": true}) +} + +func ApplyAuthorRouter(router *gin.Engine) *gin.Engine { + router.GET("/authors", FindAuthors) + router.POST("/authors", CreateAuthor) + router.GET("/authors/:id", FindAuthor) + router.PATCH("/authors/:id", UpdateAuthor) + router.DELETE("/authors/:id", DeleteAuthor) + return router +} diff --git a/controllers/format.go b/controllers/format.go new file mode 100644 index 0000000..2b78cef --- /dev/null +++ b/controllers/format.go @@ -0,0 +1,77 @@ +package controllers + +import ( + "net/http" + "preorder/models" + + "github.com/gin-gonic/gin" +) + +func FindFormats(c *gin.Context) { + var Formats []models.Format + models.DB.Find(&Formats) + + c.JSON(http.StatusOK, gin.H{"data": Formats}) +} + +func FindFormat(c *gin.Context) { + var Format models.Format + + if err := models.DB.Where("id = ?", c.Param("id")).First(&Format).Error; err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": "Record not found!"}) + } + + c.JSON(http.StatusOK, gin.H{"data": Format}) +} + +func CreateFormat(c *gin.Context) { + var input models.CreateFormatInput + if err := c.ShouldBindJSON(&input); err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) + return + } + + Format := models.Format{ + ID: input.ID, + Format: input.Format, + } + models.DB.Create(&Format) + c.JSON(http.StatusOK, gin.H{"data": Format}) +} + +func UpdateFormat(c *gin.Context) { + var Format models.Format + if err := models.DB.Where("id = ?", c.Param("id")).First(&Format).Error; err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": "Record not found!"}) + } + + var input models.UpdateFormatInput + if err := c.ShouldBindJSON(&input); err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) + return + } + + models.DB.Model(&Format).Updates(input) + c.JSON(http.StatusOK, gin.H{"data": Format}) +} + +func DeleteFormat(c *gin.Context) { + var Format models.Format + if err := models.DB.Where("id = ?", c.Param("id")).First(&Format).Error; err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": "Record not found!"}) + return + } + + models.DB.Delete(&Format) + + c.JSON(http.StatusOK, gin.H{"data": true}) +} + +func ApplyFormatRouter(router *gin.Engine) *gin.Engine { + router.GET("/formats", FindFormats) + router.POST("/formats", CreateFormat) + router.GET("/formats/:id", FindFormat) + router.PATCH("/formats/:id", UpdateFormat) + router.DELETE("/formats/:id", DeleteFormat) + return router +} diff --git a/controllers/order.go b/controllers/order.go new file mode 100644 index 0000000..f991c75 --- /dev/null +++ b/controllers/order.go @@ -0,0 +1,81 @@ +package controllers + +import ( + "net/http" + "preorder/models" + + "github.com/gin-gonic/gin" +) + +func FindOrders(c *gin.Context) { + var Orders []models.Order + models.DB.Find(&Orders) + + c.JSON(http.StatusOK, gin.H{"data": Orders}) +} + +func FindOrder(c *gin.Context) { + var Order models.Order + + if err := models.DB.Where("id = ?", c.Param("id")).First(&Order).Error; err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": "Record not found!"}) + } + + c.JSON(http.StatusOK, gin.H{"data": Order}) +} + +func CreateOrder(c *gin.Context) { + var input models.CreateOrderInput + if err := c.ShouldBindJSON(&input); err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) + return + } + + Order := models.Order{ + ID: input.ID, + Title: input.Title, + AuthorID: input.Author, + FormatID: input.Format, + ISBN13: input.ISBN13, + ReleaseDate: input.ReleaseDate, + } + models.DB.Create(&Order) + c.JSON(http.StatusOK, gin.H{"data": Order}) +} + +func UpdateOrder(c *gin.Context) { + var Order models.Order + if err := models.DB.Where("id = ?", c.Param("id")).First(&Order).Error; err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": "Record not found!"}) + } + + var input models.UpdateOrderInput + if err := c.ShouldBindJSON(&input); err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) + return + } + + models.DB.Model(&Order).Updates(input) + c.JSON(http.StatusOK, gin.H{"data": Order}) +} + +func DeleteOrder(c *gin.Context) { + var Order models.Order + if err := models.DB.Where("id = ?", c.Param("id")).First(&Order).Error; err != nil { + c.JSON(http.StatusBadRequest, gin.H{"error": "Record not found!"}) + return + } + + models.DB.Delete(&Order) + + c.JSON(http.StatusOK, gin.H{"data": true}) +} + +func ApplyOrderRouter(router *gin.Engine) *gin.Engine { + router.GET("/orders", FindOrders) + router.POST("/orders", CreateOrder) + router.GET("/orders/:id", FindOrder) + router.PATCH("/orders/:id", UpdateOrder) + router.DELETE("/orders/:id", DeleteOrder) + return router +} diff --git a/create_database.sql b/create_database.sql new file mode 100644 index 0000000..bc63584 --- /dev/null +++ b/create_database.sql @@ -0,0 +1 @@ +CREATE DATABASE IF NOT EXISTS db; diff --git a/docker-compose.yaml b/docker-compose.yaml new file mode 100644 index 0000000..922eecd --- /dev/null +++ b/docker-compose.yaml @@ -0,0 +1,29 @@ +version: '3.8' + +services: + db: + image: mariadb + restart: always + environment: + MYSQL_ROOT_PASSWORD: password + MYSQL_DATABASE: db + MYSQL_USER: mysql + MYSQL_PASSWORD: password + ports: + - "3306:3306" + volumes: + - mariadb_data:/var/lib/mysql + + api: + build: + context: . + dockerfile: Dockerfile + restart: always + ports: + - "8123:8123" + depends_on: + - db + +volumes: + mariadb_data: + driver: local diff --git a/entrypoint.sh b/entrypoint.sh new file mode 100755 index 0000000..202a174 --- /dev/null +++ b/entrypoint.sh @@ -0,0 +1,15 @@ +#!/bin/bash +set -e + +# Wait for the database to be ready +while ! mysqladmin ping -h"db" --silent; do + echo "Waiting for database connection..." + sleep 2 +done + +# Run the SQL script to initialize the database +mysql -h db -uroot -p$MYSQL_ROOT_PASSWORD < /docker-entrypoint-initdb.d/create_database.sql + +# Execute the original command +exec "$@" + diff --git a/go.mod b/go.mod new file mode 100644 index 0000000..cf9e673 --- /dev/null +++ b/go.mod @@ -0,0 +1,33 @@ +module preorder + +go 1.19 + +require ( + github.com/gin-gonic/gin v1.8.1 + gorm.io/driver/mysql v1.4.1 + gorm.io/gorm v1.24.0 +) + +require ( + github.com/gin-contrib/sse v0.1.0 // indirect + github.com/go-playground/locales v0.14.0 // indirect + github.com/go-playground/universal-translator v0.18.0 // indirect + github.com/go-playground/validator/v10 v10.10.0 // indirect + github.com/go-sql-driver/mysql v1.6.0 // indirect + github.com/goccy/go-json v0.9.7 // indirect + github.com/jinzhu/inflection v1.0.0 // indirect + github.com/jinzhu/now v1.1.5 // indirect + github.com/json-iterator/go v1.1.12 // indirect + github.com/leodido/go-urn v1.2.1 // indirect + github.com/mattn/go-isatty v0.0.14 // indirect + github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421 // indirect + github.com/modern-go/reflect2 v1.0.2 // indirect + github.com/pelletier/go-toml/v2 v2.0.1 // indirect + github.com/ugorji/go/codec v1.2.7 // indirect + golang.org/x/crypto v0.0.0-20210711020723-a769d52b0f97 // indirect + golang.org/x/net v0.0.0-20210226172049-e18ecbb05110 // indirect + golang.org/x/sys v0.0.0-20210806184541-e5e7981a1069 // indirect + golang.org/x/text v0.3.6 // indirect + google.golang.org/protobuf v1.28.0 // indirect + gopkg.in/yaml.v2 v2.4.0 // indirect +) diff --git a/go.sum b/go.sum new file mode 100644 index 0000000..45621d2 --- /dev/null +++ b/go.sum @@ -0,0 +1,98 @@ +github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= +github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= +github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/gin-contrib/sse v0.1.0 h1:Y/yl/+YNO8GZSjAhjMsSuLt29uWRFHdHYUb5lYOV9qE= +github.com/gin-contrib/sse v0.1.0/go.mod h1:RHrZQHXnP2xjPF+u1gW/2HnVO7nvIa9PG3Gm+fLHvGI= +github.com/gin-gonic/gin v1.8.1 h1:4+fr/el88TOO3ewCmQr8cx/CtZ/umlIRIs5M4NTNjf8= +github.com/gin-gonic/gin v1.8.1/go.mod h1:ji8BvRH1azfM+SYow9zQ6SZMvR8qOMZHmsCuWR9tTTk= +github.com/go-playground/assert/v2 v2.0.1 h1:MsBgLAaY856+nPRTKrp3/OZK38U/wa0CcBYNjji3q3A= +github.com/go-playground/assert/v2 v2.0.1/go.mod h1:VDjEfimB/XKnb+ZQfWdccd7VUvScMdVu0Titje2rxJ4= +github.com/go-playground/locales v0.14.0 h1:u50s323jtVGugKlcYeyzC0etD1HifMjqmJqb8WugfUU= +github.com/go-playground/locales v0.14.0/go.mod h1:sawfccIbzZTqEDETgFXqTho0QybSa7l++s0DH+LDiLs= +github.com/go-playground/universal-translator v0.18.0 h1:82dyy6p4OuJq4/CByFNOn/jYrnRPArHwAcmLoJZxyho= +github.com/go-playground/universal-translator v0.18.0/go.mod h1:UvRDBj+xPUEGrFYl+lu/H90nyDXpg0fqeB/AQUGNTVA= +github.com/go-playground/validator/v10 v10.10.0 h1:I7mrTYv78z8k8VXa/qJlOlEXn/nBh+BF8dHX5nt/dr0= +github.com/go-playground/validator/v10 v10.10.0/go.mod h1:74x4gJWsvQexRdW8Pn3dXSGrTK4nAUsbPlLADvpJkos= +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/goccy/go-json v0.9.7 h1:IcB+Aqpx/iMHu5Yooh7jEzJk1JZ7Pjtmys2ukPr7EeM= +github.com/goccy/go-json v0.9.7/go.mod h1:6MelG93GURQebXPDq3khkgXZkazVtN9CRI+MGFi0w8I= +github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= +github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU= +github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= +github.com/jinzhu/inflection v1.0.0 h1:K317FqzuhWc8YvSVlFMCCUb36O/S9MCKRDI7QkRKD/E= +github.com/jinzhu/inflection v1.0.0/go.mod h1:h+uFLlag+Qp1Va5pdKtLDYj+kHp5pxUVkryuEj+Srlc= +github.com/jinzhu/now v1.1.4/go.mod h1:d3SSVoowX0Lcu0IBviAWJpolVfI5UJVZZ7cO71lE/z8= +github.com/jinzhu/now v1.1.5 h1:/o9tlHleP7gOFmsnYNz3RGnqzefHA47wQpKrrdTIwXQ= +github.com/jinzhu/now v1.1.5/go.mod h1:d3SSVoowX0Lcu0IBviAWJpolVfI5UJVZZ7cO71lE/z8= +github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= +github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= +github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= +github.com/kr/pretty v0.2.1/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= +github.com/kr/pretty v0.3.0 h1:WgNl7dwNpEZ6jJ9k1snq4pZsg7DOEN8hP9Xw0Tsjwk0= +github.com/kr/pretty v0.3.0/go.mod h1:640gp4NfQd8pI5XOwp5fnNeVWj67G7CFk/SaSQn7NBk= +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.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= +github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= +github.com/leodido/go-urn v1.2.1 h1:BqpAaACuzVSgi/VLzGZIobT2z4v53pjosyNd9Yv6n/w= +github.com/leodido/go-urn v1.2.1/go.mod h1:zt4jvISO2HfUBqxjfIshjdMTYS56ZS/qv49ictyFfxY= +github.com/mattn/go-isatty v0.0.14 h1:yVuAays6BHfxijgZPzw+3Zlu5yQgKGP2/hcQbHb7S9Y= +github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94= +github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421 h1:ZqeYNhU3OHLH3mGKHDcjJRFFRrJa6eAM5H+CtDdOsPc= +github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= +github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= +github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= +github.com/pelletier/go-toml/v2 v2.0.1 h1:8e3L2cCQzLFi2CR4g7vGFuFxX7Jl1kKX8gW+iV0GUKU= +github.com/pelletier/go-toml/v2 v2.0.1/go.mod h1:r9LEWfGN8R5k0VXJ+0BkIe7MYkRdwZOjgMj2KwnJFUo= +github.com/pkg/diff v0.0.0-20210226163009-20ebb0f2a09e/go.mod h1:pJLUxLENpZxwdsKMEsNbx1VGcRFpLqf3715MtcvvzbA= +github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= +github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/rogpeppe/go-internal v1.6.1/go.mod h1:xXDCJY+GAPziupqXw64V24skbSoqbTEfhy4qGm1nDQc= +github.com/rogpeppe/go-internal v1.8.0 h1:FCbCCtXNOY3UtUuHUYaghJg4y7Fd14rXifAYUAtL9R8= +github.com/rogpeppe/go-internal v1.8.0/go.mod h1:WmiCO8CzOY8rg0OYDC4/i/2WRWAB6poM+XZ2dLUbcbE= +github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= +github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.7.1 h1:5TQK59W5E3v0r2duFAb7P95B6hEeOyEnHRa8MjYSMTY= +github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/ugorji/go v1.2.7/go.mod h1:nF9osbDWLy6bDVv/Rtoh6QgnvNDpmCalQV5urGCCS6M= +github.com/ugorji/go/codec v1.2.7 h1:YPXUKf7fYbp/y8xloBqZOw2qaVggbfwMlI8WM3wZUJ0= +github.com/ugorji/go/codec v1.2.7/go.mod h1:WGN1fab3R1fzQlVQTkfxVtIBhWDRqOviHU95kRgeqEY= +golang.org/x/crypto v0.0.0-20210711020723-a769d52b0f97 h1:/UOmuWzQfxxo9UtlXMwuQU8CMgg1eZXqTRwkSQJWKOI= +golang.org/x/crypto v0.0.0-20210711020723-a769d52b0f97/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= +golang.org/x/net v0.0.0-20210226172049-e18ecbb05110 h1:qWPm9rbaAMKs8Bq/9LRpbMqxWRVUAQwMI9fVrssnTfw= +golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210806184541-e5e7981a1069 h1:siQdpVirKtzPhKl3lZWozZraCFObP8S1v6PRp0bLrtU= +golang.org/x/sys v0.0.0-20210806184541-e5e7981a1069/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= +golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/text v0.3.6 h1:aRYxNxv6iGQlyVaZmk6ZgYEDa+Jg18DxebPSrd6bg1M= +golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= +google.golang.org/protobuf v1.28.0 h1:w43yiav+6bVFTBQFZX0r7ipe9JQ1QsbMgHwbBziscLw= +google.golang.org/protobuf v1.28.0/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q= +gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI= +gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= +gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= +gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo= +gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gorm.io/driver/mysql v1.4.1 h1:4InA6SOaYtt4yYpV1NF9B2kvUKe9TbvUd1iWrvxnjic= +gorm.io/driver/mysql v1.4.1/go.mod h1:sSIebwZAVPiT+27jK9HIwvsqOGKx3YMPmrA3mBJR10c= +gorm.io/gorm v1.23.8/go.mod h1:l2lP/RyAtc1ynaTjFksBde/O8v9oOGIApu2/xRitmZk= +gorm.io/gorm v1.24.0 h1:j/CoiSm6xpRpmzbFJsQHYj+I8bGYWLXVHeYEyyKlF74= +gorm.io/gorm v1.24.0/go.mod h1:DVrVomtaYTbqs7gB/x2uVvqnXzv0nqjB396B8cG4dBA= diff --git a/main.go b/main.go new file mode 100644 index 0000000..f87cee3 --- /dev/null +++ b/main.go @@ -0,0 +1,33 @@ +package main + +import ( + "net/http" + "preorder/controllers" + "preorder/models" + + "github.com/gin-gonic/gin" +) + +func SetupRouter() *gin.Engine { + router := gin.Default() + router.GET("/ping", func(c *gin.Context) { + c.JSON(200, gin.H{"message": "pong"}) + }) + router = controllers.ApplyAuthorRouter(router) + router = controllers.ApplyFormatRouter(router) + router = controllers.ApplyOrderRouter(router) + + return router +} + +func main() { + router := SetupRouter() + + models.ConnectDatabase() + + s := &http.Server{ + Addr: ":8123", + Handler: router, + } + s.ListenAndServe() +} diff --git a/models/author.go b/models/author.go new file mode 100644 index 0000000..2c531b1 --- /dev/null +++ b/models/author.go @@ -0,0 +1,15 @@ +package models + +type Author struct { + ID uint `json:"id" gorm:"primary_key"` + FullName string `json:"full_name"` +} + +type CreateAuthorInput struct { + ID uint `json:"id" binding:"required"` + FullName string `json:"full_name" binding:"required"` +} + +type UpdateAuthorInput struct { + FullName string `json:"full_name"` +} diff --git a/models/format.go b/models/format.go new file mode 100644 index 0000000..9cffee6 --- /dev/null +++ b/models/format.go @@ -0,0 +1,15 @@ +package models + +type Format struct { + ID uint `json:"id" gorm:"primary_key"` + Format string `json:"format"` +} + +type CreateFormatInput struct { + ID uint `json:"id" binding:"required"` + Format string `json:"format" binding:"required"` +} + +type UpdateFormatInput struct { + Format string `json:"format"` +} diff --git a/models/models.go b/models/models.go new file mode 100644 index 0000000..06eaf43 --- /dev/null +++ b/models/models.go @@ -0,0 +1,26 @@ +package models + +import ( + "gorm.io/driver/mysql" + "gorm.io/gorm" +) + +var DB *gorm.DB + +func ConnectDatabase() { + // Obviously change this to your settings and get securely. + //dsn := "root@unix(/var/run/mysqld/mysqld.sock)/db?charset=utf8mb4&parseTime=True&loc=Local" + //db, err := gorm.Open(mysql.New(mysql.Config{ + // DSN: dsn, + //}), &gorm.Config{}) + dsn := "root:password@tcp(db:3306)/db?charset=utf8mb4&parseTime=True&loc=Local" + db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{}) + if err != nil { + panic("Failed to connect to database") + } + _ = db.AutoMigrate(&Author{}) + _ = db.AutoMigrate(&Format{}) + _ = db.AutoMigrate(&Order{}) + + DB = db +} diff --git a/models/order.go b/models/order.go new file mode 100644 index 0000000..9222e00 --- /dev/null +++ b/models/order.go @@ -0,0 +1,27 @@ +package models + +import "time" + +type Order struct { + ID uint `json:"id" gorm:"primary_key"` + Title string `json:"title"` + AuthorID uint `json:"author"` + Author Author + ReleaseDate time.Time `json:"release_date" gorm:"column:release_date"` + ISBN13 uint `json:"isbn_13" gorm:"column:isbn_13"` + FormatID uint `json:"format"` + Format Format +} + +type CreateOrderInput struct { + ID uint `json:"id" binding:"required"` + Title string `json:"title" binding:"required"` + Author uint `json:"author" binding:"required"` + Format uint `json:"format" binding:"required"` + ReleaseDate time.Time `json:"release_date"` + ISBN13 uint `json:"isbn_13" binding:"required"` +} + +type UpdateOrderInput struct { + Title string `json:"title"` +} diff --git a/test.http b/test.http new file mode 100644 index 0000000..68c755e --- /dev/null +++ b/test.http @@ -0,0 +1,3 @@ +### +GET http://localhost:8123/orders +Content-Type: application/json