123 lines
3.5 KiB
Go
123 lines
3.5 KiB
Go
package dxcc
|
|
|
|
import (
|
|
"strings"
|
|
"testing"
|
|
)
|
|
|
|
const sampleCty = `Sov Mil Order of Malta: 15: 28: EU: 41.90: -12.43: -1.0: 1A:
|
|
1A;
|
|
Monaco: 14: 27: EU: 43.73: -7.40: -1.0: 3A:
|
|
3A;
|
|
France: 14: 27: EU: 46.00: -2.00: -1.0: F:
|
|
F,HW,HX,HY,TH,TM,TO,TP,TQ,TV,TX;
|
|
Germany: 14: 28: EU: 51.00: -10.00: -1.0: DL:
|
|
DA,DB,DC,DD,DE,DF,DG,DH,DI,DJ,DK,DL,DM,DN,DO,DP,DQ,DR;
|
|
United States: 05: 08: NA: 37.53: 91.67: 5.0: K:
|
|
=W1AW(5)[7],K,N,W,AA,AB,AC,AD,AE,AF,AG,AH,AI,AJ,AK;
|
|
`
|
|
|
|
func TestLookup(t *testing.T) {
|
|
db, err := Load(strings.NewReader(sampleCty))
|
|
if err != nil {
|
|
t.Fatalf("load: %v", err)
|
|
}
|
|
cases := []struct {
|
|
call string
|
|
wantEnt string
|
|
}{
|
|
{"F4NIE", "France"},
|
|
{"F4BPO", "France"},
|
|
{"F4BPO/P", "France"},
|
|
{"DL/F4NIE", "Germany"},
|
|
{"DL5XYZ", "Germany"},
|
|
{"K1ABC", "United States"},
|
|
{"N0CALL", "United States"},
|
|
{"3A2MD", "Monaco"},
|
|
{"W1AW", "United States"}, // exact match wins
|
|
}
|
|
for _, c := range cases {
|
|
m, ok := db.Lookup(c.call)
|
|
if !ok {
|
|
t.Errorf("%s: no match", c.call)
|
|
continue
|
|
}
|
|
if m.Entity.Name != c.wantEnt {
|
|
t.Errorf("%s: got %q, want %q", c.call, m.Entity.Name, c.wantEnt)
|
|
}
|
|
}
|
|
|
|
// W1AW exact match has CQ override 5 and ITU override 7.
|
|
m, _ := db.Lookup("W1AW")
|
|
if m.CQZone != 5 || m.ITUZone != 7 {
|
|
t.Errorf("W1AW overrides: got CQ=%d ITU=%d, want 5/7", m.CQZone, m.ITUZone)
|
|
}
|
|
}
|
|
|
|
// cty.dat marks non-DXCC entities (Sicily *IT9, African Italy *IG9) with a
|
|
// leading '*'; the parser must fold those into their parent DXCC entity
|
|
// "Italy" while leaving real DXCC entities — Sardinia (IS0), no '*' — alone.
|
|
func TestCanonicalEntityNames(t *testing.T) {
|
|
const cty = `Italy: 15: 28: EU: 42.82: -12.58: -1.0: I:
|
|
I,IK,IZ;
|
|
African Italy: 33: 37: AF: 35.67: -12.67: -1.0: *IG9:
|
|
IG9,IH9;
|
|
Sardinia: 15: 28: EU: 40.15: -9.27: -1.0: IS0:
|
|
IM0,IS,IW0U,IW0V;
|
|
Sicily: 15: 28: EU: 37.50: -14.00: -1.0: *IT9:
|
|
IT9,IW9;
|
|
`
|
|
db, err := Load(strings.NewReader(cty))
|
|
if err != nil {
|
|
t.Fatalf("load: %v", err)
|
|
}
|
|
cases := map[string]string{
|
|
"IW9EZO": "Italy", // Sicily (*IT9) → Italy
|
|
"IT9CLY": "Italy",
|
|
"IG9A": "Italy", // African Italy (*IG9) → Italy
|
|
"IK0ABC": "Italy",
|
|
"IS0XYZ": "Sardinia", // real DXCC entity — must stay Sardinia
|
|
"IM0ABC": "Sardinia",
|
|
}
|
|
for call, want := range cases {
|
|
m, ok := db.Lookup(call)
|
|
if !ok {
|
|
t.Errorf("%s: no match", call)
|
|
continue
|
|
}
|
|
if m.Entity.Name != want {
|
|
t.Errorf("%s: country = %q, want %q", call, m.Entity.Name, want)
|
|
}
|
|
}
|
|
// African Italy keeps its own zones/continent even though it reports
|
|
// Italy as the entity.
|
|
if m, _ := db.Lookup("IG9A"); m.CQZone != 33 || m.Continent != "AF" {
|
|
t.Errorf("IG9A: got CQ=%d cont=%s, want 33/AF", m.CQZone, m.Continent)
|
|
}
|
|
if EntityDXCC("Sicily") != 248 {
|
|
t.Errorf("EntityDXCC(Sicily) = %d, want 248 (Italy)", EntityDXCC("Sicily"))
|
|
}
|
|
if EntityDXCC("Sardinia") != 225 {
|
|
t.Errorf("EntityDXCC(Sardinia) = %d, want 225", EntityDXCC("Sardinia"))
|
|
}
|
|
}
|
|
|
|
func TestNormalize(t *testing.T) {
|
|
cases := map[string]string{
|
|
"F4BPO": "F4BPO",
|
|
"f4bpo": "F4BPO",
|
|
" F4BPO ": "F4BPO",
|
|
"F4BPO/P": "F4BPO",
|
|
"F4BPO/MM": "F4BPO",
|
|
"F4BPO/5": "F4BPO",
|
|
"DL/F4BPO": "DL",
|
|
"F4BPO/W6": "W6",
|
|
"VK9/F4BPO": "VK9",
|
|
}
|
|
for in, want := range cases {
|
|
if got := normalizeCallsign(in); got != want {
|
|
t.Errorf("normalize(%q) = %q, want %q", in, got, want)
|
|
}
|
|
}
|
|
}
|