package routing import "testing" // The optimizer returns the same logical field as a number in one place and a // string in another — previouskms came back as 4, actualkms as "5.09", eta as // "20". Binding those to concrete types would have silently zeroed half the // response, so the coercion is worth pinning. func TestAsFloat(t *testing.T) { cases := []struct { name string in interface{} want float64 }{ {"number", float64(4), 4}, {"decimal string", "5.09", 5.09}, {"integer string", "14", 14}, {"zero string the API sends for missing coords", "0.0", 0}, {"nil", nil, 0}, {"unparseable", "n/a", 0}, {"wrong type", true, 0}, } for _, tc := range cases { t.Run(tc.name, func(t *testing.T) { if got := asFloat(tc.in); got != tc.want { t.Fatalf("asFloat(%#v) = %v, want %v", tc.in, got, tc.want) } }) } } func TestAsInt(t *testing.T) { cases := []struct { name string in interface{} want int }{ {"number", float64(3), 3}, {"integer string", "20", 20}, // Atoi would fail on this and yield 0, which as a step number would // silently drop the stop from the sequence. {"decimal string", "20.0", 20}, {"truncates rather than rounds", "20.9", 20}, {"nil", nil, 0}, {"unparseable", "", 0}, } for _, tc := range cases { t.Run(tc.name, func(t *testing.T) { if got := asInt(tc.in); got != tc.want { t.Fatalf("asInt(%#v) = %v, want %v", tc.in, got, tc.want) } }) } } // Coordinates must go out as strings with real precision. Formatting with too // few decimals would collapse neighbouring delivery addresses onto the same // point and make the ordering meaningless. func TestCoordKeepsPrecision(t *testing.T) { if got := coord(11.0045); got != "11.004500" { t.Fatalf("coord(11.0045) = %q", got) } // ~11m apart in Coimbatore; these must not format identically. a, b := coord(11.004500), coord(11.004600) if a == b { t.Fatalf("distinct coordinates formatted identically: %q", a) } }