Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement timetrace list records command #16

Merged
merged 3 commits into from
May 15, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 22 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,28 @@ timetrace list projects
+---+-------------+
```

### List all records from a date

**Syntax:**

```
timetrace list records <YYYY-MM-DD>
```

**Arguments:**

|Argument|Description|
|-|-|
|`YYYY-MM-DD`|The date of the records to list.|

**Example:**

Display all records created on May 1st 2021:

```
timetrace list records 2021-05-01
```

### Edit a project

**Syntax:**
Expand Down
59 changes: 59 additions & 0 deletions cli/list.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,18 @@ package cli

import (
"strconv"
"time"

"github.com/dominikbraun/timetrace/core"
"github.com/dominikbraun/timetrace/out"

"github.com/spf13/cobra"
)

const (
defaultTimeLayout = "15:04"
)

func listCommand(t *core.Timetrace) *cobra.Command {
list := &cobra.Command{
Use: "list",
Expand All @@ -19,6 +24,7 @@ func listCommand(t *core.Timetrace) *cobra.Command {
}

list.AddCommand(listProjectsCommand(t))
list.AddCommand(listRecordsCommand(t))

return list
}
Expand Down Expand Up @@ -48,3 +54,56 @@ func listProjectsCommand(t *core.Timetrace) *cobra.Command {

return listProjects
}

func listRecordsCommand(t *core.Timetrace) *cobra.Command {
listRecords := &cobra.Command{
Use: "records <YYYY-MM-DD>",
Short: "List all records from a date",
Args: cobra.ExactArgs(1),
Run: func(cmd *cobra.Command, args []string) {
date, err := time.Parse("2006-01-02", args[0])
if err != nil {
out.Err("failed to parse date: %s", err.Error())
return
}

records, err := t.ListRecords(date)
if err != nil {
out.Err("failed to list records: %s", err.Error())
return
}

dateLayout := defaultTimeLayout

if t.Config().Use12Hours {
dateLayout = "03:04PM"
}

rows := make([][]string, len(records))

for i, record := range records {
end := defaultString

if record.End != nil {
end = record.End.Format(dateLayout)
}

billable := defaultBool

if record.IsBillable {
billable = "yes"
}

rows[i] = make([]string, 4)
rows[i][0] = strconv.Itoa(i + 1)
rows[i][1] = record.Start.Format(dateLayout)
rows[i][2] = end
rows[i][3] = billable
}

out.Table([]string{"#", "Start", "End", "Billable"}, rows)
},
}

return listRecords
}
26 changes: 25 additions & 1 deletion core/record.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,30 @@ func (t *Timetrace) LoadRecord(start time.Time) (*Record, error) {
return t.loadRecord(path)
}

// ListRecords loads and returns all records from the given date. If no records
// are found, an empty slice and no error will be returned.
func (t *Timetrace) ListRecords(date time.Time) ([]*Record, error) {
dir := t.fs.RecordDirFromDate(date)
paths, err := t.fs.RecordFilepaths(dir, func(_, _ string) bool {
return true
})
if err != nil {
return nil, err
}

records := make([]*Record, 0)

for _, path := range paths {
record, err := t.loadRecord(path)
if err != nil {
return nil, err
}
records = append(records, record)
}

return records, nil
}

// SaveRecord persists the given record. Returns ErrRecordAlreadyExists if the
// record already exists and saving isn't forced.
func (t *Timetrace) SaveRecord(record Record, force bool) error {
Expand Down Expand Up @@ -74,7 +98,7 @@ func (t *Timetrace) DeleteRecord(record Record) error {
func (t *Timetrace) loadAllRecords(date time.Time) ([]*Record, error) {
dir := t.fs.RecordDirFromDate(date)

recordFilepaths, err := t.fs.RecordFilepaths(dir, func(a, b string) bool {
recordFilepaths, err := t.fs.RecordFilepaths(dir, func(_, _ string) bool {
return true
})
if err != nil {
Expand Down