gte/cmd/cli/command/command.go

161 lines
3.5 KiB
Go
Raw Normal View History

2021-06-25 09:14:27 +02:00
package command
import (
2021-07-09 13:25:50 +02:00
"errors"
2022-09-28 08:49:25 +02:00
"fmt"
2021-07-27 07:10:01 +02:00
"strconv"
2022-09-28 08:49:25 +02:00
"strings"
2021-06-25 09:14:27 +02:00
2021-09-19 11:59:26 +02:00
"ewintr.nl/gte/internal/configuration"
2022-09-28 08:49:25 +02:00
"ewintr.nl/gte/internal/task"
2021-06-25 09:14:27 +02:00
)
2021-07-09 13:25:50 +02:00
var (
ErrInvalidAmountOfArgs = errors.New("invalid amount of args")
2021-08-20 10:55:11 +02:00
ErrInvalidArg = errors.New("invalid argument")
2021-07-29 07:01:24 +02:00
ErrCouldNotFindTask = errors.New("could not find task")
2021-08-20 10:55:11 +02:00
ErrUnknownFolder = errors.New("unknown folder")
2022-09-28 08:49:25 +02:00
ErrFieldAlreadyUsed = errors.New("field was already used")
ErrInvalidDate = errors.New("could not understand date format")
ErrInvalidProject = errors.New("could not understand project")
2021-07-09 13:25:50 +02:00
)
2021-06-25 09:14:27 +02:00
type Command interface {
2021-07-09 09:42:44 +02:00
Do() string
2021-06-25 09:14:27 +02:00
}
func Parse(args []string, conf *configuration.Configuration) (Command, error) {
if len(args) == 0 {
return NewEmpty()
}
2021-07-09 13:25:50 +02:00
cmd, cmdArgs := args[0], args[1:]
2021-07-27 07:10:01 +02:00
id, err := strconv.Atoi(cmd)
if err == nil {
return parseTaskCommand(id, cmdArgs, conf)
}
2021-06-25 09:14:27 +02:00
switch cmd {
2021-09-03 07:12:16 +02:00
case "fetch":
return NewFetch(conf)
2021-09-03 09:31:41 +02:00
case "send":
return NewSend(conf)
2021-11-01 10:01:21 +01:00
case "sync":
return NewSync(conf)
2021-06-25 09:14:27 +02:00
case "today":
return NewToday(conf)
2021-07-09 09:51:37 +02:00
case "tomorrow":
return NewTomorrow(conf)
2021-08-20 11:27:12 +02:00
case "week":
return NewWeek(conf)
2021-08-20 08:18:26 +02:00
case "project":
return NewProject(conf, cmdArgs)
2021-08-19 07:06:18 +02:00
case "projects":
return NewProjects(conf)
2021-08-20 08:18:26 +02:00
case "folder":
return NewFolder(conf, cmdArgs)
2021-09-04 12:20:35 +02:00
case "new":
return NewNew(conf, cmdArgs)
2021-08-20 10:55:11 +02:00
case "remote":
return parseRemote(conf, cmdArgs)
2021-06-25 09:14:27 +02:00
default:
return NewEmpty()
}
}
2021-07-27 07:10:01 +02:00
func parseTaskCommand(id int, tArgs []string, conf *configuration.Configuration) (Command, error) {
if len(tArgs) == 0 {
return NewShow(id, conf)
}
2021-07-29 07:01:24 +02:00
cmd, cmdArgs := tArgs[0], tArgs[1:]
2021-07-28 07:09:39 +02:00
switch cmd {
case "done":
2021-07-29 07:01:24 +02:00
fallthrough
case "del":
2021-07-28 07:09:39 +02:00
return NewDone(id, conf)
2021-07-29 07:01:24 +02:00
case "mod":
return NewUpdate(id, conf, cmdArgs)
2021-07-28 07:09:39 +02:00
default:
return NewShow(id, conf)
}
2021-07-27 07:10:01 +02:00
}
2021-08-20 10:55:11 +02:00
func parseRemote(conf *configuration.Configuration, cmdArgs []string) (Command, error) {
switch {
case len(cmdArgs) < 1:
cmd, _ := NewEmpty()
return cmd, ErrInvalidAmountOfArgs
case cmdArgs[0] == "recur":
return NewRecur(conf, cmdArgs[1:])
case cmdArgs[0] == "inbox":
return NewInbox(conf)
default:
cmd, _ := NewEmpty()
return cmd, ErrInvalidArg
}
}
2022-09-28 08:49:25 +02:00
func ParseTaskFieldArgs(args []string) (*task.LocalUpdate, error) {
lu := &task.LocalUpdate{}
action, fields := []string{}, []string{}
for _, f := range args {
if project, ok := parseProjectField(f); ok {
if lu.Project != "" {
return &task.LocalUpdate{}, fmt.Errorf("%w: %s", ErrFieldAlreadyUsed, task.FIELD_PROJECT)
}
if project == "" {
return &task.LocalUpdate{}, ErrInvalidProject
}
lu.Project = project
fields = append(fields, task.FIELD_PROJECT)
continue
}
if due, ok := parseDueField(f); ok {
if due.IsZero() {
return &task.LocalUpdate{}, ErrInvalidDate
}
if !lu.Due.IsZero() {
return &task.LocalUpdate{}, fmt.Errorf("%w: %s", ErrFieldAlreadyUsed, task.FIELD_DUE)
}
lu.Due = due
fields = append(fields, task.FIELD_DUE)
continue
}
if len(f) > 0 {
action = append(action, f)
}
}
if len(action) > 0 {
lu.Action = strings.Join(action, " ")
fields = append(fields, task.FIELD_ACTION)
}
lu.Fields = fields
return lu, nil
}
func parseProjectField(s string) (string, bool) {
if !strings.HasPrefix(s, "project:") && !strings.HasPrefix(s, "p:") {
return "", false
}
split := strings.SplitN(s, ":", 2)
return split[1], true
}
func parseDueField(s string) (task.Date, bool) {
if !strings.HasPrefix(s, "due:") && !strings.HasPrefix(s, "d:") {
return task.Date{}, false
}
split := strings.SplitN(s, ":", 2)
due := task.NewDateFromString(split[1])
return due, true
}