starbash 0.1.9__py3-none-any.whl → 0.1.11__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
starbash/aliases.py ADDED
@@ -0,0 +1,100 @@
1
+ import string
2
+
3
+
4
+ _translator = str.maketrans("", "", string.punctuation + string.whitespace)
5
+
6
+
7
+ def normalize_target_name(name: str | None) -> str | None:
8
+ """Converts a target name to an any filesystem-safe format by removing spaces"""
9
+ if name is None:
10
+ return None
11
+ return name.replace(" ", "").lower()
12
+
13
+
14
+ def pre_normalize(name: str) -> str:
15
+ """Pre-normalize a name by removing all whitespace and punctuation, and converting to lowercase.
16
+
17
+ Args:
18
+ name: The name to pre-normalize.
19
+
20
+ Returns:
21
+ Normalized string with only alphanumeric characters in lowercase.
22
+ """
23
+ # Create translation table that removes all punctuation and whitespace
24
+ return name.lower().translate(_translator)
25
+
26
+
27
+ class UnrecognizedAliasError(ValueError):
28
+ """Exception raised when an unrecognized alias is encountered during normalization."""
29
+
30
+ pass
31
+
32
+
33
+ class Aliases:
34
+ def __init__(self, alias_dict: dict[str, list[str]]):
35
+ """Initialize the Aliases object with a dictionary mapping keys to their alias lists.
36
+
37
+ The alias_dict structure follows the TOML format:
38
+ - Keys are reference names used in code (e.g., "dark", "flat", "bias", "fits", "SiiOiii", "HaOiii")
39
+ - Values are lists of aliases where the FIRST item is the canonical/preferred name
40
+ - The dictionary key may or may not match the canonical name
41
+
42
+ Example from TOML:
43
+ [aliases]
44
+ dark = ["dark", "darks"] # key "dark" -> canonical "dark"
45
+ flat = ["flat", "flats"] # key "flat" -> canonical "flat"
46
+ SiiOiii = ["SiiOiii", "SII-OIII", "S2-O3"] # key "SiiOiii" -> canonical "SiiOiii"
47
+ """
48
+ self.alias_dict = alias_dict
49
+ self.reverse_dict = {}
50
+
51
+ # Build reverse lookup: any alias variant maps to canonical name
52
+ for _key, aliases in alias_dict.items():
53
+ if not aliases:
54
+ continue
55
+ # The first item in the list is ALWAYS the canonical/preferred form
56
+ canonical = aliases[0]
57
+ for alias in aliases:
58
+ # Map each alias (case-insensitive) to the canonical form (first in list)
59
+ # Also remove spaces, hypens and underscores when matching for normalization
60
+ self.reverse_dict[pre_normalize(alias)] = canonical
61
+
62
+ def get(self, name: str) -> list[str] | None:
63
+ """Get the list of aliases for a given key name.
64
+
65
+ Args:
66
+ name: The key name to look up (as used in code/TOML)
67
+
68
+ Returns:
69
+ List of all aliases for this key, or None if not found.
70
+ The first item in the returned list is the canonical form.
71
+ """
72
+ return self.alias_dict.get(name)
73
+
74
+ def normalize(self, name: str) -> str:
75
+ """Normalize a name to its canonical form using aliases.
76
+
77
+ This performs case-insensitive matching to find the canonical form.
78
+ The canonical form is the first item in the alias list from the TOML.
79
+
80
+ Args:
81
+ name: The name to normalize (e.g., "darks", "FLAT", "HA-OIII")
82
+
83
+ Returns:
84
+ The canonical/preferred form (e.g., "dark", "flat", "HaOiii"), or None if not found
85
+
86
+ Examples:
87
+ normalize("darks") -> "dark"
88
+ normalize("FLAT") -> "flat"
89
+ normalize("HA-OIII") -> "HaOiii"
90
+ """
91
+ result = self.reverse_dict.get(pre_normalize(name))
92
+ if not result:
93
+ raise UnrecognizedAliasError(f"'{name}' not found in aliases.")
94
+ return result
95
+
96
+ def equals(self, name1: str, name2: str) -> bool:
97
+ """Check if two names are equivalent based on aliases."""
98
+ norm1 = self.normalize(name1.strip())
99
+ norm2 = self.normalize(name2.strip())
100
+ return norm1 == norm2