feat(latest): record one poll pass per exit with skip reason and outcome counts
Every way a Lane pass can end now writes exactly one durable row: a skip value naming the exit (paused, refusing, sidecar-down, no-fetcher, due-query, asleep, eligible-count, nothing-eligible, or empty for the loop), five outcome counts from the classification the Series read already makes, and carry-forward of the previous pass's figures exactly when the pass's own gap is zero. Refusal is durable through the poll_lanes row, so a restart does not re-probe a Site inside its backoff. Retention is 14 days. The mid-loop browser-unreachable return writes an empty skip by design: a tenth value is not invented here. (#141)
This commit is contained in:
@@ -1681,6 +1681,24 @@ func TestLanePassOutcomesSumsWindow(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestLaneGatesReadsOneRow(t *testing.T) {
|
||||
s := newTestStore(t)
|
||||
paused, refused, err := s.LaneGates("asura")
|
||||
if err != nil || paused != 0 || refused != 0 {
|
||||
t.Fatalf("LaneGates on a missing state row = (%d, %d, %v), want (0, 0, nil)", paused, refused, err)
|
||||
}
|
||||
if err := s.PauseLane("asura", 2000); err != nil {
|
||||
t.Fatalf("PauseLane: %v", err)
|
||||
}
|
||||
if err := s.SetLaneRefusal("asura", 3000); err != nil {
|
||||
t.Fatalf("SetLaneRefusal: %v", err)
|
||||
}
|
||||
paused, refused, err = s.LaneGates("asura")
|
||||
if err != nil || paused != 2000 || refused != 3000 {
|
||||
t.Fatalf("LaneGates = (%d, %d, %v), want (2000, 3000, nil)", paused, refused, err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestLaneStatePauseResumeAndRefusal(t *testing.T) {
|
||||
s := newTestStore(t)
|
||||
for _, until := range []int64{0, -1} {
|
||||
@@ -1697,8 +1715,9 @@ func TestLaneStatePauseResumeAndRefusal(t *testing.T) {
|
||||
if err := s.RecordLanePass(LanePass{Site: "asura", RanAt: 1}, -1); err != nil {
|
||||
t.Fatalf("RecordLanePass: %v", err)
|
||||
}
|
||||
if got, err := s.LanePausedUntil("asura"); err != nil || got != 2000 {
|
||||
t.Fatalf("LanePausedUntil = %d, %v; want 2000", got, err)
|
||||
pausedUntil, refuseUntil, err := s.LaneGates("asura")
|
||||
if err != nil || pausedUntil != 2000 || refuseUntil != 3000 {
|
||||
t.Fatalf("LaneGates = %d/%d, %v; want 2000/3000", pausedUntil, refuseUntil, err)
|
||||
}
|
||||
paused, err := s.PausedLanes()
|
||||
if err != nil {
|
||||
@@ -1715,8 +1734,8 @@ func TestLaneStatePauseResumeAndRefusal(t *testing.T) {
|
||||
if err != nil || !ok || latest.RefuseUntil != 3000 {
|
||||
t.Fatalf("latest refusal after resume = %+v, ok=%v, err=%v; want 3000 preserved", latest, ok, err)
|
||||
}
|
||||
if got, err := s.LanePausedUntil("asura"); err != nil || got != 0 {
|
||||
t.Fatalf("LanePausedUntil after resume = %d, %v; want 0", got, err)
|
||||
if got, got2, err := s.LaneGates("asura"); err != nil || got != 0 || got2 != 3000 {
|
||||
t.Fatalf("LaneGates after resume = %d/%d, %v; want 0/3000", got, got2, err)
|
||||
}
|
||||
if paused, err := s.PausedLanes(); err != nil || len(paused) != 0 {
|
||||
t.Fatalf("PausedLanes after resume = %+v, %v; want empty", paused, err)
|
||||
|
||||
Reference in New Issue
Block a user