diff options
| -rw-r--r-- | auth/controller.go | 52 | ||||
| -rw-r--r-- | auth/middleware.go | 4 | ||||
| -rw-r--r-- | customer/controller.go | 10 | ||||
| -rw-r--r-- | customer/customer.go | 25 | ||||
| -rw-r--r-- | customer/hooks.go | 2 | ||||
| -rw-r--r-- | db/db.go | 6 | ||||
| -rw-r--r-- | errors/errors.go | 56 | ||||
| -rw-r--r-- | errors/status.go | 4 | ||||
| -rw-r--r-- | info.go | 4 | ||||
| -rw-r--r-- | invoice/controller.go | 40 | ||||
| -rw-r--r-- | invoice/hooks.go | 2 | ||||
| -rw-r--r-- | invoice/invoice.go | 21 | ||||
| -rw-r--r-- | invoice/validators.go | 2 | ||||
| -rw-r--r-- | item/controller.go | 10 | ||||
| -rw-r--r-- | item/item.go | 1 | ||||
| -rw-r--r-- | main.go | 6 | ||||
| -rw-r--r-- | user/controller.go | 24 | ||||
| -rw-r--r-- | user/service.go | 2 | ||||
| -rw-r--r-- | user/user.go | 15 | ||||
| -rw-r--r-- | user/validators.go | 68 | ||||
| -rw-r--r-- | util/validators.go | 9 | 
21 files changed, 184 insertions, 179 deletions
diff --git a/auth/controller.go b/auth/controller.go index 8de7370..c5c931a 100644 --- a/auth/controller.go +++ b/auth/controller.go @@ -22,23 +22,24 @@ import (  	"github.com/golang-jwt/jwt/v5"  	"github.com/spf13/viper"  	"golang.org/x/crypto/bcrypt" -	"vidhukant.com/openbills/user"  	"net/http"  	"time"  	"vidhukant.com/openbills/errors" +	"vidhukant.com/openbills/user"  )  var ( -	COST int +	COST                  int  	AUTH_KEY, REFRESH_KEY []byte  ) +  func init() {  	COST = viper.GetInt("cryptography.password_hashing_cost")  	AUTH_KEY = []byte(viper.GetString("cryptography.auth_key"))  	REFRESH_KEY = []byte(viper.GetString("cryptography.refresh_key"))  } -func handleSignUp (ctx *gin.Context) { +func handleSignUp(ctx *gin.Context) {  	var u user.User  	ctx.Bind(&u) @@ -72,7 +73,7 @@ func handleSignUp (ctx *gin.Context) {  	ctx.JSON(http.StatusOK, nil)  } -func handleSignIn (ctx *gin.Context) { +func handleSignIn(ctx *gin.Context) {  	var req LoginReq  	ctx.Bind(&req) @@ -88,9 +89,9 @@ func handleSignIn (ctx *gin.Context) {  	}  	authToken, err := jwt.NewWithClaims(jwt.SigningMethodHS256, -		AuthClaims { -			jwt.RegisteredClaims { -				IssuedAt: jwt.NewNumericDate(time.Now()), +		AuthClaims{ +			jwt.RegisteredClaims{ +				IssuedAt:  jwt.NewNumericDate(time.Now()),  				ExpiresAt: jwt.NewNumericDate(time.Now().Add(time.Minute * 2)),  			},  			u.ID, @@ -105,10 +106,10 @@ func handleSignIn (ctx *gin.Context) {  	}  	refreshToken, err := jwt.NewWithClaims(jwt.SigningMethodHS256, -		RefreshClaims { -			jwt.RegisteredClaims { -				IssuedAt: jwt.NewNumericDate(time.Now()), -			  ExpiresAt: jwt.NewNumericDate(time.Now().Add(time.Hour * 6)), +		RefreshClaims{ +			jwt.RegisteredClaims{ +				IssuedAt:  jwt.NewNumericDate(time.Now()), +				ExpiresAt: jwt.NewNumericDate(time.Now().Add(time.Hour * 6)),  			},  			u.ID,  			u.TokenVersion, @@ -125,17 +126,17 @@ func handleSignIn (ctx *gin.Context) {  	u.Password = ""  	ctx.JSON(http.StatusOK, gin.H{ -		"auth_token": authToken, +		"auth_token":    authToken,  		"refresh_token": refreshToken, -		"data": u, +		"data":          u,  	})  } -func handleRefresh (ctx *gin.Context) { +func handleRefresh(ctx *gin.Context) {  	var req RefreshReq  	ctx.Bind(&req) -	tk, _ := jwt.ParseWithClaims(req.RefreshToken, &RefreshClaims{}, func (token *jwt.Token) (interface{}, error) { +	tk, _ := jwt.ParseWithClaims(req.RefreshToken, &RefreshClaims{}, func(token *jwt.Token) (interface{}, error) {  		return []byte(REFRESH_KEY), nil  	}) @@ -152,22 +153,21 @@ func handleRefresh (ctx *gin.Context) {  	if err != nil {  		if err == errors.ErrNotFound {  			// user doesn't exist -		  ctx.Error(errors.ErrUnauthorized) -		  ctx.Abort() -		  return +			ctx.Error(errors.ErrUnauthorized) +			ctx.Abort() +			return  		} else { -		  ctx.Error(err) -		  ctx.Abort() -		  return +			ctx.Error(err) +			ctx.Abort() +			return  		}  	} -	if (u.TokenVersion != claims.Version) { +	if u.TokenVersion != claims.Version {  		ctx.Error(errors.ErrSessionExpired)  		ctx.Abort()  		return  	} -  	if !tk.Valid {  		eat := claims.ExpiresAt.Unix()  		if eat != 0 && eat < time.Now().Unix() { @@ -181,9 +181,9 @@ func handleRefresh (ctx *gin.Context) {  	}  	authToken, err := jwt.NewWithClaims(jwt.SigningMethodHS256, -		AuthClaims { -			jwt.RegisteredClaims { -				IssuedAt: jwt.NewNumericDate(time.Now()), +		AuthClaims{ +			jwt.RegisteredClaims{ +				IssuedAt:  jwt.NewNumericDate(time.Now()),  				ExpiresAt: jwt.NewNumericDate(time.Now().Add(time.Minute * 2)),  			},  			u.ID, diff --git a/auth/middleware.go b/auth/middleware.go index 80e512e..e587681 100644 --- a/auth/middleware.go +++ b/auth/middleware.go @@ -18,11 +18,11 @@  package auth  import ( -	"vidhukant.com/openbills/errors"  	"github.com/gin-gonic/gin"  	"github.com/golang-jwt/jwt/v5"  	"strings"  	"time" +	"vidhukant.com/openbills/errors"  )  func getBearerToken(header []string) (string, error) { @@ -47,7 +47,7 @@ func Authorize() gin.HandlerFunc {  			return  		} -		tk, _ := jwt.ParseWithClaims(bearerToken, &AuthClaims{}, func (token *jwt.Token) (interface{}, error) { +		tk, _ := jwt.ParseWithClaims(bearerToken, &AuthClaims{}, func(token *jwt.Token) (interface{}, error) {  			return []byte(AUTH_KEY), nil  		}) diff --git a/customer/controller.go b/customer/controller.go index 83423da..b9b2b25 100644 --- a/customer/controller.go +++ b/customer/controller.go @@ -18,13 +18,13 @@  package customer  import ( -	e "vidhukant.com/openbills/errors"  	"github.com/gin-gonic/gin"  	"net/http"  	"strconv" +	e "vidhukant.com/openbills/errors"  ) -func handleGetSingleCustomer (ctx *gin.Context) { +func handleGetSingleCustomer(ctx *gin.Context) {  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil {  		ctx.Error(e.ErrInvalidID) @@ -44,7 +44,7 @@ func handleGetSingleCustomer (ctx *gin.Context) {  	})  } -func handleGetCustomers (ctx *gin.Context) { +func handleGetCustomers(ctx *gin.Context) {  	var customers []Customer  	err := getCustomers(&customers) @@ -59,7 +59,7 @@ func handleGetCustomers (ctx *gin.Context) {  	})  } -func handleSaveCustomer (ctx *gin.Context) { +func handleSaveCustomer(ctx *gin.Context) {  	var customer Customer  	ctx.Bind(&customer) @@ -75,7 +75,7 @@ func handleSaveCustomer (ctx *gin.Context) {  	})  } -func handleDelCustomer (ctx *gin.Context) { +func handleDelCustomer(ctx *gin.Context) {  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil {  		ctx.Error(e.ErrInvalidID) diff --git a/customer/customer.go b/customer/customer.go index 0d107d7..cf5c3f1 100644 --- a/customer/customer.go +++ b/customer/customer.go @@ -23,6 +23,7 @@ import (  )  var db *gorm.DB +  func init() {  	db = d.DB @@ -31,18 +32,18 @@ func init() {  type Customer struct {  	gorm.Model -	FirmName                  string -	Gstin                     string -	ContactName               string -	Phone                     string -	Email                     string -	Website                   string - -	BillingAddressText        string -	BillingAddressCity        string -	BillingAddressState       string -	BillingAddressPostalCode  string -	BillingAddressCountry     string +	FirmName    string +	Gstin       string +	ContactName string +	Phone       string +	Email       string +	Website     string + +	BillingAddressText       string +	BillingAddressCity       string +	BillingAddressState      string +	BillingAddressPostalCode string +	BillingAddressCountry    string  	ShippingAddressText       string  	ShippingAddressCity       string diff --git a/customer/hooks.go b/customer/hooks.go index 7f715c3..2160f40 100644 --- a/customer/hooks.go +++ b/customer/hooks.go @@ -34,7 +34,7 @@ func (c *Customer) BeforeSave(tx *gorm.DB) error {  }  func (c *Customer) BeforeDelete(tx *gorm.DB) error { -  // if ID is 0, customer won't be deleted +	// if ID is 0, customer won't be deleted  	if c.ID == 0 {  		return errors.ErrNoWhereCondition  	} @@ -18,11 +18,11 @@  package db  import ( -	"gorm.io/gorm" -	"gorm.io/driver/mysql" +	"fmt"  	"github.com/spf13/viper" +	"gorm.io/driver/mysql" +	"gorm.io/gorm"  	"log" -	"fmt"  )  var DB *gorm.DB diff --git a/errors/errors.go b/errors/errors.go index 17afdfe..de18bf4 100644 --- a/errors/errors.go +++ b/errors/errors.go @@ -23,43 +23,43 @@ import (  var (  	// 204 -	ErrEmptyResponse          = errors.New("No Records Found") +	ErrEmptyResponse = errors.New("No Records Found")  	// 400 -	ErrNoWhereCondition       = errors.New("No Where Condition") -	ErrInvalidID              = errors.New("Invalid ID") -	ErrEmptyContactName       = errors.New("Contact Name Cannot Be Empty") -	ErrInvalidGSTIN           = errors.New("Invalid GSTIN") -	ErrInvalidEmail           = errors.New("Invalid E-Mail Address") -  ErrEmptyEmail             = errors.New("E-Mail Address Cannot Be Empty") -  ErrInvalidUsername        = errors.New("Invalid Username") -  ErrEmptyUsername          = errors.New("Username Cannot Be Empty") -	ErrInvalidPhone           = errors.New("Invalid Phone Number") -	ErrInvalidWebsite         = errors.New("Invalid Website URL") -	ErrEmptyBrandName         = errors.New("Brand Name Cannot Be Empty") -	ErrInvalidUnitPrice       = errors.New("Invalid Unit Price") -	ErrInvalidGSTPercentage   = errors.New("Invalid GST Percentage") -	ErrPasswordTooShort       = errors.New("Password Is Too Short") -	ErrPasswordTooLong        = errors.New("Password Is Too Long") -	ErrUsernameTooShort       = errors.New("Username Is Too Short") -	ErrUsernameTooLong        = errors.New("Username Is Too Long") -	ErrInvalidLoginMethod     = errors.New("Login Method Can Only Be 'email' Or 'username'") +	ErrNoWhereCondition     = errors.New("No Where Condition") +	ErrInvalidID            = errors.New("Invalid ID") +	ErrEmptyContactName     = errors.New("Contact Name Cannot Be Empty") +	ErrInvalidGSTIN         = errors.New("Invalid GSTIN") +	ErrInvalidEmail         = errors.New("Invalid E-Mail Address") +	ErrEmptyEmail           = errors.New("E-Mail Address Cannot Be Empty") +	ErrInvalidUsername      = errors.New("Invalid Username") +	ErrEmptyUsername        = errors.New("Username Cannot Be Empty") +	ErrInvalidPhone         = errors.New("Invalid Phone Number") +	ErrInvalidWebsite       = errors.New("Invalid Website URL") +	ErrEmptyBrandName       = errors.New("Brand Name Cannot Be Empty") +	ErrInvalidUnitPrice     = errors.New("Invalid Unit Price") +	ErrInvalidGSTPercentage = errors.New("Invalid GST Percentage") +	ErrPasswordTooShort     = errors.New("Password Is Too Short") +	ErrPasswordTooLong      = errors.New("Password Is Too Long") +	ErrUsernameTooShort     = errors.New("Username Is Too Short") +	ErrUsernameTooLong      = errors.New("Username Is Too Long") +	ErrInvalidLoginMethod   = errors.New("Login Method Can Only Be 'email' Or 'username'")  	// 401 -	ErrWrongPassword          = errors.New("Wrong Password") -	ErrInvalidAuthHeader      = errors.New("Invalid Authorization Header") -	ErrUnauthorized           = errors.New("Unauthorized") -	ErrSessionExpired         = errors.New("Session Expired") +	ErrWrongPassword     = errors.New("Wrong Password") +	ErrInvalidAuthHeader = errors.New("Invalid Authorization Header") +	ErrUnauthorized      = errors.New("Unauthorized") +	ErrSessionExpired    = errors.New("Session Expired")  	// 403 -	ErrForbidden              = errors.New("You Are Not Authorized To Access This Resource") +	ErrForbidden = errors.New("You Are Not Authorized To Access This Resource")  	// 404 -	ErrNotFound               = errors.New("Not Found") -	ErrBrandNotFound          = errors.New("This Brand Does Not Exist") +	ErrNotFound      = errors.New("Not Found") +	ErrBrandNotFound = errors.New("This Brand Does Not Exist")  	// 405 -	ErrCannotEditInvoice      = errors.New("This Invoice Cannot Be Edited Now") +	ErrCannotEditInvoice = errors.New("This Invoice Cannot Be Edited Now")  	// 409  	ErrNonUniqueUsername      = errors.New("Username Is Already In Use") @@ -68,5 +68,5 @@ var (  	ErrNonUniqueInvoiceNumber = errors.New("Invoice Number Must Be Unique")  	// 500 -	ErrInternalServerError    = errors.New("Internal Server Error") +	ErrInternalServerError = errors.New("Internal Server Error")  ) diff --git a/errors/status.go b/errors/status.go index a874423..306ea27 100644 --- a/errors/status.go +++ b/errors/status.go @@ -30,8 +30,8 @@ func StatusCodeFromErr(err error) int {  	// 400  	if errors.Is(err, ErrNoWhereCondition) || -		errors.Is (err, ErrInvalidID) || -		errors.Is (err, ErrEmptyContactName) || +		errors.Is(err, ErrInvalidID) || +		errors.Is(err, ErrEmptyContactName) ||  		errors.Is(err, ErrInvalidGSTIN) ||  		errors.Is(err, ErrInvalidEmail) ||  		errors.Is(err, ErrInvalidPhone) || @@ -31,8 +31,8 @@ type Info struct {  }  func serverInfo(ctx *gin.Context) { -	info := Info { -	  Version:     OPENBILLS_VERSION, +	info := Info{ +		Version:     OPENBILLS_VERSION,  		Title:       viper.GetString("instance.title"),  		Description: viper.GetString("instance.description"),  		URL:         viper.GetString("instance.url"), diff --git a/invoice/controller.go b/invoice/controller.go index b03ec22..bb51628 100644 --- a/invoice/controller.go +++ b/invoice/controller.go @@ -18,13 +18,13 @@  package invoice  import ( -	e "vidhukant.com/openbills/errors"  	"github.com/gin-gonic/gin"  	"net/http"  	"strconv" +	e "vidhukant.com/openbills/errors"  ) -func handleGetSingleInvoice (ctx *gin.Context) { +func handleGetSingleInvoice(ctx *gin.Context) {  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil {  		ctx.Error(e.ErrInvalidID) @@ -47,22 +47,22 @@ func handleGetSingleInvoice (ctx *gin.Context) {  func handleGetInvoices(getDrafts bool) func(*gin.Context) {  	return func(ctx *gin.Context) { -	  var invoices []Invoice +		var invoices []Invoice -	  err := getInvoices(&invoices, getDrafts) -	  if err != nil { -	  	ctx.Error(err) -	  	ctx.Abort() -	  	return -	  } +		err := getInvoices(&invoices, getDrafts) +		if err != nil { +			ctx.Error(err) +			ctx.Abort() +			return +		} -	  ctx.JSON(http.StatusOK, gin.H{ -	  	"data": invoices, -	  }) +		ctx.JSON(http.StatusOK, gin.H{ +			"data": invoices, +		})  	}  } -func handleSaveInvoice (ctx *gin.Context) { +func handleSaveInvoice(ctx *gin.Context) {  	var invoice Invoice  	ctx.Bind(&invoice) @@ -92,7 +92,7 @@ func handleSaveInvoice (ctx *gin.Context) {  	})  } -func handleDelInvoice (ctx *gin.Context) { +func handleDelInvoice(ctx *gin.Context) {  	// TODO: only drafts can be deleted, non-drafts should be "cancelled"  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil { @@ -115,7 +115,7 @@ func handleDelInvoice (ctx *gin.Context) {  }  // get items belonging to a certain invoice -func handleGetInvoiceItems (ctx *gin.Context) { +func handleGetInvoiceItems(ctx *gin.Context) {  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil {  		ctx.Error(e.ErrInvalidID) @@ -136,7 +136,7 @@ func handleGetInvoiceItems (ctx *gin.Context) {  	})  } -func addItem (ctx *gin.Context) { +func addItem(ctx *gin.Context) {  	// TODO: only drafts can be edited  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil { @@ -160,7 +160,7 @@ func addItem (ctx *gin.Context) {  	ctx.JSON(http.StatusOK, nil)  } -func removeItem (ctx *gin.Context) { +func removeItem(ctx *gin.Context) {  	// TODO: only drafts can be edited  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil { @@ -183,7 +183,7 @@ func removeItem (ctx *gin.Context) {  }  // get custom fields belonging to a certain invoice -func handleGetInvoiceCustomFields (ctx *gin.Context) { +func handleGetInvoiceCustomFields(ctx *gin.Context) {  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil {  		ctx.Error(e.ErrInvalidID) @@ -204,7 +204,7 @@ func handleGetInvoiceCustomFields (ctx *gin.Context) {  	})  } -func addCustomField (ctx *gin.Context) { +func addCustomField(ctx *gin.Context) {  	// TODO: only drafts can be edited  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil { @@ -229,7 +229,7 @@ func addCustomField (ctx *gin.Context) {  	})  } -func removeCustomField (ctx *gin.Context) { +func removeCustomField(ctx *gin.Context) {  	// TODO: only drafts can be edited  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil { diff --git a/invoice/hooks.go b/invoice/hooks.go index b0ec877..68d730b 100644 --- a/invoice/hooks.go +++ b/invoice/hooks.go @@ -34,7 +34,7 @@ func (i *Invoice) BeforeSave(tx *gorm.DB) error {  }  func (i *Invoice) BeforeDelete(tx *gorm.DB) error { -  // if ID is 0, invoice won't be deleted +	// if ID is 0, invoice won't be deleted  	if i.ID == 0 {  		return errors.ErrNoWhereCondition  	} diff --git a/invoice/invoice.go b/invoice/invoice.go index 9fa931b..97ba254 100644 --- a/invoice/invoice.go +++ b/invoice/invoice.go @@ -19,13 +19,14 @@ package invoice  import (  	"gorm.io/gorm" +	"time"  	d "vidhukant.com/openbills/db" -	u "vidhukant.com/openbills/util"  	i "vidhukant.com/openbills/item" -	"time" +	u "vidhukant.com/openbills/util"  )  var db *gorm.DB +  func init() {  	db = d.DB @@ -71,14 +72,14 @@ type Invoice struct {  	Items           []InvoiceItem  	CustomFields    []CustomField -  // issuer and customer details are stored here  -  // because they are NOT intended to ever change -  IssuerFirmName      string -  IssuerFirmAddress   string -  IssuerFirmGstin     string -  IssuerFirmPhone     string -  IssuerFirmEmail     string -  IssuerFirmWebsite   string +	// issuer and customer details are stored here +	// because they are NOT intended to ever change +	IssuerFirmName      string +	IssuerFirmAddress   string +	IssuerFirmGstin     string +	IssuerFirmPhone     string +	IssuerFirmEmail     string +	IssuerFirmWebsite   string  	IssuerFirmDetails   string  	CustomerName        string  	CustomerGstin       string diff --git a/invoice/validators.go b/invoice/validators.go index 1c39cbe..13cc6e6 100644 --- a/invoice/validators.go +++ b/invoice/validators.go @@ -50,7 +50,7 @@ func isDraft(invoiceId uint) (bool, error) {  	// TODO: handle potential errors  	if err != nil {  		return invoice.IsDraft, err -  } +	}  	// invoice doesn't exist  	if invoice.ID == 0 { diff --git a/item/controller.go b/item/controller.go index 3df95c3..26c6b8b 100644 --- a/item/controller.go +++ b/item/controller.go @@ -18,13 +18,13 @@  package item  import ( -	e "vidhukant.com/openbills/errors"  	"github.com/gin-gonic/gin"  	"net/http"  	"strconv" +	e "vidhukant.com/openbills/errors"  ) -func handleGetSingleItem (ctx *gin.Context) { +func handleGetSingleItem(ctx *gin.Context) {  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil {  		ctx.Error(e.ErrInvalidID) @@ -44,7 +44,7 @@ func handleGetSingleItem (ctx *gin.Context) {  	})  } -func handleGetItems (ctx *gin.Context) { +func handleGetItems(ctx *gin.Context) {  	var items []SavedItem  	err := getItems(&items) @@ -59,7 +59,7 @@ func handleGetItems (ctx *gin.Context) {  	})  } -func handleSaveItem (ctx *gin.Context) { +func handleSaveItem(ctx *gin.Context) {  	var item SavedItem  	ctx.Bind(&item) @@ -75,7 +75,7 @@ func handleSaveItem (ctx *gin.Context) {  	})  } -func handleDelItem (ctx *gin.Context) { +func handleDelItem(ctx *gin.Context) {  	id, err := strconv.ParseUint(ctx.Param("id"), 10, 64)  	if err != nil {  		ctx.Error(e.ErrInvalidID) diff --git a/item/item.go b/item/item.go index 3a6235f..108187a 100644 --- a/item/item.go +++ b/item/item.go @@ -23,6 +23,7 @@ import (  )  var db *gorm.DB +  func init() {  	db = d.DB @@ -23,14 +23,14 @@ import (  	_ "vidhukant.com/openbills/db"  	// middlewares, etc -  "vidhukant.com/openbills/errors" +	"vidhukant.com/openbills/errors"  	// routes -	"vidhukant.com/openbills/user"  	"vidhukant.com/openbills/auth"  	"vidhukant.com/openbills/customer" -	"vidhukant.com/openbills/item"  	"vidhukant.com/openbills/invoice" +	"vidhukant.com/openbills/item" +	"vidhukant.com/openbills/user"  	"github.com/gin-gonic/gin"  	"github.com/spf13/viper" diff --git a/user/controller.go b/user/controller.go index 7dd519a..3b8c587 100644 --- a/user/controller.go +++ b/user/controller.go @@ -18,32 +18,32 @@  package user  import ( -  e "vidhukant.com/openbills/errors"  	"github.com/gin-gonic/gin"  	"net/http" +	e "vidhukant.com/openbills/errors"  ) -func handleGetUser (ctx *gin.Context) { +func handleGetUser(ctx *gin.Context) {  	var user User -  uId, ok := ctx.Get("UserID") -  if !ok { -    ctx.Error(e.ErrUnauthorized) -    ctx.Abort() -    return -  } +	uId, ok := ctx.Get("UserID") +	if !ok { +		ctx.Error(e.ErrUnauthorized) +		ctx.Abort() +		return +	} -  userId := uId.(uint) +	userId := uId.(uint) -  err := GetUserById(&user, userId) +	err := GetUserById(&user, userId)  	if err != nil {  		ctx.Error(err)  		ctx.Abort()  		return  	} -  // remove password hash from response -  user.Password = "" +	// remove password hash from response +	user.Password = ""  	ctx.JSON(http.StatusOK, gin.H{  		"data": user, diff --git a/user/service.go b/user/service.go index 4dec8bc..a4fc359 100644 --- a/user/service.go +++ b/user/service.go @@ -32,7 +32,7 @@ func GetUserByAccountName(user *User, accountName, method string) error {  		return e.ErrInvalidLoginMethod  	} -	res := db.Where(method + " = ?", accountName).Preload("Roles").Find(&user) +	res := db.Where(method+" = ?", accountName).Preload("Roles").Find(&user)  	if res.Error != nil {  		return res.Error  	} diff --git a/user/user.go b/user/user.go index 4d0ffcb..8f321eb 100644 --- a/user/user.go +++ b/user/user.go @@ -18,16 +18,17 @@  package user  import ( -	d "vidhukant.com/openbills/db" -	e "vidhukant.com/openbills/errors" +	"errors" +	"github.com/spf13/viper"  	"golang.org/x/crypto/bcrypt"  	"gorm.io/gorm" -	"github.com/spf13/viper" -	"errors" +	d "vidhukant.com/openbills/db" +	e "vidhukant.com/openbills/errors"  )  var COST int  var db *gorm.DB +  func init() {  	db = d.DB @@ -36,7 +37,7 @@ func init() {  	COST = viper.GetInt("cryptography.password_hashing_cost")  } -var VALID_ROLES []string = []string { +var VALID_ROLES []string = []string{  	"customer.*", "customer.read", "customer.write", "customer.delete",  	"item.*", "item.read", "item.write", "item.delete",  	"invoice.*", "invoice.read", "invoice.write", "invoice.delete", @@ -52,8 +53,8 @@ type Role struct {  type User struct {  	ID           uint  	TokenVersion uint // this can be incremented to disable existing refresh token(s) -  Username     string -  Email        string +	Username     string +	Email        string  	Password     string  	Roles        []Role `gorm:"constraint:OnDelete:CASCADE;"`  } diff --git a/user/validators.go b/user/validators.go index e9a894c..3207f3a 100644 --- a/user/validators.go +++ b/user/validators.go @@ -18,8 +18,8 @@  package user  import ( -	"strings"  	"github.com/spf13/viper" +	"strings"  	"vidhukant.com/openbills/errors"  	"vidhukant.com/openbills/util"  ) @@ -48,49 +48,49 @@ func validateUsername(username string) error {  	if len(username) > 32 {  		return errors.ErrUsernameTooLong  	} -  -	// (11th October 2025) what the fuck even is this  + +	// (11th October 2025) what the fuck even is this  	// I'm not even deleting this I can't stop laughing -  //  -  // for _, char := range username { -  //   if !strings.Contains(username, string(char)) { -  //     return errors.ErrInvalidUsername -  //   } -  // } +	// +	// for _, char := range username { +	//   if !strings.Contains(username, string(char)) { +	//     return errors.ErrInvalidUsername +	//   } +	// } -  return nil +	return nil  }  func (u *User) validate() error {  	u.Email = strings.TrimSpace(u.Email) -  u.Username = strings.TrimSpace(u.Username) +	u.Username = strings.TrimSpace(u.Username)  	// don't accept empty username -  if u.Username == "" { -    return errors.ErrEmptyUsername -  } else { -    // validate username -    err := validateUsername(u.Username) -    if err != nil { -      return err -    } -  } +	if u.Username == "" { +		return errors.ErrEmptyUsername +	} else { +		// validate username +		err := validateUsername(u.Username) +		if err != nil { +			return err +		} +	} -  // don't accept empty email -  if u.Email == "" { -    return errors.ErrEmptyEmail -  } else { -    // validate email -    if !util.ValidateEmail(u.Email) { -      return errors.ErrInvalidEmail -    } -  } +	// don't accept empty email +	if u.Email == "" { +		return errors.ErrEmptyEmail +	} else { +		// validate email +		if !util.ValidateEmail(u.Email) { +			return errors.ErrInvalidEmail +		} +	} -  // validate password -  err := validatePassword(u.Password) -  if err != nil { -    return err -  } +	// validate password +	err := validatePassword(u.Password) +	if err != nil { +		return err +	}  	return nil  } diff --git a/util/validators.go b/util/validators.go index c180daf..d6eb929 100644 --- a/util/validators.go +++ b/util/validators.go @@ -18,12 +18,13 @@  package util  import ( -	"regexp"  	"net/mail"  	"net/url" +	"regexp"  )  var phoneRegex, gstinRegex *regexp.Regexp +  func init() {  	phoneRegex = regexp.MustCompile(`^(?:(?:\(?(?:00|\+)([1-4]\d\d|[1-9]\d?)\)?)?[\-\.\ \\\/]?)?((?:\(?\d{1,}\)?[\-\.\ \\\/]?){0,})(?:[\-\.\ \\\/]?(?:#|ext\.?|extension|x)[\-\.\ \\\/]?(\d+))?$`)  	gstinRegex = regexp.MustCompile(`^[0-9]{2}[A-Z]{5}[0-9]{4}[A-Z]{1}[1-9A-Z]{1}Z[0-9A-Z]{1}$`) @@ -34,7 +35,7 @@ func ValidateEmail(email string) bool {  	if err != nil {  		return false  	} -  return true +	return true  }  func ValidateWebsite(website string) bool { @@ -42,7 +43,7 @@ func ValidateWebsite(website string) bool {  	if err != nil {  		return false  	} -  return true +	return true  }  func ValidateGstin(gstin string) bool { @@ -50,5 +51,5 @@ func ValidateGstin(gstin string) bool {  }  func ValidatePhone(phone string) bool { -  return phoneRegex.MatchString(phone) +	return phoneRegex.MatchString(phone)  }  |