1package commands
2
3import (
4 "fmt"
5 "strings"
6
7 "github.com/MichaelMure/git-bug/cache"
8 "github.com/MichaelMure/git-bug/identity"
9 "github.com/MichaelMure/git-bug/util/colors"
10 "github.com/MichaelMure/git-bug/util/interrupt"
11 "github.com/spf13/cobra"
12)
13
14var (
15 lsStatusQuery []string
16 lsAuthorQuery []string
17 lsLabelQuery []string
18 lsNoQuery []string
19 lsSortBy string
20 lsSortDirection string
21)
22
23func runLsBug(cmd *cobra.Command, args []string) error {
24 backend, err := cache.NewRepoCache(repo)
25 if err != nil {
26 return err
27 }
28 defer backend.Close()
29 interrupt.RegisterCleaner(backend.Close)
30
31 var query *cache.Query
32 if len(args) >= 1 {
33 query, err = cache.ParseQuery(strings.Join(args, " "))
34
35 if err != nil {
36 return err
37 }
38 } else {
39 query, err = lsQueryFromFlags()
40 if err != nil {
41 return err
42 }
43 }
44
45 allIds := backend.QueryBugs(query)
46
47 for _, id := range allIds {
48 b, err := backend.ResolveBug(id)
49 if err != nil {
50 return err
51 }
52
53 snapshot := b.Snapshot()
54
55 var author identity.Interface
56
57 if len(snapshot.Comments) > 0 {
58 create := snapshot.Comments[0]
59 author = create.Author
60 }
61
62 // truncate + pad if needed
63 titleFmt := fmt.Sprintf("%-50.50s", snapshot.Title)
64 authorFmt := fmt.Sprintf("%-15.15s", author.DisplayName())
65
66 fmt.Printf("%s %s\t%s\t%s\t%s\n",
67 colors.Cyan(b.HumanId()),
68 colors.Yellow(snapshot.Status),
69 titleFmt,
70 colors.Magenta(authorFmt),
71 snapshot.Summary(),
72 )
73 }
74
75 return nil
76}
77
78// Transform the command flags into a query
79func lsQueryFromFlags() (*cache.Query, error) {
80 query := cache.NewQuery()
81
82 for _, status := range lsStatusQuery {
83 f, err := cache.StatusFilter(status)
84 if err != nil {
85 return nil, err
86 }
87 query.Status = append(query.Status, f)
88 }
89
90 for _, author := range lsAuthorQuery {
91 f := cache.AuthorFilter(author)
92 query.Author = append(query.Author, f)
93 }
94
95 for _, label := range lsLabelQuery {
96 f := cache.LabelFilter(label)
97 query.Label = append(query.Label, f)
98 }
99
100 for _, no := range lsNoQuery {
101 switch no {
102 case "label":
103 query.NoFilters = append(query.NoFilters, cache.NoLabelFilter())
104 default:
105 return nil, fmt.Errorf("unknown \"no\" filter %s", no)
106 }
107 }
108
109 switch lsSortBy {
110 case "id":
111 query.OrderBy = cache.OrderById
112 case "creation":
113 query.OrderBy = cache.OrderByCreation
114 case "edit":
115 query.OrderBy = cache.OrderByEdit
116 default:
117 return nil, fmt.Errorf("unknown sort flag %s", lsSortBy)
118 }
119
120 switch lsSortDirection {
121 case "asc":
122 query.OrderDirection = cache.OrderAscending
123 case "desc":
124 query.OrderDirection = cache.OrderDescending
125 default:
126 return nil, fmt.Errorf("unknown sort direction %s", lsSortDirection)
127 }
128
129 return query, nil
130}
131
132var lsCmd = &cobra.Command{
133 Use: "ls [<query>]",
134 Short: "List bugs",
135 Long: `Display a summary of each bugs.
136
137You can pass an additional query to filter and order the list. This query can be expressed either with a simple query language or with flags.`,
138 Example: `List open bugs sorted by last edition with a query:
139git bug ls status:open sort:edit-desc
140
141List closed bugs sorted by creation with flags:
142git bug ls --status closed --by creation
143`,
144 PreRunE: loadRepo,
145 RunE: runLsBug,
146}
147
148func init() {
149 RootCmd.AddCommand(lsCmd)
150
151 lsCmd.Flags().SortFlags = false
152
153 lsCmd.Flags().StringSliceVarP(&lsStatusQuery, "status", "s", nil,
154 "Filter by status. Valid values are [open,closed]")
155 lsCmd.Flags().StringSliceVarP(&lsAuthorQuery, "author", "a", nil,
156 "Filter by author")
157 lsCmd.Flags().StringSliceVarP(&lsLabelQuery, "label", "l", nil,
158 "Filter by label")
159 lsCmd.Flags().StringSliceVarP(&lsNoQuery, "no", "n", nil,
160 "Filter by absence of something. Valid values are [label]")
161 lsCmd.Flags().StringVarP(&lsSortBy, "by", "b", "creation",
162 "Sort the results by a characteristic. Valid values are [id,creation,edit]")
163 lsCmd.Flags().StringVarP(&lsSortDirection, "direction", "d", "asc",
164 "Select the sorting direction. Valid values are [asc,desc]")
165}