This commit is contained in:
2026-09-15 09:15:53 -05:00
parent 97c930196a
commit ab9573b875
21 changed files with 1664 additions and 0 deletions
+100
View File
@@ -0,0 +1,100 @@
package api
import (
"fmt"
"net/http"
"github.com/gin-contrib/sessions"
"github.com/gin-gonic/gin"
"golang.org/x/crypto/bcrypt"
"jp.wtf/go-fishing/internal/models"
)
type CreateAnglerRequest struct {
Username string `json:"username" binding:"required"`
Password string `json:"password" binding:"required"`
}
type Response struct {
Data any `json:"$data,omitempty"`
Meta *APIMetadata `json:"$meta,omitempty"`
Error *APIError `json:"$error,omitempty"`
}
type APIMetadata struct {
Version string `json:"version,omitempty"`
}
type APIErrorCode string
const (
APIErrorCodeUnknown APIErrorCode = "API_ERR_UNKNOWN"
APIErrorCodeUnauthorized APIErrorCode = "API_ERR_UNAUTHORIZED"
APIErrorCodeNotFound APIErrorCode = "API_ERR_NOT_FOUND"
APIErrorCodeInvalidBody APIErrorCode = "API_ERR_INVALID_BODY"
APIErrorCodeInvalidRequest APIErrorCode = "API_ERR_INVALID_REQUEST"
)
type APIError struct {
Code APIErrorCode `json:"code"`
Message string `json:"message"`
}
func SendJSONResponse(c *gin.Context, status int, response Response) {
c.JSON(status, response)
}
func OK(c *gin.Context, data any) {
SendJSONResponse(c, http.StatusOK, Response{
Data: data,
Meta: &APIMetadata{
Version: c.GetString("APIVersion"),
},
})
}
func Fail(c *gin.Context, status int, code APIErrorCode, message string) {
SendJSONResponse(c, status, Response{
Error: &APIError{
Code: code,
Message: message,
},
})
}
func FailAndAbort(c *gin.Context, status int, code APIErrorCode, message string) {
Fail(c, status, code, message)
c.Abort()
}
func CheckIfLoggedIn(c *gin.Context) bool {
s := sessions.Default(c)
val := s.Get("angler_id")
return val != nil && val != ""
}
func GetAnglerFromSession(c *gin.Context) (models.Angler, error) {
val, exists := c.Get("angler")
if !exists {
return models.Angler{}, fmt.Errorf("No angler")
}
angler, ok := val.(models.Angler)
if !ok {
return models.Angler{}, fmt.Errorf("Malformed or invalid angler")
}
return angler, nil
}
func HashPassword(password string) (string, error) {
bytes, err := bcrypt.GenerateFromPassword([]byte(password), bcrypt.DefaultCost)
return string(bytes), err
}
func CheckPassword(password, hash string) bool {
err := bcrypt.CompareHashAndPassword([]byte(hash), []byte(password))
return err == nil
}