fix(tester): improve error handling
This commit is contained in:
parent
c67405f584
commit
e6088953b9
14 changed files with 103 additions and 206 deletions
|
@ -2,6 +2,7 @@ package rest
|
|||
|
||||
import (
|
||||
"git.sch9.ru/new_gate/ms-tester/internal/tester"
|
||||
"git.sch9.ru/new_gate/ms-tester/pkg"
|
||||
testerv1 "git.sch9.ru/new_gate/ms-tester/proto/tester/v1"
|
||||
"github.com/gofiber/fiber/v2"
|
||||
)
|
||||
|
@ -29,7 +30,7 @@ func (h *TesterHandlers) ListProblems(c *fiber.Ctx) error {
|
|||
func (h *TesterHandlers) CreateContest(c *fiber.Ctx) error {
|
||||
id, err := h.contestsUC.CreateContest(c.Context(), "Название контеста")
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.JSON(testerv1.CreateContestResponse{
|
||||
|
@ -40,7 +41,7 @@ func (h *TesterHandlers) CreateContest(c *fiber.Ctx) error {
|
|||
func (h *TesterHandlers) DeleteContest(c *fiber.Ctx, id int32) error {
|
||||
err := h.contestsUC.DeleteContest(c.Context(), id)
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.SendStatus(fiber.StatusOK)
|
||||
|
@ -49,7 +50,7 @@ func (h *TesterHandlers) DeleteContest(c *fiber.Ctx, id int32) error {
|
|||
func (h *TesterHandlers) GetContest(c *fiber.Ctx, id int32) error {
|
||||
contest, err := h.contestsUC.ReadContestById(c.Context(), id)
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.JSON(testerv1.GetContestResponse{
|
||||
|
@ -65,7 +66,7 @@ func (h *TesterHandlers) GetContest(c *fiber.Ctx, id int32) error {
|
|||
func (h *TesterHandlers) DeleteParticipant(c *fiber.Ctx, id int32, params testerv1.DeleteParticipantParams) error {
|
||||
err := h.contestsUC.DeleteParticipant(c.Context(), params.ParticipantId)
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.SendStatus(fiber.StatusOK)
|
||||
|
@ -74,7 +75,7 @@ func (h *TesterHandlers) DeleteParticipant(c *fiber.Ctx, id int32, params tester
|
|||
func (h *TesterHandlers) AddParticipant(c *fiber.Ctx, id int32, params testerv1.AddParticipantParams) error {
|
||||
id, err := h.contestsUC.AddParticipant(c.Context(), id, params.UserId)
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.JSON(testerv1.AddParticipantResponse{
|
||||
|
@ -85,7 +86,7 @@ func (h *TesterHandlers) AddParticipant(c *fiber.Ctx, id int32, params testerv1.
|
|||
func (h *TesterHandlers) DeleteTask(c *fiber.Ctx, id int32, params testerv1.DeleteTaskParams) error {
|
||||
err := h.contestsUC.DeleteTask(c.Context(), params.TaskId)
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.SendStatus(fiber.StatusOK)
|
||||
|
@ -94,7 +95,7 @@ func (h *TesterHandlers) DeleteTask(c *fiber.Ctx, id int32, params testerv1.Dele
|
|||
func (h *TesterHandlers) AddTask(c *fiber.Ctx, id int32, params testerv1.AddTaskParams) error {
|
||||
id, err := h.contestsUC.AddTask(c.Context(), id, params.ProblemId)
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.SendStatus(fiber.StatusNotImplemented)
|
||||
|
@ -103,7 +104,7 @@ func (h *TesterHandlers) AddTask(c *fiber.Ctx, id int32, params testerv1.AddTask
|
|||
func (h *TesterHandlers) CreateProblem(c *fiber.Ctx) error {
|
||||
id, err := h.problemsUC.CreateProblem(c.Context(), "Название задачи")
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.JSON(testerv1.CreateProblemResponse{
|
||||
|
@ -114,7 +115,7 @@ func (h *TesterHandlers) CreateProblem(c *fiber.Ctx) error {
|
|||
func (h *TesterHandlers) DeleteProblem(c *fiber.Ctx, id int32) error {
|
||||
err := h.problemsUC.DeleteProblem(c.Context(), id)
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.SendStatus(fiber.StatusOK)
|
||||
|
@ -124,7 +125,7 @@ func (h *TesterHandlers) DeleteProblem(c *fiber.Ctx, id int32) error {
|
|||
func (h *TesterHandlers) GetProblem(c *fiber.Ctx, id int32) error {
|
||||
problem, err := h.problemsUC.ReadProblemById(c.Context(), id)
|
||||
if err != nil {
|
||||
return err
|
||||
return c.SendStatus(pkg.ToREST(err))
|
||||
}
|
||||
|
||||
return c.JSON(
|
||||
|
|
|
@ -1,23 +1,27 @@
|
|||
package repository
|
||||
|
||||
import (
|
||||
"database/sql"
|
||||
"errors"
|
||||
"git.sch9.ru/new_gate/ms-tester/pkg/utils"
|
||||
"git.sch9.ru/new_gate/ms-tester/pkg"
|
||||
"github.com/jackc/pgerrcode"
|
||||
"github.com/jackc/pgx/v5/pgconn"
|
||||
)
|
||||
|
||||
func handlePgErr(err error) error {
|
||||
func handlePgErr(err error, op string) error {
|
||||
var pgErr *pgconn.PgError
|
||||
if !errors.As(err, &pgErr) {
|
||||
return utils.StorageError(err, utils.ErrUnknown, "unexpected error from postgres")
|
||||
if errors.As(err, &pgErr) {
|
||||
if pgerrcode.IsIntegrityConstraintViolation(pgErr.Code) {
|
||||
return pkg.Wrap(pkg.ErrBadInput, err, op, pgErr.Message)
|
||||
}
|
||||
if pgerrcode.IsNoData(pgErr.Code) {
|
||||
return pkg.Wrap(pkg.ErrNotFound, err, op, pgErr.Message)
|
||||
}
|
||||
}
|
||||
if pgerrcode.IsIntegrityConstraintViolation(pgErr.Code) {
|
||||
// TODO: probably should specify which constraint
|
||||
return utils.StorageError(err, utils.ErrConflict, pgErr.Message)
|
||||
|
||||
if errors.Is(err, sql.ErrNoRows) {
|
||||
return pkg.Wrap(pkg.ErrNotFound, err, op, "no rows found")
|
||||
}
|
||||
if pgerrcode.IsNoData(pgErr.Code) {
|
||||
return utils.StorageError(err, utils.ErrNotFound, pgErr.Message)
|
||||
}
|
||||
return utils.StorageError(err, utils.ErrUnimplemented, "unimplemented error")
|
||||
|
||||
return pkg.Wrap(pkg.ErrUnhandled, err, op, "unexpected error")
|
||||
}
|
||||
|
|
|
@ -22,11 +22,13 @@ func NewContestRepository(db *sqlx.DB, logger *zap.Logger) *ContestRepository {
|
|||
const createContestQuery = "INSERT INTO contests (title) VALUES (?) RETURNING id"
|
||||
|
||||
func (r *ContestRepository) CreateContest(ctx context.Context, title string) (int32, error) {
|
||||
const op = "ContestRepository.CreateContest"
|
||||
|
||||
query := r.db.Rebind(createContestQuery)
|
||||
|
||||
rows, err := r.db.QueryxContext(ctx, query, title)
|
||||
if err != nil {
|
||||
return 0, handlePgErr(err)
|
||||
return 0, handlePgErr(err, op)
|
||||
}
|
||||
|
||||
defer rows.Close()
|
||||
|
@ -34,7 +36,7 @@ func (r *ContestRepository) CreateContest(ctx context.Context, title string) (in
|
|||
rows.Next()
|
||||
err = rows.Scan(&id)
|
||||
if err != nil {
|
||||
return 0, handlePgErr(err)
|
||||
return 0, handlePgErr(err, op)
|
||||
}
|
||||
|
||||
return id, nil
|
||||
|
@ -43,11 +45,13 @@ func (r *ContestRepository) CreateContest(ctx context.Context, title string) (in
|
|||
const readContestByIdQuery = "SELECT * from contests WHERE id=? LIMIT 1"
|
||||
|
||||
func (r *ContestRepository) ReadContestById(ctx context.Context, id int32) (*models.Contest, error) {
|
||||
const op = "ContestRepository.ReadContestById"
|
||||
|
||||
var contest models.Contest
|
||||
query := r.db.Rebind(readContestByIdQuery)
|
||||
err := r.db.GetContext(ctx, &contest, query, id)
|
||||
if err != nil {
|
||||
return nil, handlePgErr(err)
|
||||
return nil, handlePgErr(err, op)
|
||||
}
|
||||
return &contest, nil
|
||||
}
|
||||
|
@ -55,10 +59,12 @@ func (r *ContestRepository) ReadContestById(ctx context.Context, id int32) (*mod
|
|||
const deleteContestQuery = "DELETE FROM contests WHERE id=?"
|
||||
|
||||
func (r *ContestRepository) DeleteContest(ctx context.Context, id int32) error {
|
||||
const op = "ContestRepository.DeleteContest"
|
||||
|
||||
query := r.db.Rebind(deleteContestQuery)
|
||||
_, err := r.db.ExecContext(ctx, query, id)
|
||||
if err != nil {
|
||||
return handlePgErr(err)
|
||||
return handlePgErr(err, op)
|
||||
}
|
||||
|
||||
return nil
|
||||
|
@ -67,17 +73,19 @@ func (r *ContestRepository) DeleteContest(ctx context.Context, id int32) error {
|
|||
const addTaskQuery = "INSERT INTO tasks (problem_id, contest_id, position) VALUES (?, ?,COALESCE(SELECT MAX(position) FROM task WHERE contest_id = ? ,0) + 1) RETURNING id"
|
||||
|
||||
func (r *ContestRepository) AddTask(ctx context.Context, contestId int32, problem_id int32) (int32, error) {
|
||||
const op = "ContestRepository.AddTask"
|
||||
|
||||
query := r.db.Rebind(addTaskQuery)
|
||||
rows, err := r.db.QueryxContext(ctx, query, problem_id, contestId, contestId)
|
||||
if err != nil {
|
||||
return 0, handlePgErr(err)
|
||||
return 0, handlePgErr(err, op)
|
||||
}
|
||||
defer rows.Close()
|
||||
var id int32
|
||||
rows.Next()
|
||||
err = rows.Scan(&id)
|
||||
if err != nil {
|
||||
return 0, handlePgErr(err)
|
||||
return 0, handlePgErr(err, op)
|
||||
}
|
||||
return id, nil
|
||||
}
|
||||
|
@ -85,10 +93,12 @@ func (r *ContestRepository) AddTask(ctx context.Context, contestId int32, proble
|
|||
const deleteTaskQuery = "DELETE FROM tasks WHERE id=?"
|
||||
|
||||
func (r *ContestRepository) DeleteTask(ctx context.Context, taskId int32) error {
|
||||
const op = "ContestRepository.DeleteTask"
|
||||
|
||||
query := r.db.Rebind(deleteTaskQuery)
|
||||
_, err := r.db.ExecContext(ctx, query, taskId)
|
||||
if err != nil {
|
||||
return handlePgErr(err)
|
||||
return handlePgErr(err, op)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
@ -96,11 +106,13 @@ func (r *ContestRepository) DeleteTask(ctx context.Context, taskId int32) error
|
|||
const addParticipantQuery = "INSERT INTO participants (user_id ,contest_id, name) VALUES (?, ?, ?) RETURNING id"
|
||||
|
||||
func (r *ContestRepository) AddParticipant(ctx context.Context, contestId int32, userId int32) (int32, error) {
|
||||
const op = "ContestRepository.AddParticipant"
|
||||
|
||||
query := r.db.Rebind(addParticipantQuery)
|
||||
name := ""
|
||||
rows, err := r.db.QueryxContext(ctx, query, contestId, userId, name)
|
||||
if err != nil {
|
||||
return 0, handlePgErr(err)
|
||||
return 0, handlePgErr(err, op)
|
||||
}
|
||||
defer rows.Close()
|
||||
var id int32
|
||||
|
@ -115,10 +127,12 @@ func (r *ContestRepository) AddParticipant(ctx context.Context, contestId int32,
|
|||
const deleteParticipantQuery = "DELETE FROM participants WHERE id=?"
|
||||
|
||||
func (r *ContestRepository) DeleteParticipant(ctx context.Context, participantId int32) error {
|
||||
const op = "ContestRepository.DeleteParticipant"
|
||||
|
||||
query := r.db.Rebind(deleteParticipantQuery)
|
||||
_, err := r.db.ExecContext(ctx, query, participantId)
|
||||
if err != nil {
|
||||
return handlePgErr(err)
|
||||
return handlePgErr(err, op)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -22,10 +22,12 @@ func NewProblemRepository(db *sqlx.DB, logger *zap.Logger) *ProblemRepository {
|
|||
const createProblemQuery = "INSERT INTO problems (title) VALUES (?) RETURNING id"
|
||||
|
||||
func (r *ProblemRepository) CreateProblem(ctx context.Context, title string) (int32, error) {
|
||||
const op = "ProblemRepository.CreateProblem"
|
||||
|
||||
query := r.db.Rebind(createProblemQuery)
|
||||
rows, err := r.db.QueryxContext(ctx, query, title)
|
||||
if err != nil {
|
||||
return 0, handlePgErr(err)
|
||||
return 0, handlePgErr(err, op)
|
||||
}
|
||||
|
||||
defer rows.Close()
|
||||
|
@ -33,7 +35,7 @@ func (r *ProblemRepository) CreateProblem(ctx context.Context, title string) (in
|
|||
rows.Next()
|
||||
err = rows.Scan(&id)
|
||||
if err != nil {
|
||||
return 0, handlePgErr(err)
|
||||
return 0, handlePgErr(err, op)
|
||||
}
|
||||
|
||||
return id, nil
|
||||
|
@ -42,11 +44,13 @@ func (r *ProblemRepository) CreateProblem(ctx context.Context, title string) (in
|
|||
const readProblemQuery = "SELECT * from problems WHERE id=? LIMIT 1"
|
||||
|
||||
func (r *ProblemRepository) ReadProblemById(ctx context.Context, id int32) (*models.Problem, error) {
|
||||
const op = "ProblemRepository.ReadProblemById"
|
||||
|
||||
var problem models.Problem
|
||||
query := r.db.Rebind(readProblemQuery)
|
||||
err := r.db.GetContext(ctx, &problem, query, id)
|
||||
if err != nil {
|
||||
return nil, handlePgErr(err)
|
||||
return nil, handlePgErr(err, op)
|
||||
}
|
||||
return &problem, nil
|
||||
}
|
||||
|
@ -54,10 +58,12 @@ func (r *ProblemRepository) ReadProblemById(ctx context.Context, id int32) (*mod
|
|||
const deleteProblemQuery = "DELETE FROM problems WHERE id=?"
|
||||
|
||||
func (r *ProblemRepository) DeleteProblem(ctx context.Context, id int32) error {
|
||||
const op = "ProblemRepository.DeleteProblem"
|
||||
|
||||
query := r.db.Rebind(deleteProblemQuery)
|
||||
_, err := r.db.ExecContext(ctx, query, id)
|
||||
if err != nil {
|
||||
return handlePgErr(err)
|
||||
return handlePgErr(err, op)
|
||||
}
|
||||
|
||||
return nil
|
||||
|
|
4
main.go
4
main.go
|
@ -6,7 +6,7 @@ import (
|
|||
"git.sch9.ru/new_gate/ms-tester/internal/tester/delivery/rest"
|
||||
problemsRepository "git.sch9.ru/new_gate/ms-tester/internal/tester/repository"
|
||||
testerUseCase "git.sch9.ru/new_gate/ms-tester/internal/tester/usecase"
|
||||
"git.sch9.ru/new_gate/ms-tester/pkg/external/postgres"
|
||||
"git.sch9.ru/new_gate/ms-tester/pkg"
|
||||
testerv1 "git.sch9.ru/new_gate/ms-tester/proto/tester/v1"
|
||||
"github.com/gofiber/fiber/v2"
|
||||
fiberlogger "github.com/gofiber/fiber/v2/middleware/logger"
|
||||
|
@ -34,7 +34,7 @@ func main() {
|
|||
}
|
||||
|
||||
logger.Info("connecting to postgres")
|
||||
db, err := postgres.NewPostgresDB(cfg.PostgresDSN)
|
||||
db, err := pkg.NewPostgresDB(cfg.PostgresDSN)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
|
|
1
pkg/aws-s3-client.go
Normal file
1
pkg/aws-s3-client.go
Normal file
|
@ -0,0 +1 @@
|
|||
package pkg
|
37
pkg/errors.go
Normal file
37
pkg/errors.go
Normal file
|
@ -0,0 +1,37 @@
|
|||
package pkg
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"net/http"
|
||||
)
|
||||
|
||||
var (
|
||||
NoPermission = errors.New("no permission")
|
||||
ErrUnauthenticated = errors.New("unauthenticated")
|
||||
ErrUnhandled = errors.New("unhandled")
|
||||
ErrNotFound = errors.New("not found")
|
||||
ErrBadInput = errors.New("bad input")
|
||||
ErrInternal = errors.New("internal")
|
||||
)
|
||||
|
||||
func Wrap(basic error, err error, op string, msg string) error {
|
||||
return errors.Join(basic, err, fmt.Errorf("during %s: %s", op, msg))
|
||||
}
|
||||
|
||||
func ToREST(err error) int {
|
||||
switch {
|
||||
case errors.Is(err, ErrUnauthenticated):
|
||||
return http.StatusUnauthorized
|
||||
case errors.Is(err, ErrBadInput):
|
||||
return http.StatusBadRequest
|
||||
case errors.Is(err, ErrNotFound):
|
||||
return http.StatusNotFound
|
||||
case errors.Is(err, ErrInternal):
|
||||
return http.StatusInternalServerError
|
||||
case errors.Is(err, NoPermission):
|
||||
return http.StatusForbidden
|
||||
}
|
||||
|
||||
return http.StatusInternalServerError
|
||||
}
|
1
pkg/external/aws/client.go
vendored
1
pkg/external/aws/client.go
vendored
|
@ -1 +0,0 @@
|
|||
package aws
|
|
@ -1,4 +1,4 @@
|
|||
package pandoc
|
||||
package pkg
|
||||
|
||||
import (
|
||||
"bytes"
|
|
@ -1,4 +1,4 @@
|
|||
package postgres
|
||||
package pkg
|
||||
|
||||
import (
|
||||
_ "github.com/jackc/pgx/v5/stdlib"
|
|
@ -1,4 +1,4 @@
|
|||
package rabbitmq
|
||||
package pkg
|
||||
|
||||
import amqp "github.com/rabbitmq/amqp091-go"
|
||||
|
|
@ -1,132 +0,0 @@
|
|||
package utils
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"go.uber.org/zap/zapcore"
|
||||
"runtime"
|
||||
)
|
||||
|
||||
type code uint8
|
||||
|
||||
const (
|
||||
ErrValidationFailed code = 1
|
||||
ErrInternal code = 2
|
||||
ErrExternal code = 3
|
||||
ErrNoPermission code = 4
|
||||
ErrUnknown code = 5
|
||||
ErrDeadlineExceeded code = 6
|
||||
ErrNotFound code = 7
|
||||
ErrAlreadyExists code = 8
|
||||
ErrConflict code = 9
|
||||
ErrUnimplemented code = 10
|
||||
ErrBadInput code = 11
|
||||
ErrUnauthenticated code = 12
|
||||
)
|
||||
|
||||
func (c code) String() string {
|
||||
switch {
|
||||
case errors.Is(c, ErrValidationFailed):
|
||||
return "validation error"
|
||||
case errors.Is(c, ErrInternal):
|
||||
return "internal error"
|
||||
case errors.Is(c, ErrExternal):
|
||||
return "external error"
|
||||
case errors.Is(c, ErrNoPermission):
|
||||
return "permission error"
|
||||
case errors.Is(c, ErrUnknown):
|
||||
return "unknown error"
|
||||
case errors.Is(c, ErrDeadlineExceeded):
|
||||
return "deadline error"
|
||||
case errors.Is(c, ErrNotFound):
|
||||
return "not found error"
|
||||
case errors.Is(c, ErrAlreadyExists):
|
||||
return "already exists error"
|
||||
case errors.Is(c, ErrConflict):
|
||||
return "conflict error"
|
||||
case errors.Is(c, ErrUnimplemented):
|
||||
return "unimplemented error"
|
||||
case errors.Is(c, ErrBadInput):
|
||||
return "bad input error"
|
||||
}
|
||||
|
||||
panic("unimplemented")
|
||||
}
|
||||
|
||||
func (c code) Error() string {
|
||||
return c.String()
|
||||
}
|
||||
|
||||
type layer uint8
|
||||
|
||||
const (
|
||||
LayerTransport layer = 1
|
||||
LayerService layer = 2
|
||||
LayerStorage layer = 3
|
||||
)
|
||||
|
||||
func (l layer) String() string {
|
||||
switch l {
|
||||
case LayerTransport:
|
||||
return "transport"
|
||||
case LayerService:
|
||||
return "service"
|
||||
case LayerStorage:
|
||||
return "storage"
|
||||
}
|
||||
|
||||
panic("unimplemented")
|
||||
}
|
||||
|
||||
func location(skip int) string {
|
||||
_, file, line, _ := runtime.Caller(skip)
|
||||
return fmt.Sprintf("%s:%d", file, line)
|
||||
}
|
||||
|
||||
type Error struct {
|
||||
src error
|
||||
layer layer
|
||||
code code
|
||||
msg string
|
||||
loc string
|
||||
}
|
||||
|
||||
func wrap(src error, layer layer, class code, msg string, loc string) *Error {
|
||||
return &Error{
|
||||
src: src,
|
||||
layer: layer,
|
||||
code: class,
|
||||
msg: msg,
|
||||
loc: loc,
|
||||
}
|
||||
}
|
||||
|
||||
func (e *Error) Unwrap() []error {
|
||||
return []error{e.src, e.code}
|
||||
}
|
||||
|
||||
func (e *Error) Error() string {
|
||||
return fmt.Sprintf("%s: %s", e.code.String(), e.msg)
|
||||
}
|
||||
|
||||
func (e *Error) MarshalLogObject(encoder zapcore.ObjectEncoder) error {
|
||||
if e.src != nil {
|
||||
encoder.AddString("src", e.src.Error())
|
||||
}
|
||||
encoder.AddString("layer", e.layer.String())
|
||||
encoder.AddString("code", e.code.String())
|
||||
encoder.AddString("msg", e.msg)
|
||||
return nil
|
||||
}
|
||||
|
||||
func TransportError(src error, code code, msg string) error {
|
||||
return wrap(src, LayerTransport, code, msg, location(2))
|
||||
}
|
||||
|
||||
func ServiceError(src error, code code, msg string) error {
|
||||
return wrap(src, LayerService, code, msg, location(2))
|
||||
}
|
||||
|
||||
func StorageError(src error, code code, msg string) error {
|
||||
return wrap(src, LayerStorage, code, msg, location(2))
|
||||
}
|
|
@ -1,33 +0,0 @@
|
|||
package utils
|
||||
|
||||
import (
|
||||
"google.golang.org/protobuf/types/known/timestamppb"
|
||||
"time"
|
||||
)
|
||||
|
||||
func AsTimeP(t time.Time) *time.Time {
|
||||
return &t
|
||||
}
|
||||
|
||||
func AsInt32P(v int32) *int32 {
|
||||
return &v
|
||||
}
|
||||
|
||||
func AsStringP(str string) *string {
|
||||
return &str
|
||||
}
|
||||
|
||||
func TimeP(t *timestamppb.Timestamp) *time.Time {
|
||||
if t == nil {
|
||||
return nil
|
||||
}
|
||||
tt := t.AsTime()
|
||||
return &tt
|
||||
}
|
||||
|
||||
func TimestampP(t *time.Time) *timestamppb.Timestamp {
|
||||
if t == nil {
|
||||
return nil
|
||||
}
|
||||
return timestamppb.New(*t)
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package valkey
|
||||
package pkg
|
||||
|
||||
import "github.com/valkey-io/valkey-go"
|
||||
|
Loading…
Add table
Reference in a new issue