cat / 012
clone

a spreadsheet for the terminal: lotus 1-2-3 looks, google sheets keys and formulas, one go binary

main
012 / e2e / screensources_test.go
screensources_test.go 4.6K
1package e2e23import (4 "path/filepath"5 "strings"6 "testing"78 ghostty "go.mitchellh.com/libghostty"9)1011// Golden screens for linked sources: two million trips on a tab of12// their own, sorted by fare and scrolled halfway down by the scrollbar;13// formulas over them on a sheet in their columns' formats, and one past14// max-cells saying why at 80 columns, the rest on F1; the condition a15// source's column is filtered by; and a source whose file isn't there.16// Each on a light terminal too, the tab and the explanation in the17// high-contrast theme as well.1819func tripsFile(t *testing.T, dir string) { writeTrips(t, dir, tripRows) }2021// sortedTrips links trips.parquet, sorts it by fare Z to A and drags22// the scrollbar halfway down.23func sortedTrips(s *session) {24 s.linkSource("trips.parquet")25 s.waitFor("2,000,000 rows, 5 columns")26 s.keys("<right>", "<right>")27 s.keys("<ctrl+k>", "Sort sheet Z to A", "<enter>")28 s.waitFor("sorted by fare Z to A")29 s.waitFor("92.99")30 bar := int(s.cols) - 131 top, bottom := 7, int(s.rows)-232 s.click(ghostty.MouseButtonLeft, bar, (top+bottom)/2)33 s.waitFor("┃")34 s.eventually("the rows halfway down", func() bool {35 return strings.Contains(s.line(1), " 48") && !strings.Contains(s.screen(), " … ")36 })37}3839// tripFormulas reads the trips from a sheet, max-cells a million in the40// screen's config: counts, sums, a lookup, the last day, a MEDIAN and a41// percentile, each in its column's format, and a STDEV past max-cells;42// column B widened for the fares, the pointer on the median.43func tripFormulas(s *session) {44 s.linkSource("trips.parquet")45 s.keys("<ctrl+pgup>")46 s.waitFor("Sheet1")47 for _, row := range [][2]string{48 {"Trips", "=ROWS(trips)"},49 {"Fares", "=SUM(trips[fare])"},50 {"By card", `=SUMIFS(trips[fare],trips[payment],"card")`},51 {"Vouchers", `=COUNTIF(trips[payment],"voucher")`},52 {"Longest", "=MAX(trips[miles])"},53 {"Last day", "=MAX(trips[day])"},54 {"Trip 1M", "=XLOOKUP(1000000,trips[trip],trips[fare])"},55 {"Median", "=MEDIAN(trips[fare])"},56 {"90th pct", "=PERCENTILE(trips[fare],0.9)"},57 {"Spread", "=STDEV(trips[fare])"},58 } {59 s.keys(row[0], "<tab>", row[1], "<enter>")60 }61 s.keys("<ctrl+home>", "<right>", "<ctrl+k>", "Column width", "<enter>")62 s.waitFor("Column width (1-240)")63 s.keys("14", "<enter>")64 s.waitFor("285,714")65 s.waitFor("95,990,000.00")66 s.eventually("every answer", func() bool { return !strings.Contains(s.screen(), "Loading") })67 for range 7 {68 s.keys("<down>")69 }70 s.waitFor("=MEDIAN(trips[fare])")71}7273// tripWhy is tripFormulas with the pointer on the STDEV past max-cells74// and F1 pressed: its whole explanation in a box beside it.75func tripWhy(s *session) {76 tripCut(s)77 s.keys("<f1>")78 s.waitFor("#VALUE! in B10")79}8081// tripCut is tripFormulas with the pointer on the STDEV past max-cells:82// the context line says the first of why, with F1 for the rest.83func tripCut(s *session) {84 tripFormulas(s)85 s.keys("<down>", "<down>")86 s.waitFor("Raise max-cells to 2,000,000")87 s.waitFor("F1")88}8990var sourceScreens = []screen{91 {name: "source-tab", files: tripsFile, setup: sortedTrips},92 {name: "source-formulas", opts: options{config: "max-cells = 1000000\n"}, files: tripsFile, setup: tripFormulas},93 {name: "source-formulas-cut", opts: options{cols: 80, rows: 24, config: "max-cells = 1000000\n"}, files: tripsFile, setup: tripCut},94 {name: "source-formulas-why", opts: options{config: "max-cells = 1000000\n"}, files: tripsFile, setup: tripWhy},95 {name: "source-filter", files: tripsFile, setup: func(s *session) {96 s.linkSource("trips.parquet")97 s.waitFor("card")98 s.keys("<right>")99 s.keys("<ctrl+k>", "Filter by column", "<enter>")100 s.waitFor("Filter B payment")101 for range 7 {102 s.keys("<down>")103 }104 s.keys("card")105 s.waitFor("Text is exactly")106 s.waitFor("card ")107 }},108 {name: "source-missing", files: func(t *testing.T, dir string) {109 writeText(t, filepath.Join(dir, "rides.012"),110 `{"version": 7, "sheets": [{"name": "Sheet1", "cells": {"A1": "=SUM(trips[fare])"}}, `+111 `{"name": "trips", "cells": {}, "regions": [{"name": "trips", "at": "A1", "path": "trips.parquet", "paged": true}]}]}`)112 }, args: []string{"rides.012"}, setup: func(s *session) {113 s.waitFor("#REF!")114 s.keys("<ctrl+pgdown>")115 s.waitFor("! trips.parquet: the file isn't there")116 }},117}118119func init() {120 for _, sc := range sourceScreens {121 light := sc122 light.name += "-light"123 light.opts.light = true124 screens = append(screens, sc, light)125 if sc.name == "source-tab" || sc.name == "source-formulas-why" {126 hc := sc127 hc.name += "-high-contrast"128 hc.opts.config = sc.opts.config + highContrastConfig129 screens = append(screens, hc)130 }131 }132}