date, folders and fix cleanup
This commit is contained in:
parent
9092336bf9
commit
204c660d34
|
@ -1,14 +1,31 @@
|
||||||
package task
|
package task
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
DateFormat = "2006-01-02 (Monday)"
|
||||||
|
)
|
||||||
|
|
||||||
|
var Today Date
|
||||||
|
|
||||||
|
func init() {
|
||||||
|
year, month, day := time.Now().Date()
|
||||||
|
Today = NewDate(year, int(month), day)
|
||||||
|
}
|
||||||
|
|
||||||
type Date struct {
|
type Date struct {
|
||||||
t time.Time
|
t time.Time
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewDate(year, month, day int) *Date {
|
func NewDate(year, month, day int) Date {
|
||||||
|
|
||||||
|
if year == 0 && month == 0 && day == 0 {
|
||||||
|
return Date{}
|
||||||
|
}
|
||||||
|
|
||||||
var m time.Month
|
var m time.Month
|
||||||
switch month {
|
switch month {
|
||||||
case 1:
|
case 1:
|
||||||
|
@ -37,21 +54,73 @@ func NewDate(year, month, day int) *Date {
|
||||||
m = time.December
|
m = time.December
|
||||||
}
|
}
|
||||||
|
|
||||||
t := time.Date(year, m, day, 10, 0, 0, 0, time.UTC)
|
t := time.Date(year, m, day, 0, 0, 0, 0, time.UTC)
|
||||||
|
|
||||||
if year == 0 && month == 0 && day == 0 {
|
return Date{
|
||||||
t = time.Time{}
|
|
||||||
}
|
|
||||||
|
|
||||||
return &Date{
|
|
||||||
t: t,
|
t: t,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func NewDateFromString(date string) Date {
|
||||||
|
date = strings.ToLower(strings.TrimSpace(date))
|
||||||
|
|
||||||
|
if date == "no date" || date == "" {
|
||||||
|
return Date{}
|
||||||
|
}
|
||||||
|
|
||||||
|
t, err := time.Parse(DateFormat, date)
|
||||||
|
if err == nil {
|
||||||
|
return Date{t: t}
|
||||||
|
}
|
||||||
|
t, err = time.Parse("2006-01-02", date)
|
||||||
|
if err == nil {
|
||||||
|
return Date{t: t}
|
||||||
|
}
|
||||||
|
|
||||||
|
weekday := Today.Weekday()
|
||||||
|
var newWeekday time.Weekday
|
||||||
|
switch {
|
||||||
|
case date == "monday" || date == "maandag":
|
||||||
|
newWeekday = time.Monday
|
||||||
|
case date == "tuesday" || date == "dinsdag":
|
||||||
|
newWeekday = time.Tuesday
|
||||||
|
case date == "wednesday" || date == "woensdag":
|
||||||
|
newWeekday = time.Wednesday
|
||||||
|
case date == "thursday" || date == "donderdag":
|
||||||
|
newWeekday = time.Thursday
|
||||||
|
case date == "friday" || date == "vrijdag":
|
||||||
|
newWeekday = time.Friday
|
||||||
|
case date == "saturday" || date == "zaterdag":
|
||||||
|
newWeekday = time.Saturday
|
||||||
|
case date == "sunday" || date == "zondag":
|
||||||
|
newWeekday = time.Sunday
|
||||||
|
}
|
||||||
|
|
||||||
|
daysToAdd := int(newWeekday) - weekday
|
||||||
|
if daysToAdd < 0 {
|
||||||
|
daysToAdd += 7
|
||||||
|
}
|
||||||
|
|
||||||
|
return Today.Add(daysToAdd)
|
||||||
|
}
|
||||||
|
|
||||||
func (d *Date) String() string {
|
func (d *Date) String() string {
|
||||||
if d.t.IsZero() {
|
if d.t.IsZero() {
|
||||||
return "no date"
|
return "no date"
|
||||||
}
|
}
|
||||||
|
|
||||||
return d.t.Format("2006-01-02")
|
return strings.ToLower(d.t.Format(DateFormat))
|
||||||
|
}
|
||||||
|
|
||||||
|
func (d *Date) IsZero() bool {
|
||||||
|
return d.t.IsZero()
|
||||||
|
}
|
||||||
|
|
||||||
|
func (d *Date) Weekday() int {
|
||||||
|
return int(d.t.Weekday())
|
||||||
|
}
|
||||||
|
|
||||||
|
func (d *Date) Add(days int) Date {
|
||||||
|
year, month, day := d.t.Date()
|
||||||
|
return NewDate(year, int(month), day+days)
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,10 +7,58 @@ import (
|
||||||
"git.sr.ht/~ewintr/gte/internal/task"
|
"git.sr.ht/~ewintr/gte/internal/task"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func TestNewDateFromString(t *testing.T) {
|
||||||
|
task.Today = task.NewDate(2021, 1, 30)
|
||||||
|
for _, tc := range []struct {
|
||||||
|
name string
|
||||||
|
input string
|
||||||
|
exp task.Date
|
||||||
|
}{
|
||||||
|
{
|
||||||
|
name: "empty",
|
||||||
|
exp: task.Date{},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "no date",
|
||||||
|
input: "no date",
|
||||||
|
exp: task.Date{},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "normal",
|
||||||
|
input: "2021-01-30 (saturday)",
|
||||||
|
exp: task.NewDate(2021, 1, 30),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "short",
|
||||||
|
input: "2021-01-30",
|
||||||
|
exp: task.NewDate(2021, 1, 30),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "english dayname lowercase",
|
||||||
|
input: "monday",
|
||||||
|
exp: task.NewDate(2021, 2, 1),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "english dayname capitalized",
|
||||||
|
input: "Monday",
|
||||||
|
exp: task.NewDate(2021, 2, 1),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "ducth dayname lowercase",
|
||||||
|
input: "maandag",
|
||||||
|
exp: task.NewDate(2021, 2, 1),
|
||||||
|
},
|
||||||
|
} {
|
||||||
|
t.Run(tc.name, func(t *testing.T) {
|
||||||
|
test.Equals(t, tc.exp, task.NewDateFromString(tc.input))
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func TestDateString(t *testing.T) {
|
func TestDateString(t *testing.T) {
|
||||||
for _, tc := range []struct {
|
for _, tc := range []struct {
|
||||||
name string
|
name string
|
||||||
date *task.Date
|
date task.Date
|
||||||
exp string
|
exp string
|
||||||
}{
|
}{
|
||||||
{
|
{
|
||||||
|
@ -21,12 +69,12 @@ func TestDateString(t *testing.T) {
|
||||||
{
|
{
|
||||||
name: "normal",
|
name: "normal",
|
||||||
date: task.NewDate(2021, 1, 30),
|
date: task.NewDate(2021, 1, 30),
|
||||||
exp: "2021-01-30",
|
exp: "2021-01-30 (saturday)",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "normalize",
|
name: "normalize",
|
||||||
date: task.NewDate(2021, 1, 32),
|
date: task.NewDate(2021, 1, 32),
|
||||||
exp: "2021-02-01",
|
exp: "2021-02-01 (monday)",
|
||||||
},
|
},
|
||||||
} {
|
} {
|
||||||
t.Run(tc.name, func(t *testing.T) {
|
t.Run(tc.name, func(t *testing.T) {
|
||||||
|
|
|
@ -3,6 +3,7 @@ package task
|
||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"strconv"
|
||||||
|
|
||||||
"git.sr.ht/~ewintr/gte/pkg/mstore"
|
"git.sr.ht/~ewintr/gte/pkg/mstore"
|
||||||
)
|
)
|
||||||
|
@ -67,43 +68,52 @@ func (tr *TaskRepo) Update(t *Task) error {
|
||||||
|
|
||||||
// Cleanup removes older versions of tasks
|
// Cleanup removes older versions of tasks
|
||||||
func (tr *TaskRepo) CleanUp() error {
|
func (tr *TaskRepo) CleanUp() error {
|
||||||
// loop through folders, get all tasks
|
// loop through folders, get all task version info
|
||||||
taskSet := make(map[string][]*Task)
|
type msgInfo struct {
|
||||||
|
Version int
|
||||||
|
Message *mstore.Message
|
||||||
|
}
|
||||||
|
msgsSet := make(map[string][]msgInfo)
|
||||||
|
|
||||||
for _, folder := range knownFolders {
|
for _, folder := range knownFolders {
|
||||||
tasks, err := tr.FindAll(folder)
|
msgs, err := tr.mstore.Messages(folder)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return fmt.Errorf("%w: %v", ErrMStoreError, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, t := range tasks {
|
for _, msg := range msgs {
|
||||||
if _, ok := taskSet[t.Id]; !ok {
|
id, _ := FieldFromBody(FIELD_ID, msg.Body)
|
||||||
taskSet[t.Id] = []*Task{}
|
versionStr, _ := FieldFromBody(FIELD_VERSION, msg.Body)
|
||||||
|
version, _ := strconv.Atoi(versionStr)
|
||||||
|
if _, ok := msgsSet[id]; !ok {
|
||||||
|
msgsSet[id] = []msgInfo{}
|
||||||
}
|
}
|
||||||
taskSet[t.Id] = append(taskSet[t.Id], t)
|
msgsSet[id] = append(msgsSet[id], msgInfo{
|
||||||
|
Version: version,
|
||||||
|
Message: msg,
|
||||||
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// determine which ones need to be gone
|
// determine which ones need to be gone
|
||||||
var tobeRemoved []*Task
|
var tobeRemoved []*mstore.Message
|
||||||
for _, tasks := range taskSet {
|
for _, mInfos := range msgsSet {
|
||||||
maxVersion := 0
|
maxVersion := 0
|
||||||
for _, t := range tasks {
|
for _, mInfo := range mInfos {
|
||||||
if t.Version > maxVersion {
|
if mInfo.Version > maxVersion {
|
||||||
maxVersion = t.Version
|
maxVersion = mInfo.Version
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
for _, mInfo := range mInfos {
|
||||||
for _, t := range tasks {
|
if mInfo.Version < maxVersion {
|
||||||
if t.Version < maxVersion {
|
tobeRemoved = append(tobeRemoved, mInfo.Message)
|
||||||
tobeRemoved = append(tobeRemoved, t)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// remove them
|
// remove them
|
||||||
for _, t := range tobeRemoved {
|
for _, msg := range tobeRemoved {
|
||||||
if err := tr.mstore.Remove(t.Message); err != nil {
|
if err := tr.mstore.Remove(msg); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -201,6 +201,5 @@ version: 3
|
||||||
}}
|
}}
|
||||||
actPlanned, err := mem.Messages(folderPlanned)
|
actPlanned, err := mem.Messages(folderPlanned)
|
||||||
test.OK(t, err)
|
test.OK(t, err)
|
||||||
fmt.Printf("act: %+v\n", actPlanned[0])
|
|
||||||
test.Equals(t, expPlanned, actPlanned)
|
test.Equals(t, expPlanned, actPlanned)
|
||||||
}
|
}
|
||||||
|
|
|
@ -78,10 +78,12 @@ type Task struct {
|
||||||
func New(msg *mstore.Message) *Task {
|
func New(msg *mstore.Message) *Task {
|
||||||
// Id
|
// Id
|
||||||
dirty := false
|
dirty := false
|
||||||
|
newId := false
|
||||||
id, d := FieldFromBody(FIELD_ID, msg.Body)
|
id, d := FieldFromBody(FIELD_ID, msg.Body)
|
||||||
if id == "" {
|
if id == "" {
|
||||||
id = uuid.New().String()
|
id = uuid.New().String()
|
||||||
dirty = true
|
dirty = true
|
||||||
|
newId = true
|
||||||
}
|
}
|
||||||
if d {
|
if d {
|
||||||
dirty = true
|
dirty = true
|
||||||
|
@ -106,10 +108,27 @@ func New(msg *mstore.Message) *Task {
|
||||||
dirty = true
|
dirty = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Due
|
||||||
|
dueStr, d := FieldFromBody(FIELD_DUE, msg.Body)
|
||||||
|
if dueStr == "" || d {
|
||||||
|
dirty = true
|
||||||
|
}
|
||||||
|
due := NewDateFromString(dueStr)
|
||||||
|
|
||||||
// Folder
|
// Folder
|
||||||
folder := msg.Folder
|
folderOld := msg.Folder
|
||||||
if folder == FOLDER_INBOX {
|
folderNew := folderOld
|
||||||
folder = FOLDER_NEW
|
if folderOld == FOLDER_INBOX {
|
||||||
|
switch {
|
||||||
|
case newId:
|
||||||
|
folderNew = FOLDER_NEW
|
||||||
|
case !newId && due.IsZero():
|
||||||
|
folderNew = FOLDER_UNPLANNED
|
||||||
|
case !newId && !due.IsZero():
|
||||||
|
folderNew = FOLDER_PLANNED
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if folderOld != folderNew {
|
||||||
dirty = true
|
dirty = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -126,8 +145,9 @@ func New(msg *mstore.Message) *Task {
|
||||||
return &Task{
|
return &Task{
|
||||||
Id: id,
|
Id: id,
|
||||||
Version: version,
|
Version: version,
|
||||||
Folder: folder,
|
Folder: folderNew,
|
||||||
Action: action,
|
Action: action,
|
||||||
|
Due: due,
|
||||||
Project: project,
|
Project: project,
|
||||||
Message: msg,
|
Message: msg,
|
||||||
Current: true,
|
Current: true,
|
||||||
|
@ -136,10 +156,16 @@ func New(msg *mstore.Message) *Task {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *Task) FormatSubject() string {
|
func (t *Task) FormatSubject() string {
|
||||||
order := []string{FIELD_PROJECT, FIELD_ACTION}
|
var order []string
|
||||||
|
if !t.Due.IsZero() {
|
||||||
|
order = append(order, FIELD_DUE)
|
||||||
|
}
|
||||||
|
order = append(order, FIELD_PROJECT, FIELD_ACTION)
|
||||||
|
|
||||||
fields := map[string]string{
|
fields := map[string]string{
|
||||||
FIELD_PROJECT: t.Project,
|
FIELD_PROJECT: t.Project,
|
||||||
FIELD_ACTION: t.Action,
|
FIELD_ACTION: t.Action,
|
||||||
|
FIELD_DUE: t.Due.String(),
|
||||||
}
|
}
|
||||||
|
|
||||||
parts := []string{}
|
parts := []string{}
|
||||||
|
@ -154,12 +180,13 @@ func (t *Task) FormatSubject() string {
|
||||||
|
|
||||||
func (t *Task) FormatBody() string {
|
func (t *Task) FormatBody() string {
|
||||||
body := fmt.Sprintf("\n")
|
body := fmt.Sprintf("\n")
|
||||||
order := []string{FIELD_ID, FIELD_VERSION, FIELD_PROJECT, FIELD_ACTION}
|
order := []string{FIELD_ACTION, FIELD_DUE, FIELD_PROJECT, FIELD_VERSION, FIELD_ID}
|
||||||
fields := map[string]string{
|
fields := map[string]string{
|
||||||
FIELD_ID: t.Id,
|
FIELD_ID: t.Id,
|
||||||
FIELD_VERSION: strconv.Itoa(t.Version),
|
FIELD_VERSION: strconv.Itoa(t.Version),
|
||||||
FIELD_PROJECT: t.Project,
|
FIELD_PROJECT: t.Project,
|
||||||
FIELD_ACTION: t.Action,
|
FIELD_ACTION: t.Action,
|
||||||
|
FIELD_DUE: t.Due.String(),
|
||||||
}
|
}
|
||||||
|
|
||||||
keyLen := 0
|
keyLen := 0
|
||||||
|
@ -215,15 +242,11 @@ func FieldFromBody(field, body string) (string, bool) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func FieldFromSubject(field, subject string) string {
|
func FieldFromSubject(field, subject string) string {
|
||||||
if field == FIELD_ACTION {
|
if field != FIELD_ACTION {
|
||||||
return strings.ToLower(subject)
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
return ""
|
terms := strings.Split(subject, SUBJECT_SEPARATOR)
|
||||||
}
|
|
||||||
|
|
||||||
func increment(s string) string {
|
return terms[len(terms)-1]
|
||||||
i, _ := strconv.Atoi(s)
|
|
||||||
i++
|
|
||||||
return strconv.Itoa(i)
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -14,7 +14,7 @@ func TestNewFromMessage(t *testing.T) {
|
||||||
version := 2
|
version := 2
|
||||||
action := "some action"
|
action := "some action"
|
||||||
project := "project"
|
project := "project"
|
||||||
folder := task.FOLDER_NEW
|
date := task.NewDate(2021, 1, 20)
|
||||||
|
|
||||||
for _, tc := range []struct {
|
for _, tc := range []struct {
|
||||||
name string
|
name string
|
||||||
|
@ -33,9 +33,10 @@ func TestNewFromMessage(t *testing.T) {
|
||||||
{
|
{
|
||||||
name: "id, action, project and folder",
|
name: "id, action, project and folder",
|
||||||
message: &mstore.Message{
|
message: &mstore.Message{
|
||||||
Folder: folder,
|
Folder: task.FOLDER_UNPLANNED,
|
||||||
Body: fmt.Sprintf(`
|
Body: fmt.Sprintf(`
|
||||||
id: %s
|
id: %s
|
||||||
|
due: no date
|
||||||
version: %d
|
version: %d
|
||||||
action: %s
|
action: %s
|
||||||
project: %s
|
project: %s
|
||||||
|
@ -46,21 +47,40 @@ project: %s
|
||||||
exp: &task.Task{
|
exp: &task.Task{
|
||||||
Id: id,
|
Id: id,
|
||||||
Version: version,
|
Version: version,
|
||||||
Folder: folder,
|
Folder: task.FOLDER_UNPLANNED,
|
||||||
Action: action,
|
Action: action,
|
||||||
Project: project,
|
Project: project,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "with date",
|
||||||
|
message: &mstore.Message{
|
||||||
|
Folder: task.FOLDER_PLANNED,
|
||||||
|
Body: fmt.Sprintf(`
|
||||||
|
id: %s
|
||||||
|
due: %s
|
||||||
|
version: %d
|
||||||
|
action: %s
|
||||||
|
`, id, date.String(), version, action),
|
||||||
|
},
|
||||||
|
hasId: true,
|
||||||
|
hasVersion: true,
|
||||||
|
exp: &task.Task{
|
||||||
|
Id: id,
|
||||||
|
Folder: task.FOLDER_PLANNED,
|
||||||
|
Action: action,
|
||||||
|
Version: version,
|
||||||
|
Due: date,
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "folder inbox get updated to new",
|
name: "folder inbox get updated to new",
|
||||||
message: &mstore.Message{
|
message: &mstore.Message{
|
||||||
Folder: task.FOLDER_INBOX,
|
Folder: task.FOLDER_INBOX,
|
||||||
Body: fmt.Sprintf(`
|
Body: fmt.Sprintf(`
|
||||||
id: %s
|
|
||||||
action: %s
|
action: %s
|
||||||
`, id, action),
|
`, action),
|
||||||
},
|
},
|
||||||
hasId: true,
|
|
||||||
exp: &task.Task{
|
exp: &task.Task{
|
||||||
Id: id,
|
Id: id,
|
||||||
Folder: task.FOLDER_NEW,
|
Folder: task.FOLDER_NEW,
|
||||||
|
@ -68,13 +88,51 @@ action: %s
|
||||||
Dirty: true,
|
Dirty: true,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "folder inbox gets updated to planned",
|
||||||
|
message: &mstore.Message{
|
||||||
|
Folder: task.FOLDER_INBOX,
|
||||||
|
Body: fmt.Sprintf(`
|
||||||
|
id: %s
|
||||||
|
due: %s
|
||||||
|
action: %s
|
||||||
|
`, id, date.String(), action),
|
||||||
|
},
|
||||||
|
hasId: true,
|
||||||
|
exp: &task.Task{
|
||||||
|
Id: id,
|
||||||
|
Folder: task.FOLDER_PLANNED,
|
||||||
|
Action: action,
|
||||||
|
Due: date,
|
||||||
|
Dirty: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "folder new gets updated to unplanned",
|
||||||
|
message: &mstore.Message{
|
||||||
|
Folder: task.FOLDER_INBOX,
|
||||||
|
Body: fmt.Sprintf(`
|
||||||
|
id: %s
|
||||||
|
due: no date
|
||||||
|
action: %s
|
||||||
|
`, id, action),
|
||||||
|
},
|
||||||
|
hasId: true,
|
||||||
|
exp: &task.Task{
|
||||||
|
Id: id,
|
||||||
|
Folder: task.FOLDER_UNPLANNED,
|
||||||
|
Action: action,
|
||||||
|
Dirty: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "action in subject takes precedence",
|
name: "action in subject takes precedence",
|
||||||
message: &mstore.Message{
|
message: &mstore.Message{
|
||||||
Folder: folder,
|
Folder: task.FOLDER_PLANNED,
|
||||||
Subject: "some other action",
|
Subject: "some other action",
|
||||||
Body: fmt.Sprintf(`
|
Body: fmt.Sprintf(`
|
||||||
id: %s
|
id: %s
|
||||||
|
due: no date
|
||||||
version: %d
|
version: %d
|
||||||
action: %s
|
action: %s
|
||||||
`, id, version, action),
|
`, id, version, action),
|
||||||
|
@ -84,21 +142,21 @@ action: %s
|
||||||
exp: &task.Task{
|
exp: &task.Task{
|
||||||
Id: id,
|
Id: id,
|
||||||
Version: version,
|
Version: version,
|
||||||
Folder: folder,
|
Folder: task.FOLDER_PLANNED,
|
||||||
Action: action,
|
Action: action,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "action from subject if not present in body",
|
name: "action from subject if not present in body",
|
||||||
message: &mstore.Message{
|
message: &mstore.Message{
|
||||||
Folder: folder,
|
Folder: task.FOLDER_PLANNED,
|
||||||
Subject: action,
|
Subject: action,
|
||||||
Body: fmt.Sprintf(`id: %s`, id),
|
Body: fmt.Sprintf(`id: %s`, id),
|
||||||
},
|
},
|
||||||
hasId: true,
|
hasId: true,
|
||||||
exp: &task.Task{
|
exp: &task.Task{
|
||||||
Id: id,
|
Id: id,
|
||||||
Folder: folder,
|
Folder: task.FOLDER_PLANNED,
|
||||||
Action: action,
|
Action: action,
|
||||||
Dirty: true,
|
Dirty: true,
|
||||||
},
|
},
|
||||||
|
@ -106,7 +164,7 @@ action: %s
|
||||||
{
|
{
|
||||||
name: "quoted fields",
|
name: "quoted fields",
|
||||||
message: &mstore.Message{
|
message: &mstore.Message{
|
||||||
Folder: folder,
|
Folder: task.FOLDER_PLANNED,
|
||||||
Body: fmt.Sprintf(`
|
Body: fmt.Sprintf(`
|
||||||
action: %s
|
action: %s
|
||||||
|
|
||||||
|
@ -118,7 +176,7 @@ Forwarded message:
|
||||||
hasId: true,
|
hasId: true,
|
||||||
exp: &task.Task{
|
exp: &task.Task{
|
||||||
Id: id,
|
Id: id,
|
||||||
Folder: folder,
|
Folder: task.FOLDER_PLANNED,
|
||||||
Action: action,
|
Action: action,
|
||||||
Dirty: true,
|
Dirty: true,
|
||||||
},
|
},
|
||||||
|
@ -143,6 +201,7 @@ Forwarded message:
|
||||||
func TestFormatSubject(t *testing.T) {
|
func TestFormatSubject(t *testing.T) {
|
||||||
action := "an action"
|
action := "an action"
|
||||||
project := " a project"
|
project := " a project"
|
||||||
|
due := task.NewDate(2021, 1, 30)
|
||||||
|
|
||||||
for _, tc := range []struct {
|
for _, tc := range []struct {
|
||||||
name string
|
name string
|
||||||
|
@ -155,18 +214,34 @@ func TestFormatSubject(t *testing.T) {
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "action",
|
name: "action",
|
||||||
task: &task.Task{Action: action},
|
task: &task.Task{
|
||||||
exp: action,
|
Action: action,
|
||||||
|
},
|
||||||
|
exp: action,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "project",
|
name: "project",
|
||||||
task: &task.Task{Project: project},
|
task: &task.Task{
|
||||||
exp: project,
|
Project: project,
|
||||||
|
},
|
||||||
|
exp: project,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "action and project",
|
name: "action and project",
|
||||||
task: &task.Task{Action: action, Project: project},
|
task: &task.Task{
|
||||||
exp: fmt.Sprintf("%s - %s", project, action),
|
Action: action,
|
||||||
|
Project: project,
|
||||||
|
},
|
||||||
|
exp: fmt.Sprintf("%s - %s", project, action),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "action, date and project",
|
||||||
|
task: &task.Task{
|
||||||
|
Action: action,
|
||||||
|
Project: project,
|
||||||
|
Due: due,
|
||||||
|
},
|
||||||
|
exp: fmt.Sprintf("%s - %s - %s", due.String(), project, action),
|
||||||
},
|
},
|
||||||
} {
|
} {
|
||||||
t.Run(tc.name, func(t *testing.T) {
|
t.Run(tc.name, func(t *testing.T) {
|
||||||
|
@ -190,10 +265,11 @@ func TestFormatBody(t *testing.T) {
|
||||||
name: "empty",
|
name: "empty",
|
||||||
task: &task.Task{},
|
task: &task.Task{},
|
||||||
exp: `
|
exp: `
|
||||||
id:
|
|
||||||
version: 0
|
|
||||||
project:
|
|
||||||
action:
|
action:
|
||||||
|
due: no date
|
||||||
|
project:
|
||||||
|
version: 0
|
||||||
|
id:
|
||||||
`,
|
`,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -203,15 +279,17 @@ action:
|
||||||
Version: version,
|
Version: version,
|
||||||
Action: action,
|
Action: action,
|
||||||
Project: project,
|
Project: project,
|
||||||
|
Due: task.NewDate(2021, 1, 30),
|
||||||
Message: &mstore.Message{
|
Message: &mstore.Message{
|
||||||
Body: "previous body",
|
Body: "previous body",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
exp: `
|
exp: `
|
||||||
id: an id
|
|
||||||
version: 6
|
|
||||||
project: project
|
|
||||||
action: an action
|
action: an action
|
||||||
|
due: 2021-01-30 (saturday)
|
||||||
|
project: project
|
||||||
|
version: 6
|
||||||
|
id: an id
|
||||||
|
|
||||||
Previous version:
|
Previous version:
|
||||||
|
|
||||||
|
@ -327,6 +405,7 @@ field: valuea
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestFieldFromSubject(t *testing.T) {
|
func TestFieldFromSubject(t *testing.T) {
|
||||||
|
action := "action"
|
||||||
for _, tc := range []struct {
|
for _, tc := range []struct {
|
||||||
name string
|
name string
|
||||||
field string
|
field string
|
||||||
|
@ -335,7 +414,7 @@ func TestFieldFromSubject(t *testing.T) {
|
||||||
}{
|
}{
|
||||||
{
|
{
|
||||||
name: "empty field",
|
name: "empty field",
|
||||||
subject: "subject",
|
subject: action,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "empty subject",
|
name: "empty subject",
|
||||||
|
@ -344,13 +423,25 @@ func TestFieldFromSubject(t *testing.T) {
|
||||||
{
|
{
|
||||||
name: "unknown field",
|
name: "unknown field",
|
||||||
field: "unknown",
|
field: "unknown",
|
||||||
subject: "subject",
|
subject: action,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "known field",
|
name: "known field",
|
||||||
field: task.FIELD_ACTION,
|
field: task.FIELD_ACTION,
|
||||||
subject: "subject",
|
subject: action,
|
||||||
exp: "subject",
|
exp: action,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "with project",
|
||||||
|
field: task.FIELD_ACTION,
|
||||||
|
subject: fmt.Sprintf("project - %s", action),
|
||||||
|
exp: action,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "with due and project",
|
||||||
|
field: task.FIELD_ACTION,
|
||||||
|
subject: fmt.Sprintf("due - project - %s", action),
|
||||||
|
exp: action,
|
||||||
},
|
},
|
||||||
} {
|
} {
|
||||||
t.Run(tc.name, func(t *testing.T) {
|
t.Run(tc.name, func(t *testing.T) {
|
||||||
|
|
Loading…
Reference in New Issue