Я использую GraphQL и go -pg .
У меня много таких сущностей:
type Player struct {
ID int
CreatedAt time.Time `pg:"default:now(),notnull"`
TeamID int `pg:",notnull"`
Team *Team
Type int
Score int64 `pg:",notnull"`
Note *string
// and others...
}
type PlayerInput struct {
TeamID int
Type int
Score int64
Note *string
// and others...
}
У меня много раз такие функции :
func (db *postgres) Update(context context.Context, id int, input types.PlayerInput) (*types.Player, error) {
var actualPlayer types.Player
newPlayer := graphqlToDB(&input)
tx, err := db.Begin()
//handle err
err = tx.Model(&actualPlayer).Where("id = ?", id).For("UPDATE").Select()
// handle err and rollback
actualPlayer.TeamID = newPlayer.TeamID
actualPlayer.Type = newPlayer.Type
actualPlayer.Score = newPlayer.Score
actualPlayer.Note = newPlayer.Note
// and others...
_, err = tx.Model(&actualPlayer).WherePK().Update()
// handle err and rollback
err = tx.Commit()
//handle err
return &actualPlayer, nil
}
func graphqlToDB(input *types.PlayerInput) *types.Player {
var output = &types.Player{
TeamID: input.TeamID,
Type: input.Type,
Score: input.Score,
Note: input.Note,
// and others...
}
if input.Type == "example" {
output.Score = 10000000
}
return output
}
У меня есть этот код для каждой сущности в моем проекте, и я хотел бы ограничить / избежать избыточного кода, особенно:
преобразование из типа ввода Graphql каждый раз
newPlayer := graphqlToDB(&input)
ручное обновление этих (и других) полей каждый раз
actualPlayer.TeamID = newPlayer.TeamID
actualPlayer.Type = newPlayer.Type
actualPlayer.Score = newPlayer.Score
actualPlayer.Note = newPlayer.Note
открытие и закрытие транзакции БД каждый раз
tx, err := db.Begin()
Я прошу луну?