todo/internal/todo/service/service.go

113 lines
2.2 KiB
Go

package service
import (
"context"
"errors"
"log/slog"
"gitea.michaelthomson.dev/mthomson/habits/internal/todo/repository"
)
var (
ErrNotFound error = errors.New("Todo cannot be found")
)
type Todo struct {
Id int64
Name string
Done bool
}
func NewTodo(name string, done bool) Todo {
return Todo{Name: name, Done: done}
}
func TodoFromTodoRow(todoRow repository.TodoRow) Todo {
return Todo{Id: todoRow.Id, Name: todoRow.Name, Done: todoRow.Done}
}
func TodoRowFromTodo(todo Todo) repository.TodoRow {
return repository.TodoRow{Id: todo.Id, Name: todo.Name, Done: todo.Done}
}
func (t Todo) Equal(todo Todo) bool {
return t.Id == todo.Id && t.Name == todo.Name && t.Done == todo.Done
}
type TodoRepository interface {
Create(todo repository.TodoRow) (repository.TodoRow, error)
GetById(id int64) (repository.TodoRow, error)
Update(todo repository.TodoRow) error
Delete(id int64) error
}
type TodoService struct {
logger *slog.Logger
repo TodoRepository
}
func NewTodoService(logger *slog.Logger, todoRepo TodoRepository) *TodoService {
return &TodoService{
logger: logger,
repo: todoRepo,
}
}
func (s *TodoService) GetTodo(ctx context.Context, id int64) (Todo, error) {
todo, err := s.repo.GetById(id)
if err != nil {
if err == repository.ErrNotFound {
return Todo{}, ErrNotFound
}
s.logger.ErrorContext(ctx, err.Error())
return Todo{}, err
}
return TodoFromTodoRow(todo), err
}
func (s *TodoService) CreateTodo(ctx context.Context, todo Todo) (Todo, error) {
todoRow := TodoRowFromTodo(todo)
newTodoRow, err := s.repo.Create(todoRow)
if err != nil {
s.logger.ErrorContext(ctx, err.Error())
return Todo{}, err
}
return TodoFromTodoRow(newTodoRow), err
}
func (s *TodoService) DeleteTodo(ctx context.Context, id int64) error {
err := s.repo.Delete(id)
if err == repository.ErrNotFound {
return ErrNotFound
}
if (err != nil) {
s.logger.ErrorContext(ctx, err.Error())
}
return err
}
func (s *TodoService) UpdateTodo(ctx context.Context, todo Todo) error {
todoRow := TodoRowFromTodo(todo)
err := s.repo.Update(todoRow)
if err == repository.ErrNotFound {
return ErrNotFound
}
if (err != nil) {
s.logger.ErrorContext(ctx, err.Error())
}
return err
}