I have an API Swagger generated, I'm not satisfied with how I'm handling my part of the contract e.g. how I have constructed my db
and handlers
modules.
Specially how I'm dealing the the database connection, can this not be made more robust by using interfaces
. For simplicity I'm just including one implemented endpoint.
// This file is safe to edit. Once it exists it will not be overwritten
package restapi
import (
"crypto/tls"
"net/http"
"github.com/go-openapi/errors"
"github.com/go-openapi/runtime"
"github.com/go-openapi/runtime/middleware"
log "github.com/sirupsen/logrus"
"hairdoo.com/m/v2/handlers"
"hairdoo.com/m/v2/models"
"hairdoo.com/m/v2/restapi/operations"
"hairdoo.com/m/v2/restapi/operations/company"
"hairdoo.com/m/v2/restapi/operations/employee"
)
//go:generate swagger generate server --target ../../hairdoo --name Hairdoo --spec ../swagger.yml --principal interface{}
//var db *gorm.DB
func init() {
// Log as JSON instead of the default ASCII formatter.
/*log.SetFormatter(&log.JSONFormatter{
TimestampFormat: "2006-01-02 15:04:05",
//PrettyPrint: true,
})*/
// Output to stdout instead of the default stderr
// Can be any io.Writer, see below for File example
//log.SetOutput(os.Stdout)
log.SetFormatter(&log.TextFormatter{
DisableColors: false,
FullTimestamp: true,
})
// Only log the warning severity or above.
//log.SetLevel(log.WarnLevel)
log.SetLevel(log.InfoLevel)
}
func configureFlags(api *operations.HairdooAPI) {
// api.CommandLineOptionsGroups = []swag.CommandLineOptionsGroup{ ... }
}
func configureAPI(api *operations.HairdooAPI) http.Handler {
// configure the api here
api.ServeError = errors.ServeError
// Set your custom logger if needed. Default one is log.Printf
// Expected interface func(string, ...interface{})
//
// Example:
//api.Logger = log.Printf
api.UseSwaggerUI()
// To continue using redoc as your UI, uncomment the following line
// api.UseRedoc()
api.JSONConsumer = runtime.JSONConsumer()
//api.UrlformConsumer = runtime.DiscardConsumer
api.JSONProducer = runtime.JSONProducer()
api.CompanyAddCompanyHandler = company.AddCompanyHandlerFunc(func(params company.AddCompanyParams) middleware.Responder {
//log.Debugf("Add commpay Handler Called")
//log.Infof("Payload Data : %v", params.Body)
response, err := handlers.AddCompany(params)
if err != nil {
return company.NewAddCompanyBadRequest().WithPayload(&models.ErrorReponse400{
Error: err.Error(),
})
}
return company.NewAddCompanyCreated().WithPayload(response)
})
handlers/company.go
package handlers
import (
"hairdoo.com/m/v2/db"
"hairdoo.com/m/v2/models"
"hairdoo.com/m/v2/restapi/operations/company"
)
func AddCompany(params company.AddCompanyParams) (*models.Company, error) {
result, err := db.AddCompany(params.Body)
if err != nil {
return nil, err
}
return result, nil
}
db/company.go
import (
"fmt"
"time"
"gorm.io/gorm"
"hairdoo.com/m/v2/models"
)
type Company struct {
gorm.Model
Name string `gorm:"uniqueIndex"`
Phone string
Email string
ContatctPerson string
CategoryID int
Category *Category
Status string
}
type Category struct {
ID int
Name string `gorm:"uniqueIndex"`
}
func AddCompany(companyObj *models.Company) (*models.Company, error) {
db := Open()
var result *gorm.DB
category := &Category{}
db.Where("name = ?", companyObj.Category.Name).First(category)
company := convertToDBCompany(companyObj, false)
if category.ID != 0 {
result = db.Exec("INSERT INTO companies (created_at, updated_at, name, phone, email, contatct_person, category_id) values (?, ?, ?, ?, ?, ?, ?);",
time.Now(), time.Now(), companyObj.Name, companyObj.Phone, companyObj.Email, companyObj.ContatctPerson, category.ID)
} else {
result = db.Create(company)
}
if result.RowsAffected < 1 {
return nil, result.Error
}
// add employee to db if object present
var employees []*models.EmployeeItems0
if companyObj.Employee != nil {
for _, employeeInput := range companyObj.Employee {
result, err := AddEmployee(employeeInput)
if err != nil {
return nil, err
}
employees = append(employees, result)
}
}
return convertToModelCompany(company, employees), nil
}
database.go
package db
import (
"gorm.io/driver/mysql"
"gorm.io/gorm"
)
func Open() *gorm.DB {
connString := "root:12345@tcp(0.0.0.0:3306)/test?charset=utf8mb4&parseTime=True&loc=Local"
db, err := gorm.Open(mysql.Open(connString), &gorm.Config{})
if err != nil {
panic(err)
}
db.AutoMigrate(Company{}, Category{}, Employee{})
return db
}
```