mesh-issues keeps each design's milestone in the state milestones (history 5), says milestone-set and milestone-moved, and serves milestones, milestone-set and milestone-move. An issue's milestone is its own link of kind milestone, so at most one milestone per issue is checked inside the issue's own write; kind commit links a fixing commit. The triage links no milestone, pull request or commit. import with milestones=N seeds a design's table once. mesh-knowledge's progress reads issue-tracker.milestones and its table parse is gone. Squashed from four commits so the branch history does not carry a compiled bundle that was committed by mistake (6 MB); the path is now in .gitignore.
54 lines
1.8 KiB
Go
54 lines
1.8 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"
|
|
)
|
|
|
|
// 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"`
|
|
}
|
|
|
|
// 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})
|
|
}
|
|
out := make([]*Design, 0, len(ds))
|
|
for _, d := range ds {
|
|
c := *d
|
|
c.Milestones = by[d.Number]
|
|
out = append(out, &c)
|
|
}
|
|
return out, nil
|
|
}
|