package metrics import "testing" // real rows from grid's /proc/spl/kstat/zfs/tank/txgs, 2026-10-25 const txgsSample = `81 1 0x01 26 7072 20029594359 13953814329135 txg birth state ndirty nread nwritten reads writes otime qtime wtime stime 15812833 13936408791659 C 0 0 0 0 0 5119980242 2040 58385 309580 15812834 13941528771901 C 0 0 0 0 0 5119948815 8471 65826 112612 15812835 13946648720716 C 885760 0 2293760 0 367 5120100556 1704 56762 271264374 15812836 13951768821272 S 4194304 0 0 0 0 5120000000 1000 50000 0 15812837 13956888821272 O 0 0 0 0 0 0 0 0 0 ` func TestParseTxgs(t *testing.T) { w, top := parseTxgs(txgsSample, 0) if w != 2293760 || top != 15812835 { t.Fatalf("from 0: written %d top %d", w, top) } // only txgs synced since the last look count, and an open or syncing txg never does w, top = parseTxgs(txgsSample, 15812834) if w != 2293760 || top != 15812835 { t.Fatalf("after 15812834: written %d top %d", w, top) } w, top = parseTxgs(txgsSample, 15812835) if w != 0 || top != 15812835 { t.Fatalf("nothing new: written %d top %d", w, top) } } func TestParseBranches(t *testing.T) { p, m := parseBranches("/srv/landing/tank=RW:/tank=NC,50G:/mnt/old=RO\n") if len(p) != 3 || p[0] != "/srv/landing/tank" || p[1] != "/tank" || p[2] != "/mnt/old" { t.Fatalf("paths %q", p) } if m[0] != "RW" || m[1] != "NC" || m[2] != "RO" { t.Fatalf("modes %q", m) } if p, _ := parseBranches("/a:/b"); len(p) != 2 { t.Fatalf("bare paths %q", p) } } func TestMountFor(t *testing.T) { ms := []mountEntry{ {"/dev/sdj2", "/", "ext4"}, {"/dev/nvme0n1p1", "/srv/landing", "ext4"}, {"tank", "/tank", "zfs"}, {"tank/media", "/tank/media", "zfs"}, {"tank-landing", "/srv/tank", "fuse.mergerfs"}, } cases := map[string]string{ "/srv/landing/tank": "/srv/landing", "/tank": "/tank", "/tank/media/x": "/tank/media", "/tankfoo": "/", "/srv/landingx": "/", } for path, want := range cases { if m, ok := mountFor(ms, path); !ok || m.point != want { t.Errorf("%s: got %q want %q", path, m.point, want) } } } func TestUnescapeMount(t *testing.T) { if got := unescapeMount(`/mnt/my\040disk`); got != "/mnt/my disk" { t.Fatalf("got %q", got) } } func TestFoldZFSWrites(t *testing.T) { mk := func(dirty uint64, bps, in, drain float64) Sample { return Sample{ZFSWrite: &ZFSWrites{Dirty: dirty, Limit: 100, Pools: []PoolWrites{{Pool: "tank", WriteBps: bps, Landing: &Landing{Branch: "/srv/landing/tank", InBps: in, DrainBps: drain, Mover: &Mover{State: "moving"}}}}}} } b := []Sample{mk(10, 100, 400, 0), mk(30, 300, 0, 60)} got := fold(b).ZFSWrite if got.Dirty != 20 || got.Pools[0].WriteBps != 200 || got.Pools[0].Landing.InBps != 200 || got.Pools[0].Landing.DrainBps != 30 { t.Fatalf("folded %+v / %+v", got, got.Pools[0].Landing) } // the fold must not write through to the newest sample it copied from if b[1].ZFSWrite.Pools[0].Landing.InBps != 0 || b[1].ZFSWrite.Dirty != 30 { t.Fatalf("fold changed its input") } if got.Pools[0].Landing.Mover.State != "moving" { t.Fatalf("mover state lost") } }