mirror of
https://git.ianrenton.com/ian/spothole.git
synced 2026-09-20 22:37:44 +00:00
Refactor activity names to use an enum instead of a string to avoid typos #147
This commit is contained in:
@@ -3,9 +3,9 @@ import re
|
||||
|
||||
from pyhamtools.locator import latlong_to_locator, locator_to_latlong
|
||||
|
||||
from core.constants import ACTIVITIES
|
||||
from core.activity_utils import get_activity_by_name
|
||||
from core.data_store import DATA_STORE
|
||||
from core.enums import ActivityRefType
|
||||
from core.enums import ActivityName, ActivityRefType
|
||||
from core.geo_utils import wab_wai_square_to_lat_lon
|
||||
from data.activity_ref import ActivityRef
|
||||
|
||||
@@ -30,10 +30,10 @@ def get_activity_ref_info(activity_name, ref_id):
|
||||
activity_ref = ActivityRef(sig=activity_name, id=ref_id)
|
||||
|
||||
# We can always get the reference type and the icon from the activity itself
|
||||
for activity in ACTIVITIES:
|
||||
if activity.name.upper() == activity_name.upper():
|
||||
activity_ref.ref_type = activity.ref_type
|
||||
activity_ref.icon = activity.icon
|
||||
activity = get_activity_by_name(activity_name)
|
||||
if activity:
|
||||
activity_ref.ref_type = activity.ref_type
|
||||
activity_ref.icon = activity.icon
|
||||
|
||||
try:
|
||||
### FUDGES ###
|
||||
@@ -41,7 +41,7 @@ def get_activity_ref_info(activity_name, ref_id):
|
||||
# DME fudge. Our database has leading zeros padding to 5 digits which is the expected format, but not all
|
||||
# activators add leading zeros. We also need to normalise "DME 01234" to "DME-01234" to match what's in our
|
||||
# database.
|
||||
if activity_name.upper() == "DME":
|
||||
if activity_name.upper() == ActivityName.DME:
|
||||
match = re.match(r"DME[\- ](\d{3,5})", ref_id, re.IGNORECASE)
|
||||
if match:
|
||||
number = match.group(1)
|
||||
@@ -49,21 +49,21 @@ def get_activity_ref_info(activity_name, ref_id):
|
||||
|
||||
# DTMBA spotters sometimes include spaces and dashes, our regex allows them but they must be removed here so we
|
||||
# can look up against the official list which doesn't have them
|
||||
if activity_name.upper() == "DTMBA":
|
||||
if activity_name.upper() == ActivityName.DTMBA:
|
||||
ref_id = ref_id.replace("-", "").replace(" ", "")
|
||||
|
||||
### NO DATA ACTIVITIES ###
|
||||
#
|
||||
# If the activity is HEMA or BIWOTA, we have no way to either generate useful data or look it up on a
|
||||
# reference list, so just skip the lookup here.
|
||||
if activity_name.upper() == "HEMA" or activity_name.upper() == "BIWOTA":
|
||||
if activity_name.upper() == ActivityName.HEMA or activity_name.upper() == ActivityName.BIWOTA:
|
||||
return activity_ref
|
||||
|
||||
### PROGRAMMATIC DATA GENERATION INSTEAD OF LOOKUPS ###
|
||||
#
|
||||
# If the activity is Tiles, WAB, WAI or BOTA (Beaches), we don't have anything to look up from the data
|
||||
# store, we can calculate all the information we are going to get directly.
|
||||
if activity_name.upper() == "TILES":
|
||||
if activity_name.upper() == ActivityName.TILES.upper():
|
||||
# Tiles on the Air just uses Maidenhead 6-digit squares, so ID, Name and Grid are all the same
|
||||
if not activity_ref.name:
|
||||
activity_ref.name = activity_ref.id
|
||||
@@ -75,7 +75,7 @@ def get_activity_ref_info(activity_name, ref_id):
|
||||
activity_ref.longitude = ll[1]
|
||||
return activity_ref
|
||||
|
||||
elif activity_name.upper() == "WAB" or activity_name.upper() == "WAI":
|
||||
elif activity_name.upper() == ActivityName.WAB or activity_name.upper() == ActivityName.WAI:
|
||||
ll = wab_wai_square_to_lat_lon(ref_id)
|
||||
if ll:
|
||||
activity_ref.name = ref_id
|
||||
@@ -87,7 +87,7 @@ def get_activity_ref_info(activity_name, ref_id):
|
||||
logger.warning("Invalid lat/lon received for WAB/WAI reference")
|
||||
return activity_ref
|
||||
|
||||
elif activity_name.upper() == "BOTA":
|
||||
elif activity_name.upper() == ActivityName.BOTA:
|
||||
# For BOTA all we can ever generate is the URL, there is no data file or lookup for lat/longs
|
||||
if not activity_ref.name:
|
||||
activity_ref.name = activity_ref.id
|
||||
@@ -97,11 +97,11 @@ def get_activity_ref_info(activity_name, ref_id):
|
||||
)
|
||||
return activity_ref
|
||||
|
||||
elif activity_name.upper() == "GMA Islands":
|
||||
elif activity_name.upper() == ActivityName.GMA_ISLANDS.upper():
|
||||
# GMA Islands is a bit of a mess of GMA and IOTA references. Try looking them both up and see what returns
|
||||
# the best result.
|
||||
iota_lookup = get_activity_ref_info("IOTA", ref_id)
|
||||
gma_lookup = get_activity_ref_info("GMA", ref_id)
|
||||
iota_lookup = get_activity_ref_info(ActivityName.IOTA, ref_id)
|
||||
gma_lookup = get_activity_ref_info(ActivityName.GMA, ref_id)
|
||||
for key, value in iota_lookup.__dict__.items():
|
||||
if value is not None and activity_ref.__dict__.get(key) is None:
|
||||
activity_ref.__dict__[key] = value
|
||||
|
||||
+20
-12
@@ -1,23 +1,31 @@
|
||||
from core.constants import ACTIVITIES
|
||||
from data.activities import ACTIVITIES
|
||||
|
||||
|
||||
def get_activity_by_name(name):
|
||||
"""Utility function to resolve an arbitrary, case-insensitive activity name string (e.g. from a spot comment, a
|
||||
provider, or an API request) to the matching known Activity. Returns None if no match is found."""
|
||||
|
||||
if not name:
|
||||
return None
|
||||
for activity_name, activity in ACTIVITIES.items():
|
||||
if activity_name.upper() == name.upper():
|
||||
return activity
|
||||
return None
|
||||
|
||||
|
||||
def get_ref_regex_for_activity(activity):
|
||||
"""Utility function to get the regex string for an activity reference for a named activity. If no match is
|
||||
found, None will be returned."""
|
||||
|
||||
for a in ACTIVITIES:
|
||||
if a.name.upper() == activity.upper():
|
||||
return a.ref_regex
|
||||
return None
|
||||
found = get_activity_by_name(activity)
|
||||
return found.ref_regex if found else None
|
||||
|
||||
|
||||
def get_icon_for_activity(activity):
|
||||
"""Utility function to get the icon for a named activity. If no match is found, None will be returned."""
|
||||
|
||||
for a in ACTIVITIES:
|
||||
if a.name.upper() == activity.upper():
|
||||
return a.icon
|
||||
return None
|
||||
found = get_activity_by_name(activity)
|
||||
return found.icon if found else None
|
||||
|
||||
|
||||
def get_activity_name_from_comment_name(activity):
|
||||
@@ -25,11 +33,11 @@ def get_activity_name_from_comment_name(activity):
|
||||
but there are some cases (e.g. is "TOTA" Towers, Tiles or Toilets?) where we need to transform one to the
|
||||
other."""
|
||||
|
||||
for a in ACTIVITIES:
|
||||
for activity_name, a in ACTIVITIES.items():
|
||||
if any(n.upper() == activity.upper() for n in a.comment_names):
|
||||
return a.name
|
||||
return activity_name
|
||||
return None
|
||||
|
||||
|
||||
# Regex matching any activity's "comment name", i.e. how it may be referred to in spot comments
|
||||
ANY_ACTIVITY_REGEX = rf"({'|'.join(n for a in ACTIVITIES for n in a.comment_names)})"
|
||||
ANY_ACTIVITY_REGEX = rf"({'|'.join(n for a in ACTIVITIES.values() for n in a.comment_names)})"
|
||||
|
||||
@@ -1,6 +1,4 @@
|
||||
from core.config import SERVER_OWNER_CALLSIGN
|
||||
from core.enums import ActivityRefType, ActivityType
|
||||
from data.activity import Activity
|
||||
from data.band import Band
|
||||
|
||||
# General software
|
||||
@@ -10,442 +8,6 @@ SOFTWARE_VERSION = "2.2-pre"
|
||||
HTTP_HEADERS = {"User-Agent": f"Spothole v{SOFTWARE_VERSION} (operated by {SERVER_OWNER_CALLSIGN})"}
|
||||
HAMQTH_PRG = f"Spothole v{SOFTWARE_VERSION} operated by {SERVER_OWNER_CALLSIGN}".replace(" ", "_")
|
||||
|
||||
# Activities
|
||||
ACTIVITIES = [
|
||||
Activity(
|
||||
name="Contest",
|
||||
comment_names=["CONTEST"],
|
||||
description="Contest",
|
||||
sig_type=ActivityType.TRADITIONAL,
|
||||
icon="fa-trophy",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="DXpedition",
|
||||
comment_names=[],
|
||||
description="Radio expedition to a remote location",
|
||||
sig_type=ActivityType.TRADITIONAL,
|
||||
icon="fa-book-atlas",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="Satellite",
|
||||
comment_names=[],
|
||||
description="Amateur Radio Satellite",
|
||||
sig_type=ActivityType.TRADITIONAL,
|
||||
icon="fa-satellite",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="EME",
|
||||
comment_names=[],
|
||||
description="Earth-Moon-Earth (Moonbounce)",
|
||||
sig_type=ActivityType.TRADITIONAL,
|
||||
icon="fa-moon",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="/AM",
|
||||
comment_names=[],
|
||||
description="Aeronautical Mobile",
|
||||
sig_type=ActivityType.TRADITIONAL,
|
||||
icon="fa-plane",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="/MM",
|
||||
comment_names=[],
|
||||
description="Maritime Mobile",
|
||||
sig_type=ActivityType.TRADITIONAL,
|
||||
icon="fa-sailboat",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="QRP",
|
||||
comment_names=["QRP"],
|
||||
description="Low power",
|
||||
sig_type=ActivityType.TRADITIONAL,
|
||||
icon="fa-volume-low",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="POTA",
|
||||
comment_names=["POTA"],
|
||||
description="Parks on the Air",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.PARK,
|
||||
ref_regex=r"[A-Z]{2}\-\d{4,5}|K\-TEST",
|
||||
icon="fa-tree",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="SOTA",
|
||||
comment_names=["SOTA"],
|
||||
description="Summits on the Air",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.SUMMIT,
|
||||
ref_regex=r"[A-Z0-9]{1,3}\/[A-Z]{2}\-\d{3}",
|
||||
icon="fa-mountain-sun",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="WWFF",
|
||||
comment_names=["WWFF"],
|
||||
description="World Wide Flora & Fauna",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.PARK,
|
||||
ref_regex=r"[A-Z0-9]{1,3}FF\-\d{4}",
|
||||
icon="fa-seedling",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="GMA",
|
||||
comment_names=["GMA"],
|
||||
description="Global Mountain Activity",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.SUMMIT,
|
||||
ref_regex=r"[A-Z0-9]{1,3}\/[A-Z]{2}\-\d{3}",
|
||||
icon="fa-person-hiking",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="WWBOTA",
|
||||
comment_names=["WWBOTA", "BOTA"],
|
||||
description="Worldwide Bunkers on the Air",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.BUNKER,
|
||||
ref_regex=r"B\/[A-Z0-9]{1,3}\-\d{3,4}",
|
||||
icon="fa-radiation",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="HEMA",
|
||||
comment_names=["HEMA"],
|
||||
description="HuMPs Excluding Marilyns Award",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.SUMMIT,
|
||||
ref_regex=r"[A-Z0-9]{1,3}\/[A-Z]{3}\-\d{3}",
|
||||
icon="fa-mound",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="IOTA",
|
||||
comment_names=["IOTA"],
|
||||
description="Islands on the Air",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.ISLAND,
|
||||
ref_regex=r"[A-Z]{2}\-\d{3}",
|
||||
icon="fa-book-atlas",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="GMA Islands",
|
||||
comment_names=[],
|
||||
description="Global Mountain Activity - Islands",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.ISLAND,
|
||||
ref_regex=r"(([A-Z]{2}\-\d{3})|([A-Z0-9]{1,3}\/[A-Z]{2}\-\d{3}))",
|
||||
icon="fa-person-hiking",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="ARLHS",
|
||||
comment_names=["ARLHS"],
|
||||
description="Amateur Radio Lighthouse Society",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.LIGHTHOUSE,
|
||||
ref_regex=r"[A-Z]{3}[\- ]\d{3,4}",
|
||||
icon="fa-house-flood-water",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="ILLW",
|
||||
comment_names=["ILLW"],
|
||||
description="International Lighthouse & Lightship Weekend",
|
||||
sig_type=ActivityType.EVENT,
|
||||
ref_type=ActivityRefType.LIGHTHOUSE,
|
||||
ref_regex=r"[A-Z]{2}\d{4}",
|
||||
icon="fa-house-flood-water",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="MOTA",
|
||||
comment_names=["MOTA"],
|
||||
description="Mills on the Air",
|
||||
sig_type=ActivityType.EVENT,
|
||||
ref_type=ActivityRefType.MILL,
|
||||
ref_regex=r"X\d{4,6}",
|
||||
icon="fa-fan",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="SIOTA",
|
||||
comment_names=["SIOTA"],
|
||||
description="Silos on the Air",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.SILO,
|
||||
ref_regex=r"[A-Z]{2}\-[A-Z]{3}\d",
|
||||
icon="fa-wheat-awn",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="WCA",
|
||||
comment_names=["WCA"],
|
||||
description="World Castles Award",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.CASTLE,
|
||||
ref_regex=r"[A-Z0-9]{1,3}\-\d{5}",
|
||||
icon="fa-chess-rook",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="ZLOTA",
|
||||
comment_names=["ZLOTA"],
|
||||
description="New Zealand on the Air",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=None,
|
||||
ref_regex=r"ZL[A-Z]/[A-Z]{2}\-\d{3,4}",
|
||||
icon="fa-kiwi-bird",
|
||||
region_flag="🇳🇿",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="WOTA",
|
||||
comment_names=["WOTA"],
|
||||
description="Wainwrights on the Air",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.SUMMIT,
|
||||
ref_regex=r"[A-Z]{3}-[0-9]{2}",
|
||||
icon="fa-w",
|
||||
region_flag="🇬🇧",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="BOTA",
|
||||
comment_names=[],
|
||||
description="Beaches on the Air",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.BEACH,
|
||||
icon="fa-umbrella-beach",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="KRMNPA",
|
||||
comment_names=["KRMNPA"],
|
||||
description="Keith Roget Memorial National Parks Award",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.PARK,
|
||||
ref_regex=r"VKFF\-\d{4}",
|
||||
icon="fa-earth-oceania",
|
||||
region_flag="🇦🇺",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="SANPCPA",
|
||||
comment_names=["SANPCPA"],
|
||||
description="South Australian National Parks and Conservation Parks Award",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.PARK,
|
||||
ref_regex=r"VKFF\-\d{4}",
|
||||
icon="fa-earth-oceania",
|
||||
region_flag="🇦🇺",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="LLOTA",
|
||||
comment_names=["LLOTA"],
|
||||
description="Lagos y Lagunas on the Air",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.LAKE,
|
||||
ref_regex=r"LL[A-Z]{2}\-\d{4}",
|
||||
icon="fa-water",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="Towers",
|
||||
comment_names=["TOTA"],
|
||||
description="Towers on the Air",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.TOWER,
|
||||
ref_regex=r"[A-Z]{2,3}R\-\d{4}",
|
||||
icon="fa-tower-observation",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="Tiles",
|
||||
comment_names=[],
|
||||
description="Tiles on the Air",
|
||||
sig_type=ActivityType.ADVENTURE,
|
||||
ref_type=ActivityRefType.GRID,
|
||||
ref_regex=r"[A-Za-z]{2}[0-9]{2}[A-Za-z]{2}",
|
||||
icon="fa-square",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="RaDAR Rally",
|
||||
comment_names=["RaDAR"],
|
||||
description="RaDAR Rally",
|
||||
sig_type=ActivityType.EVENT,
|
||||
icon="fa-headset",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="WAB",
|
||||
comment_names=["WAB"],
|
||||
description="Worked All Britain",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.GRID,
|
||||
ref_regex=r"[A-Z]{1,2}[0-9]{2}",
|
||||
icon="fa-table-cells-large",
|
||||
region_flag="🇬🇧",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="WAI",
|
||||
comment_names=["WAI"],
|
||||
description="Worked All Ireland",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.GRID,
|
||||
ref_regex=r"[A-Z][0-9]{2}",
|
||||
icon="fa-table-cells-large",
|
||||
region_flag="🇮🇪",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="DMF",
|
||||
comment_names=["DMF"],
|
||||
description="Diplôme des Moulins de France",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.MILL,
|
||||
icon="fa-fan",
|
||||
region_flag="🇫🇷",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="DME",
|
||||
comment_names=["DME"],
|
||||
description="Diploma Municipios de España",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.TOWN,
|
||||
ref_regex=r"DME[\- ]\d{3,5}",
|
||||
icon="fa-building",
|
||||
region_flag="🇪🇸",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="FEA",
|
||||
comment_names=["FEA"],
|
||||
description="Diploma Faros de España",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.LIGHTHOUSE,
|
||||
# FEA references are technically [DE]\-\d{4}(\.\d)? but spotters always seem to miss out the D- or E-
|
||||
# prefix and just use FEA-1234 or FEA 1234, so allow for that. The FEA activity ref data provider adds both
|
||||
# forms to the database.
|
||||
ref_regex=r"([DE]|FEA)[\- ]\d{4}(\.\d)?",
|
||||
icon="fa-house-flood-water",
|
||||
region_flag="🇪🇸",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="DMUE",
|
||||
comment_names=["DMUE"],
|
||||
description="Diploma Museos de España",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.BUILDING,
|
||||
ref_regex=r"MUE[A-Z]{2}-\d{3}",
|
||||
icon="fa-landmark",
|
||||
region_flag="🇪🇸",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="DMVE",
|
||||
comment_names=["DMVE"],
|
||||
description="Diploma Monumentos y Vestigios de España",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.BUILDING,
|
||||
ref_regex=r"MV[A-Z]{1,2}-\d{4}",
|
||||
icon="fa-monument",
|
||||
region_flag="🇪🇸",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="DCE",
|
||||
comment_names=["DCE"],
|
||||
description="Diploma Castillos de España",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.CASTLE,
|
||||
ref_regex=r"C[A-Z]{1,2}-\d{3}",
|
||||
icon="fa-chess-rook",
|
||||
region_flag="🇪🇸",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="DEFE",
|
||||
comment_names=["DEFE"],
|
||||
description="Diploma Estaciones de Ferrocarril de España",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.BUILDING,
|
||||
ref_regex=r"EF[A-Z]{1,2}-\d{3}",
|
||||
icon="fa-train",
|
||||
region_flag="🇪🇸",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="DTMBA",
|
||||
comment_names=["DTMBA"],
|
||||
description="Diploma Teatri Musei e Belle Arti",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.BUILDING,
|
||||
ref_regex=r"I-?[0-9]{3,4}\s?[A-Z]{2}",
|
||||
icon="fa-landmark",
|
||||
region_flag="🇮🇹",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
Activity(
|
||||
name="BIWOTA",
|
||||
comment_names=["BIWOTA"],
|
||||
description="British Inland Waterways on the Air",
|
||||
sig_type=ActivityType.EVENT,
|
||||
ref_type=ActivityRefType.WATERWAY,
|
||||
icon="fa-ship",
|
||||
region_flag="🇬🇧",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="COTA",
|
||||
comment_names=["COTA"],
|
||||
description="Castles on the Air",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.CASTLE,
|
||||
ref_regex=r"[A-Z]{3}\-[0-9]{3,5}",
|
||||
icon="fa-chess-rook",
|
||||
region_flag="🇩🇪",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="PGA",
|
||||
comment_names=["PGA"],
|
||||
description="Polish Gmina Award",
|
||||
sig_type=ActivityType.REGIONAL,
|
||||
ref_type=ActivityRefType.REGION,
|
||||
ref_regex=r"[A-Z]{2}[0-9]{2}",
|
||||
icon="fa-g",
|
||||
region_flag="🇵🇱",
|
||||
refs_globally_unique=False,
|
||||
),
|
||||
Activity(
|
||||
name="Toilets",
|
||||
comment_names=[],
|
||||
description="Toilets on the Air",
|
||||
sig_type=ActivityType.EVENT,
|
||||
ref_type=ActivityRefType.TOILET,
|
||||
ref_regex=r"T\-[0-9]{2}",
|
||||
icon="fa-toilet",
|
||||
region_flag="🏴☠️",
|
||||
refs_globally_unique=True,
|
||||
),
|
||||
]
|
||||
|
||||
# Band definitions
|
||||
BANDS = [
|
||||
Band(name="2200m", start_freq=135700, end_freq=137800),
|
||||
|
||||
@@ -90,6 +90,60 @@ class LocationSourceForCallsign(str, Enum):
|
||||
DXCC = "DXCC"
|
||||
|
||||
|
||||
# Definitions of every activity Spothole knows about, keyed by the ActivityName enum. An enum is used for the
|
||||
# names to avoid typos when using literal strings like "POTA" all over the place.
|
||||
class ActivityName(str, Enum):
|
||||
"""Canonical name of every activity. Spothole uses these rather than literals like "POTA" around the code
|
||||
to ensure I don't accidentally introduce typos."""
|
||||
|
||||
CONTEST = "Contest"
|
||||
DXPEDITION = "DXpedition"
|
||||
SATELLITE = "Satellite"
|
||||
EME = "EME"
|
||||
AERONAUTICAL_MOBILE = "/AM"
|
||||
MARITIME_MOBILE = "/MM"
|
||||
QRP = "QRP"
|
||||
POTA = "POTA"
|
||||
SOTA = "SOTA"
|
||||
WWFF = "WWFF"
|
||||
GMA = "GMA"
|
||||
WWBOTA = "WWBOTA"
|
||||
HEMA = "HEMA"
|
||||
IOTA = "IOTA"
|
||||
GMA_ISLANDS = "GMA Islands"
|
||||
ARLHS = "ARLHS"
|
||||
ILLW = "ILLW"
|
||||
MOTA = "MOTA"
|
||||
SIOTA = "SIOTA"
|
||||
WCA = "WCA"
|
||||
ZLOTA = "ZLOTA"
|
||||
WOTA = "WOTA"
|
||||
BOTA = "BOTA"
|
||||
KRMNPA = "KRMNPA"
|
||||
SANPCPA = "SANPCPA"
|
||||
LLOTA = "LLOTA"
|
||||
TOWERS = "Towers"
|
||||
TILES = "Tiles"
|
||||
RADAR_RALLY = "RaDAR Rally"
|
||||
WAB = "WAB"
|
||||
WAI = "WAI"
|
||||
DMF = "DMF"
|
||||
DME = "DME"
|
||||
FEA = "FEA"
|
||||
DMUE = "DMUE"
|
||||
DMVE = "DMVE"
|
||||
DCE = "DCE"
|
||||
DEFE = "DEFE"
|
||||
DTMBA = "DTMBA"
|
||||
BIWOTA = "BIWOTA"
|
||||
COTA = "COTA"
|
||||
PGA = "PGA"
|
||||
TOILETS = "Toilets"
|
||||
|
||||
def __str__(self):
|
||||
return str(self.value)
|
||||
|
||||
|
||||
class ActivityRefType(str, Enum):
|
||||
"""Type of an activity reference."""
|
||||
|
||||
|
||||
Reference in New Issue
Block a user