62 lines
2.0 KiB
Go
62 lines
2.0 KiB
Go
package main
|
|
|
|
// A design's milestones are records of the issue tracker (novox/hq ADR 0493 §1, issue 1781): progress asks
|
|
// `issue-tracker.milestones` once per answer, on the bus, for each milestone with its issues, instead of reading the
|
|
// design's table through the records module.
|
|
|
|
import (
|
|
"encoding/json"
|
|
"fmt"
|
|
"time"
|
|
)
|
|
|
|
// MilestonesVerb is the tracker's verb that answers the milestones.
|
|
const MilestonesVerb = "seat:issue-tracker.milestones"
|
|
|
|
// trackerMilestone is a row of `issue-tracker.milestones`.
|
|
type trackerMilestone struct {
|
|
Design int `json:"design"`
|
|
ID string `json:"id"`
|
|
Outcome string `json:"outcome"`
|
|
Status string `json:"status"`
|
|
Reason string `json:"reason"`
|
|
Issues []int `json:"issues"`
|
|
Moved *stamp `json:"moved"`
|
|
}
|
|
|
|
// stamp is who did something and when, as the tracker says it.
|
|
type stamp struct {
|
|
By string `json:"by"`
|
|
At time.Time `json:"at"`
|
|
}
|
|
|
|
// withMilestones is each design with its milestones as the tracker holds them, in their table's order; design 0 asks
|
|
// every design's. The designs are copies: the cache keeps what hq says, never what the tracker said.
|
|
func (k *KB) withMilestones(ds []*Design, design int) ([]*Design, error) {
|
|
body := map[string]any{}
|
|
if design != 0 {
|
|
body["design"] = design
|
|
}
|
|
raw, err := k.Seats(MilestonesVerb, body)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("the issue tracker does not answer its milestones: %v", err)
|
|
}
|
|
var l struct {
|
|
Milestones []trackerMilestone `json:"milestones"`
|
|
}
|
|
if err := json.Unmarshal(raw, &l); err != nil {
|
|
return nil, fmt.Errorf("issue-tracker.milestones answered something else: %v", err)
|
|
}
|
|
by := map[int][]Milestone{}
|
|
for _, m := range l.Milestones {
|
|
by[m.Design] = append(by[m.Design], Milestone{ID: m.ID, Outcome: m.Outcome, Issues: m.Issues, Status: m.Status, Reason: m.Reason, Moved: m.Moved})
|
|
}
|
|
out := make([]*Design, 0, len(ds))
|
|
for _, d := range ds {
|
|
c := *d
|
|
c.Milestones = by[d.Number]
|
|
out = append(out, &c)
|
|
}
|
|
return out, nil
|
|
}
|