├── .github └── workflows │ ├── pypi-publish.yml │ └── snyk-security.yml ├── .gitignore ├── CoT ├── __init__.py ├── convert │ └── ais.py ├── models │ ├── __init__.py │ └── core.py ├── types.py ├── utils.py └── xml │ └── __init__.py ├── LICENSE ├── MITRE-MP090284.pdf ├── README.md ├── examples ├── admin.p12 ├── pyais-to-tak-with-cert.py ├── pycot-aisstream.py ├── pycot-from-file.py ├── pycot-from-json-igs.py ├── pycot-from-pcap.py ├── pycot-from-sat-info.py ├── pycot-from-scapy.py ├── pycot-from-string.py ├── pycot-to-prometheus.py ├── pycot-to-tak-with-cert.py ├── pycot-to-tak.py └── pycot-with-movingpandas.ipynb ├── extensions └── mitre │ ├── __init__.py │ ├── setup.py │ └── xsd │ ├── CoT Contact Schema (PUBLIC RELEASE).xsd │ ├── CoT Flow-Tags Schema (PUBLIC RELEASE).xsd │ ├── CoT Link Schema (PUBLIC RELEASE).xsd │ ├── CoT Remarks Schema (PUBLIC RELEASE).xsd │ ├── CoT Request Schema (PUBLIC RELEASE).xsd │ ├── CoT Spatial Schema (PUBLIC RELEASE).xsd │ ├── CoT Track Schema (PUBLIC RELEASE).xsd │ └── CoT Uid Schema (PUBLIC RELEASE).xsd ├── requirements.txt ├── setup.py └── tests ├── geolife_small.gpkg ├── messages ├── MITRE-Message.xml └── README.md ├── test_cot_xml_interopability.py └── test_messages.py /.github/workflows/pypi-publish.yml: -------------------------------------------------------------------------------- 1 | name: Upload Python Package to PyPI when a Release is Created 2 | 3 | on: 4 | release: 5 | types: [created] 6 | 7 | jobs: 8 | pypi-publish: 9 | name: Publish release to PyPI 10 | runs-on: ubuntu-latest 11 | environment: 12 | name: pypi 13 | url: https://pypi.org/p/pycot 14 | permissions: 15 | id-token: write 16 | steps: 17 | - uses: actions/checkout@v4 18 | - name: Set up Python 19 | uses: actions/setup-python@v4 20 | with: 21 | python-version: "3.x" 22 | - name: Install dependencies 23 | run: | 24 | python -m pip install --upgrade pip 25 | pip install setuptools wheel 26 | - name: Build package 27 | run: | 28 | python setup.py sdist bdist_wheel # Could also be python -m build 29 | - name: Publish package distributions to PyPI 30 | uses: pypa/gh-action-pypi-publish@release/v1 -------------------------------------------------------------------------------- /.github/workflows/snyk-security.yml: -------------------------------------------------------------------------------- 1 | name: Snyk Security 2 | 3 | on: 4 | push: 5 | branches: ["main" ] 6 | pull_request: 7 | branches: ["main"] 8 | 9 | permissions: 10 | contents: read # for actions/checkout to fetch code 11 | security-events: write # for github/codeql-action/upload-sarif to upload SARIF results 12 | actions: read # only required for a private repository by github/codeql-action/upload-sarif to get the Action run status 13 | 14 | jobs: 15 | security: 16 | runs-on: ubuntu-latest 17 | steps: 18 | - uses: actions/checkout@master 19 | - name: Run Snyk to check for vulnerabilities 20 | uses: snyk/actions/python@master 21 | continue-on-error: true # To make sure that SARIF upload gets called 22 | env: 23 | SNYK_TOKEN: ${{ secrets.SNYK_TOKEN }} 24 | with: 25 | args: --sarif-file-output=snyk.sarif 26 | - name: Upload result to GitHub Code Scanning 27 | uses: github/codeql-action/upload-sarif@v3 28 | with: 29 | sarif_file: snyk.sarif 30 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # hiding MIL-STD-6090 schema 2 | /CoT/mil 3 | 4 | __pycache__ 5 | env/ 6 | build/ 7 | *.egg-info/ 8 | .pytest_cache/ 9 | 10 | lib 11 | bin 12 | activate 13 | 14 | pyvenv.cfg -------------------------------------------------------------------------------- /CoT/__init__.py: -------------------------------------------------------------------------------- 1 | from CoT import xml 2 | from CoT.models import Event, Point 3 | 4 | __extensions_installed__ = {"milstd": True, "mitre": True} 5 | 6 | try: 7 | import pycot_ext_mitre as mitre 8 | except ImportError: 9 | 10 | # Handle the case where MITRE-specific dependencies aren't installed 11 | __extensions_installed__["mitre"] = False 12 | 13 | 14 | try: 15 | import pycot_ext_milstd as milstd 16 | except ImportError: 17 | # Handle the case where MILSTD-specific dependencies aren't installed 18 | __extensions_installed__["milstd"] = False 19 | -------------------------------------------------------------------------------- /CoT/convert/ais.py: -------------------------------------------------------------------------------- 1 | import datetime 2 | from CoT.models.core import Event, Point 3 | 4 | def FromAIS(data: bytes) -> Event: 5 | try: 6 | import pyais 7 | _pyais_available = True 8 | except ImportError: 9 | _pyais_available = False 10 | 11 | if not _pyais_available: 12 | raise ImportError("The 'pyais' library is required for FromAIS but is not installed. Install it with: pip install pycot[ais]") 13 | 14 | ais_decoded = pyais.decode(data) 15 | ais_dict = ais_decoded.asdict() 16 | 17 | now = datetime.datetime.now(datetime.timezone.utc) 18 | stale = now + datetime.timedelta(minutes=2) 19 | 20 | return Event( 21 | version="2.0", 22 | type="a-u-S-X-M", 23 | access="Undefined", 24 | uid="MMSI-{}".format(ais_dict['MetaData']['MMSI']), 25 | time=now, 26 | start=now, 27 | stale=stale, 28 | how="m-f", 29 | qos="2-i-c", 30 | point=Point(lat=float(ais_dict["Message"]["PositionReport"]["Latitude"]), lon=float(ais_dict["Message"]["PositionReport"]["Longitude"]), hae=9999999, ce=9999999, le=9999999), 31 | detail={"contact": {"callsign": ais_dict["MetaData"]["ShipName"]}}, 32 | ) 33 | 34 | def FromGeoJSON(dict) -> Event: 35 | pass -------------------------------------------------------------------------------- /CoT/models/__init__.py: -------------------------------------------------------------------------------- 1 | from CoT.models.core import * 2 | -------------------------------------------------------------------------------- /CoT/models/core.py: -------------------------------------------------------------------------------- 1 | import datetime 2 | import re 3 | from datetime import datetime 4 | from typing import Optional, Any 5 | 6 | from pydantic import ConfigDict, Field, GetCoreSchemaHandler, computed_field, constr 7 | from pydantic_core import CoreSchema, core_schema 8 | from CoT.utils import CustomModel 9 | from CoT.xml import unparse 10 | from CoT.types import CoTTypes, CoTReservations, CoTHow 11 | from pydantic import BaseModel 12 | KeywordsPattern = constr(pattern=r"^[\w\- ]+(,[\w\- ]+)*$") 13 | 14 | class Remarks(BaseModel): 15 | text: str 16 | 17 | # MITRE Definition does not have addition subschema 18 | class Detail(CustomModel): 19 | model_config = ConfigDict(extras=True, populate_by_name=True) 20 | remarks: Remarks = Optional[Remarks] 21 | 22 | class Point(CustomModel): 23 | lat: float = Field(ge=-90, le=90) 24 | lon: float = Field(ge=-180, le=180) 25 | hae: float 26 | ce: float 27 | le: float 28 | 29 | 30 | 31 | class Types(str): 32 | value: str 33 | 34 | @computed_field 35 | @property 36 | def description(self) -> str: 37 | searchType = self.split("-") 38 | searchType[1] = "." 39 | searchType = "-".join(searchType) 40 | 41 | if searchType not in CoTTypes: 42 | return "Unknown" 43 | 44 | return CoTTypes[searchType].get("desc") 45 | 46 | @computed_field 47 | @property 48 | def full(self) -> str: 49 | searchType = self.split("-") 50 | searchType[1] = "." 51 | searchType = "-".join(searchType) 52 | 53 | if searchType not in CoTTypes: 54 | return "Unknown" 55 | 56 | return CoTTypes[searchType].get("full") 57 | 58 | @computed_field 59 | @property 60 | def reservation(self) -> str: 61 | return CoTReservations[str(self).split("-")[1]] 62 | 63 | @classmethod 64 | def __get_pydantic_core_schema__( 65 | cls, source_type: Any, handler: GetCoreSchemaHandler 66 | ) -> CoreSchema: 67 | return core_schema.no_info_after_validator_function(cls, handler(str)) 68 | 69 | 70 | class How(str): 71 | value: str 72 | 73 | @computed_field 74 | @property 75 | def description(self) -> str: 76 | if self.value not in CoTHow: 77 | return "Unknown" 78 | 79 | return CoTHow[self.value] 80 | 81 | class Event(CustomModel): 82 | version: float = 2.0 83 | type: Types 84 | uid: str 85 | time: datetime 86 | start: datetime 87 | stale: datetime 88 | how: How = Field(pattern=r"\w(-\w)+") 89 | opex: Optional[str] = None 90 | qos: Optional[str] = None 91 | access: Optional[str] = None 92 | detail: Optional[Detail] = None 93 | point: Optional[Point] = None 94 | 95 | def xml(self): 96 | return unparse( 97 | {"event": CustomModel.deep_prefix_add(self.model_dump(exclude_none=True))} 98 | ).replace( 99 | '', 100 | '', 101 | ) 102 | 103 | 104 | -------------------------------------------------------------------------------- /CoT/types.py: -------------------------------------------------------------------------------- 1 | CoTReservations = { 2 | "f": "friendly", 3 | "h": "hostile", 4 | "u": "unknown", 5 | "p": "pending", 6 | "a": "assumed", 7 | "n": "neutral", 8 | "s": "suspect", 9 | "j": "joker", 10 | "k": "faker", 11 | "o": "not specified", 12 | "x": "other", 13 | } 14 | 15 | CoTTypes = { 16 | "a-.-A" : { 17 | "full": "Air/Air Track", 18 | "desc": "Air Track", 19 | }, 20 | "a-.-A-C" : { 21 | "full": "Air/Civ", 22 | "desc": "CIVIL AIRCRAFT", 23 | }, 24 | "a-.-A-C-F" : { 25 | "full": "Air/Civ/fixed", 26 | "desc": "FIXED WING", 27 | }, 28 | "a-.-A-C-F-q" : { 29 | "full": "Air/Civ/fixed/rpv, drone, uav", 30 | "desc": "FIXED WING RPV/Drone", 31 | }, 32 | "a-.-A-C-H" : { 33 | "full": "Air/Civ/rotary", 34 | "desc": "ROTARY WING", 35 | }, 36 | "a-.-A-C-L" : { 37 | "full": "Air/Civ/Blimp", 38 | "desc": "LIGHTER THAN AIR", 39 | }, 40 | "a-.-A-M-F" : { 41 | "full": "Air/Mil/Fixed", 42 | "desc": "FIXED WING", 43 | }, 44 | "a-.-A-M-F-g" : { 45 | "full": "Air/Mil/Fixed/Gunship", 46 | "desc": "FIXED WING GUNSHIP", 47 | }, 48 | "a-.-A-M-F-A" : { 49 | "full": "Air/Mil/Fixed/Attack/Strike", 50 | "desc": "ATTACK/STRIKE", 51 | }, 52 | "a-.-A-M-F-B" : { 53 | "full": "Air/Mil/Fixed/Bomber", 54 | "desc": "BOMBER", 55 | }, 56 | "a-.-A-M-F-C" : { 57 | "full": "Air/Mil/Fixed/Transport", 58 | "desc": "CARGO AIRLIFT (TRANSPORT)", 59 | }, 60 | "a-.-A-M-F-C-H" : { 61 | "full": "Air/Mil/Fixed/Transport/Heavy", 62 | "desc": "CARGO AIRLIFT (HEAVY)", 63 | }, 64 | "a-.-A-M-F-C-L" : { 65 | "full": "Air/Mil/Fixed/Transport/Light", 66 | "desc": "CARGO AIRLIFT (LIGHT)", 67 | }, 68 | "a-.-A-M-F-C-M" : { 69 | "full": "Air/Mil/Fixed/Transport/Medium", 70 | "desc": "CARGO AIRLIFT (MEDIUM)", 71 | }, 72 | "a-.-A-M-F-D" : { 73 | "full": "Air/Mil/Fixed/C2", 74 | "desc": "AIRBORNE COMMAND POST (C2)", 75 | }, 76 | "a-.-A-M-F-F" : { 77 | "full": "Air/Mil/Fixed/Fighter", 78 | "desc": "FIGHTER", 79 | }, 80 | "a-.-A-M-F-F-I" : { 81 | "full": "Air/Mil/Fixed/Interceptor", 82 | "desc": "INTERCEPTOR", 83 | }, 84 | "a-.-A-M-F-H" : { 85 | "full": "Air/Mil/Fixed/CSAR", 86 | "desc": "COMBAT SEARCH AND RESCUE (CSAR)", 87 | }, 88 | "a-.-A-M-F-J" : { 89 | "full": "Air/Mil/Fixed/ECM/Jammer", 90 | "desc": "ELECTRONIC COUNTERMEASURES (ECM/JAMMER)", 91 | }, 92 | "a-.-A-M-F-K" : { 93 | "full": "Air/Mil/Fixed/Tanker", 94 | "desc": "TANKER", 95 | }, 96 | "a-.-A-M-F-L" : { 97 | "full": "Air/Mil/Fixed/VSTOL", 98 | "desc": "VSTOL", 99 | }, 100 | "a-.-A-M-F-M" : { 101 | "full": "Air/Mil/Fixed/SOF", 102 | "desc": "SPECIAL OPERATIONS FORCES (SOF)", 103 | }, 104 | "a-.-A-M-F-O" : { 105 | "full": "Air/Mil/Fixed/MEDEVAC", 106 | "desc": "MEDEVAC", 107 | }, 108 | "a-.-A-M-F-P" : { 109 | "full": "Air/Mil/Fixed/Patrol", 110 | "desc": "PATROL", 111 | }, 112 | "a-.-A-M-F-P-M" : { 113 | "full": "Air/Mil/Fixed/Mine Countermeasures", 114 | "desc": "MINE COUNTERMEASURES", 115 | }, 116 | "a-.-A-M-F-P-N" : { 117 | "full": "Air/Mil/Fixed/ASUW", 118 | "desc": "ANTISURFACE WARFARE/ASUW", 119 | }, 120 | "a-.-A-M-F-Q" : { 121 | "full": "Air/Mil/Fixed/Drone,RPV,UAV", 122 | "desc": "DRONE (RPV/UAV)", 123 | }, 124 | "a-.-A-M-F-R" : { 125 | "full": "Air/Mil/Fixed/RECONN", 126 | "desc": "RECONNAISSANCE", 127 | }, 128 | "a-.-A-M-F-R-W" : { 129 | "full": "Air/Mil/Fixed/AEW", 130 | "desc": "AIRBORNE EARLY WARNING (AEW)", 131 | }, 132 | "a-.-A-M-F-R-X" : { 133 | "full": "Air/Mil/Fixed/Photo", 134 | "desc": "PHOTOGRAPHIC", 135 | }, 136 | "a-.-A-M-F-R-Z" : { 137 | "full": "Air/Mil/Fixed/ESM", 138 | "desc": "ELECTRONIC SURVEILLANCE MEASURES", 139 | }, 140 | "a-.-A-M-F-S" : { 141 | "full": "Air/Mil/Fixed/ASW/Carrier Based", 142 | "desc": "ANTISUBMARINE WARFARE (ASW) CARRIER BASED", 143 | }, 144 | "a-.-A-M-F-T" : { 145 | "full": "Air/Mil/Fixed/Trainer", 146 | "desc": "TRAINER", 147 | }, 148 | "a-.-A-M-F-U" : { 149 | "full": "Air/Mil/Fixed/Utility", 150 | "desc": "UTILITY", 151 | }, 152 | "a-.-A-M-F-U-H" : { 153 | "full": "Air/Mil/Fixed/Utility/Heavy", 154 | "desc": "UTILITY (HEAVY)", 155 | }, 156 | "a-.-A-M-F-U-L" : { 157 | "full": "Air/Mil/Fixed/Utility/Light", 158 | "desc": "UTILITY (LIGHT)", 159 | }, 160 | "a-.-A-M-F-U-M" : { 161 | "full": "Air/Mil/Fixed/Utility/Medium", 162 | "desc": "UTILITY (MEDIUM)", 163 | }, 164 | "a-.-A-M-F-Y" : { 165 | "full": "Air/Mil/Fixed/C3I", 166 | "desc": "COMMUNICATIONS (C3I)", 167 | }, 168 | "a-.-A-M-H" : { 169 | "full": "Air/Mil/Rotor", 170 | "desc": "ROTARY WING", 171 | }, 172 | "a-.-A-M-H-A" : { 173 | "full": "Air/Mil/Rotor/Attack", 174 | "desc": "ATTACK", 175 | }, 176 | "a-.-A-M-H-C" : { 177 | "full": "Air/Mil/Rotor/Transport", 178 | "desc": "CARGO AIRLIFT (TRANSPORT)", 179 | }, 180 | "a-.-A-M-H-C-H" : { 181 | "full": "Air/Mil/Rotor/Transport/Heavy", 182 | "desc": "CARGO AIRLIFT (HEAVY)", 183 | }, 184 | "a-.-A-M-H-C-L" : { 185 | "full": "Air/Mil/Rotor/Transport/Light", 186 | "desc": "CARGO AIRLIFT (LIGHT)", 187 | }, 188 | "a-.-A-M-H-C-M" : { 189 | "full": "Air/Mil/Rotor/Transport/Medium", 190 | "desc": "CARGO AIRLIFT (MEDIUM)", 191 | }, 192 | "a-.-A-M-H-D" : { 193 | "full": "Air/Mil/Rotor/C2", 194 | "desc": "AIRBORNE COMMAND POST (C2)", 195 | }, 196 | "a-.-A-M-H-H" : { 197 | "full": "Air/Mil/Rotor/CSAR", 198 | "desc": "COMBAT SEARCH AND RESCUE (CSAR)", 199 | }, 200 | "a-.-A-M-H-I" : { 201 | "full": "Air/Mil/Rotor/Mine Countermeasures", 202 | "desc": "MINE COUNTERMEASURES", 203 | }, 204 | "a-.-A-M-H-J" : { 205 | "full": "Air/Mil/Rotor/ECM/Jammer", 206 | "desc": "ELECTRONIC COUNTERMEASURES (ECM/JAMMER)", 207 | }, 208 | "a-.-A-M-H-K" : { 209 | "full": "Air/Mil/Rotor/Tanker", 210 | "desc": "TANKER", 211 | }, 212 | "a-.-A-M-H-M" : { 213 | "full": "Air/Mil/Rotor/SOF", 214 | "desc": "SPECIAL OPERATIONS FORCES (SOF)", 215 | }, 216 | "a-.-A-M-H-O" : { 217 | "full": "Air/Mil/Rotor/MEDEVAC", 218 | "desc": "MEDEVAC", 219 | }, 220 | "a-.-A-M-H-Q" : { 221 | "full": "Air/Mil/Rotor/Drone,RPV,UAV", 222 | "desc": "DRONE (RPV/UAV)", 223 | }, 224 | "a-.-A-M-H-R" : { 225 | "full": "Air/Mil/Rotor/Reconnaissance", 226 | "desc": "RECONNAISSANCE", 227 | }, 228 | "a-.-A-M-H-S" : { 229 | "full": "Air/Mil/Rotor/ASW/MPA", 230 | "desc": "ANTISUBMARINE WARFARE/MPA", 231 | }, 232 | "a-.-A-M-H-T" : { 233 | "full": "Air/Mil/Rotor/Trainer", 234 | "desc": "TRAINER", 235 | }, 236 | "a-.-A-M-H-U" : { 237 | "full": "Air/Mil/Rotor/Utility", 238 | "desc": "UTILITY", 239 | }, 240 | "a-.-A-M-H-U-H" : { 241 | "full": "Air/Mil/Rotor/Utility/Heavy)", 242 | "desc": "UTILITY (HEAVY)", 243 | }, 244 | "a-.-A-M-H-U-L" : { 245 | "full": "Air/Mil/Rotor/Utility/Light)", 246 | "desc": "UTILITY (LIGHT)", 247 | }, 248 | "a-.-A-M-H-U-M" : { 249 | "full": "Air/Mil/Rotor/Utility/Medium)", 250 | "desc": "UTILITY (MEDIUM)", 251 | }, 252 | "a-.-A-M-L" : { 253 | "full": "Air/Mil/Blimp", 254 | "desc": "LIGHTER THAN AIR", 255 | }, 256 | "a-.-A-W" : { 257 | "full": "Air/Weapon", 258 | "desc": "WEAPON", 259 | }, 260 | "a-.-A-W-D" : { 261 | "full": "Air/Weapon/Decoy", 262 | "desc": "DECOY", 263 | }, 264 | "a-.-A-W-M" : { 265 | "full": "Air/Weapon/Missile In Flight", 266 | "desc": "MISSILE IN FLIGHT", 267 | }, 268 | "a-.-A-W-M-A" : { 269 | "full": "Air/Weapon/Missile/Air Launched", 270 | "desc": "AIR LAUNCHED MISSILE", 271 | }, 272 | "a-.-A-W-M-A-A" : { 273 | "full": "Air/Weapon/Missile/Air To Air", 274 | "desc": "AIR TO AIR MISSILE (AAM)", 275 | }, 276 | "a-.-A-W-M-A-S" : { 277 | "full": "Air/Weapon/Missile/Air To Surface", 278 | "desc": "AIR TO SURFACE MISSILE (ASM)", 279 | }, 280 | "a-.-A-W-M-L" : { 281 | "full": "Air/Weapon/Missile/Attack Missile", 282 | "desc": "LAND ATTACK MISSILE", 283 | }, 284 | "a-.-A-W-M-S" : { 285 | "full": "Air/Weapon/Missile/Land Launched Missile", 286 | "desc": "SURFACE/LAND LAUNCHED MISSILE", 287 | }, 288 | "a-.-A-W-M-S-A" : { 289 | "full": "Air/Weapon/Missile/SAM", 290 | "desc": "SURFACE TO AIR MISSILE (SAM)", 291 | }, 292 | "a-.-A-W-M-S-A-f" : { 293 | "full": "Air/Weapon/Missile/SAM/FixedSite", 294 | "desc": "SAM (FixedSite)", 295 | }, 296 | "a-.-A-W-M-S-A-i" : { 297 | "full": "Air/Weapon/Missile/SAM/Manpad", 298 | "desc": "SAM (Manpad)", 299 | }, 300 | "a-.-A-W-M-S-A-m" : { 301 | "full": "Air/Weapon/Missile/SAM/Mobile", 302 | "desc": "SAM (Mobile)", 303 | }, 304 | "a-.-A-W-M-S-S" : { 305 | "full": "Air/Weapon/Missile/Surface To Surface (SSM)", 306 | "desc": "SURFACE TO SURFACE MISSILE (SSM)", 307 | }, 308 | "a-.-A-W-M-U" : { 309 | "full": "Air/Weapon/Missile/Subsurface To Surface (S/SSM)", 310 | "desc": "SUBSURFACE TO SURFACE MISSILE (S/SSM)", 311 | }, 312 | "a-.-G" : { 313 | "full": "Ground", 314 | "desc": "GROUND TRACK", 315 | }, 316 | "a-.-G-E" : { 317 | "full": "Gnd/Equipment", 318 | "desc": "EQUIPMENT", 319 | }, 320 | "a-.-G-E-S" : { 321 | "full": "Gnd/Equip/Sensor", 322 | "desc": "SENSOR", 323 | }, 324 | "a-.-G-E-S-E" : { 325 | "full": "Gnd/Equip/Sensor/Emplaced", 326 | "desc": "EMPLACED SENSOR", 327 | }, 328 | "a-.-G-E-S-R" : { 329 | "full": "Gnd/Equip/Sensor/Radar", 330 | "desc": "RADAR", 331 | }, 332 | "a-.-G-E-V" : { 333 | "full": "Gnd/Equip/Vehicle", 334 | "desc": "GROUND VEHICLE", 335 | }, 336 | "a-.-G-E-V-A" : { 337 | "full": "Gnd/Equip/Vehic/Armor/Gun", 338 | "desc": "Armor (GUN)", 339 | }, 340 | "a-.-G-E-V-A-A" : { 341 | "full": "Gnd/Equip/Vehic/Armor/Apc", 342 | "desc": "Armor (APC)", 343 | }, 344 | "a-.-G-E-V-A-A-R" : { 345 | "full": "Gnd/Equip/Vehic/Armor/Apc/Recovery", 346 | "desc": "ARMORED PERSONNEL CARRIER RECOVERY", 347 | }, 348 | "a-.-G-E-V-A-C" : { 349 | "full": "Gnd/Equip/Vehic/Armor/C2V/ACV", 350 | "desc": "C2V/ACV", 351 | }, 352 | "a-.-G-E-V-A-I" : { 353 | "full": "Gnd/Equip/Vehic/Armor/Infantry", 354 | "desc": "ARMORED INFANTRY", 355 | }, 356 | "a-.-G-E-V-A-L" : { 357 | "full": "Gnd/Equip/Vehic/Armor/Light", 358 | "desc": "LIGHT ARMORED VEHICLE", 359 | }, 360 | "a-.-G-E-V-A-S" : { 361 | "full": "Gnd/Equip/Vehic/Armor/Combat Service Support", 362 | "desc": "COMBAT SERVICE SUPPORT VEHICLE", 363 | }, 364 | "a-.-G-E-V-A-T" : { 365 | "full": "Gnd/Equip/Vehic/Armor/Tank", 366 | "desc": "TANK", 367 | }, 368 | "a-.-G-E-V-A-T-H" : { 369 | "full": "Gnd/Equip/Vehic/Armor/Tank/Heavy", 370 | "desc": "TANK HEAVY", 371 | }, 372 | "a-.-G-E-V-A-T-H-R" : { 373 | "full": "Gnd/Equip/Vehic/Armor/Tank/Heavy/Recovery", 374 | "desc": "TANK HEAVY RECOVERY", 375 | }, 376 | "a-.-G-E-V-A-T-L" : { 377 | "full": "Gnd/Equip/Vehic/Armor/Tank/Light", 378 | "desc": "TANK LIGHT", 379 | }, 380 | "a-.-G-E-V-A-T-L-R" : { 381 | "full": "Gnd/Equip/Vehic/Armor/Tank/Light/Recovery", 382 | "desc": "TANK LIGHT RECOVERY", 383 | }, 384 | "a-.-G-E-V-A-T-M" : { 385 | "full": "Gnd/Equip/Vehic/Armor/Tank/Medium", 386 | "desc": "TANK MEDIUM", 387 | }, 388 | "a-.-G-E-V-A-T-M-R" : { 389 | "full": "Gnd/Equip/Vehic/Armor/Tank/Medium/Recovery", 390 | "desc": "TANK MEDIUM RECOVERY", 391 | }, 392 | "a-.-G-E-V-C" : { 393 | "full": "Gnd/Equip/Vehic/Civilian", 394 | "desc": "CIVILIAN VEHICLE", 395 | }, 396 | "a-.-G-E-V-E" : { 397 | "full": "Gnd/Equip/Vehic/Engineer", 398 | "desc": "ENGINEER VEHICLE", 399 | }, 400 | "a-.-G-E-V-E-A" : { 401 | "full": "Gnd/Equip/Vehic/Mine Clearing Vehicle", 402 | "desc": "MINE CLEARING VEHICLE", 403 | }, 404 | "a-.-G-E-V-E-A-A" : { 405 | "full": "Gnd/Equip/Vehic/Armored Mounted Mine Clearing Vehicle", 406 | "desc": "ARMORED MOUNTED MINE CLEARING VEHICLE", 407 | }, 408 | "a-.-G-E-V-E-A-T" : { 409 | "full": "Gnd/Equip/Vehic/Trailer Mounted Mine Clearing Vehicle", 410 | "desc": "TRAILER MOUNTED MINE CLEARING VEHICLE", 411 | }, 412 | "a-.-G-E-V-E-B" : { 413 | "full": "Gnd/Equip/Vehic/Bridge", 414 | "desc": "BRIDGE", 415 | }, 416 | "a-.-G-E-V-E-C" : { 417 | "full": "Gnd/Equip/Vehic/Construction", 418 | "desc": "CONSTRUCTION VEHICLE", 419 | }, 420 | "a-.-G-E-V-E-D" : { 421 | "full": "Gnd/Equip/Vehic/Dozer", 422 | "desc": "DOZER", 423 | }, 424 | "a-.-G-E-V-E-E" : { 425 | "full": "Gnd/Equip/Vehic/Earthmover", 426 | "desc": "EARTHMOVER", 427 | }, 428 | "a-.-G-E-V-E-M" : { 429 | "full": "Gnd/Equip/Vehic/Mine Laying Vehicle", 430 | "desc": "MINE LAYING VEHICLE", 431 | }, 432 | "a-.-G-E-V-E-M-L" : { 433 | "full": "Gnd/Equip/Vehic/Truck Mounted With Volcano", 434 | "desc": "TRUCK MOUNTED WITH VOLCANO", 435 | }, 436 | "a-.-G-E-V-E-M-V" : { 437 | "full": "Gnd/Equip/Vehic/Armored Carrier With Volcano", 438 | "desc": "ARMORED CARRIER WITH VOLCANO", 439 | }, 440 | "a-.-G-E-V-T" : { 441 | "full": "Gnd/Equip/Vehic/Locomotive", 442 | "desc": "Locomotive", 443 | }, 444 | "a-.-G-E-V-U" : { 445 | "full": "Gnd/Equip/Vehic/Utility", 446 | "desc": "UTILITY VEHICLE", 447 | }, 448 | "a-.-G-E-V-U-B" : { 449 | "full": "Gnd/Equip/Vehic/Bus", 450 | "desc": "BUS", 451 | }, 452 | "a-.-G-E-V-U-L" : { 453 | "full": "Gnd/Equip/Vehic/Limited Cross Country Truck", 454 | "desc": "LIMITED CROSS COUNTRY TRUCK", 455 | }, 456 | "a-.-G-E-V-U-R" : { 457 | "full": "Gnd/Equip/Vehic/Boat", 458 | "desc": "WATER CRAFT", 459 | }, 460 | "a-.-G-E-V-U-R-l" : { 461 | "full": "Gnd/Equip/Vehic/Boat/Large", 462 | "desc": "Boat (Large)", 463 | }, 464 | "a-.-G-E-V-U-R-m" : { 465 | "full": "Gnd/Equip/Vehic/Boat/Med", 466 | "desc": "Boat (Med)", 467 | }, 468 | "a-.-G-E-V-U-R-s" : { 469 | "full": "Gnd/Equip/Vehic/Boat/Small", 470 | "desc": "Boat (Small)", 471 | }, 472 | "a-.-G-E-V-U-S" : { 473 | "full": "Gnd/Equip/Vehic/Semi", 474 | "desc": "SEMI", 475 | }, 476 | "a-.-G-E-V-U-X" : { 477 | "full": "Gnd/Equip/Vehic/Cross Country Truck", 478 | "desc": "CROSS COUNTRY TRUCK", 479 | }, 480 | "a-.-G-E-V-m" : { 481 | "full": "Gnd/Equip/Vehic/Ambulance", 482 | "desc": "Ambulance", 483 | }, 484 | "a-.-G-E-W" : { 485 | "full": "Gnd/Equip/Weapon", 486 | "desc": "WEAPON", 487 | }, 488 | "a-.-G-E-W-A" : { 489 | "full": "Gnd/Equip/Weapon/Air Defense Gun", 490 | "desc": "AIR DEFENSE GUN", 491 | }, 492 | "a-.-G-E-W-A-H" : { 493 | "full": "Gnd/Equip/Weapon/AAA/Heavy", 494 | "desc": "AAA (Heavy)", 495 | }, 496 | "a-.-G-E-W-A-L" : { 497 | "full": "Gnd/Equip/Weapon/AAA/Light", 498 | "desc": "AAA (Light)", 499 | }, 500 | "a-.-G-E-W-A-M" : { 501 | "full": "Gnd/Equip/Weapon/AAA/Medium", 502 | "desc": "AAA (Medium)", 503 | }, 504 | "a-.-G-E-W-D" : { 505 | "full": "Gnd/Equip/Weapon/DirectFire/", 506 | "desc": "DIRECT FIRE GUN", 507 | }, 508 | "a-.-G-E-W-D-H" : { 509 | "full": "Gnd/Equip/Weapon/DirectFire/Heavy", 510 | "desc": "DIRECT FIRE GUN HEAVY", 511 | }, 512 | "a-.-G-E-W-D-H-S" : { 513 | "full": "Gnd/Equip/Weapon/DirectFire/Heavy/Self Propelled", 514 | "desc": "DIRECT FIRE GUN HEAVY SELF PROPELLED", 515 | }, 516 | "a-.-G-E-W-D-L" : { 517 | "full": "Gnd/Equip/Weapon/DirectFire/Light", 518 | "desc": "DIRECT FIRE GUN LIGHT", 519 | }, 520 | "a-.-G-E-W-D-L-S" : { 521 | "full": "Gnd/Equip/Weapon/DirectFire/Light/Self Propelled", 522 | "desc": "DIRECT FIRE GUN LIGHT SELF PROPELLED", 523 | }, 524 | "a-.-G-E-W-D-M" : { 525 | "full": "Gnd/Equip/Weapon/DirectFire/Medium", 526 | "desc": "DIRECT FIRE GUN MEDIUM", 527 | }, 528 | "a-.-G-E-W-D-M-S" : { 529 | "full": "Gnd/Equip/Weapon/DirectFire/Medium/Self Propelled", 530 | "desc": "DIRECT FIRE GUN MEDIUM SELF PROPELLED", 531 | }, 532 | "a-.-G-E-W-G" : { 533 | "full": "Gnd/Equip/Weapon/AnitTankGun", 534 | "desc": "ANTI TANK GUN", 535 | }, 536 | "a-.-G-E-W-G-H" : { 537 | "full": "Gnd/Equip/Weapon/Atg/Heavy", 538 | "desc": "ANTI TANK GUN HEAVY", 539 | }, 540 | "a-.-G-E-W-G-L" : { 541 | "full": "Gnd/Equip/Weapon/Atg/Light", 542 | "desc": "ANTI TANK GUN LIGHT", 543 | }, 544 | "a-.-G-E-W-G-M" : { 545 | "full": "Gnd/Equip/Weapon/Atg/Medium", 546 | "desc": "ANTI TANK GUN MEDIUM", 547 | }, 548 | "a-.-G-E-W-G-R" : { 549 | "full": "Gnd/Equip/Weapon/Atg/Recoilless", 550 | "desc": "ANTI TANK GUN RECOILLESS", 551 | }, 552 | "a-.-G-E-W-H" : { 553 | "full": "Gnd/Equip/Weapon/Howitzer", 554 | "desc": "HOWITZER", 555 | }, 556 | "a-.-G-E-W-H-H" : { 557 | "full": "Gnd/Equip/Weapon/Howitzer/Heavy", 558 | "desc": "HOWITZER HEAVY", 559 | }, 560 | "a-.-G-E-W-H-H-S" : { 561 | "full": "Gnd/Equip/Weapon/Howitzer/Heavy/Self Propelled", 562 | "desc": "HOWITZER HEAVY SELF PROPELLED", 563 | }, 564 | "a-.-G-E-W-H-L" : { 565 | "full": "Gnd/Equip/Weapon/Howitzer/Light", 566 | "desc": "HOWITZER LIGHT", 567 | }, 568 | "a-.-G-E-W-H-L-S" : { 569 | "full": "Gnd/Equip/Weapon/Howitzer/Light/Self Propelled", 570 | "desc": "HOWITZER LIGHT SELF PROPELLED", 571 | }, 572 | "a-.-G-E-W-H-M" : { 573 | "full": "Gnd/Equip/Weapon/Howitzer/Medium", 574 | "desc": "HOWITZER MEDIUM", 575 | }, 576 | "a-.-G-E-W-H-M-S" : { 577 | "full": "Gnd/Equip/Weapon/Howitzer/Medium/Self Propelled", 578 | "desc": "HOWITZER MEDIUM SELF PROPELLED", 579 | }, 580 | "a-.-G-E-W-M" : { 581 | "full": "Gnd/Equip/Weapon/MissileLauncher", 582 | "desc": "MISSILE LAUNCHER", 583 | }, 584 | "a-.-G-E-W-M-A" : { 585 | "full": "Gnd/Equip/Weapon/MissileLauncher/Ad/Air Defense", 586 | "desc": "AIR DEFENSE (AD) MISSILE LAUNCHER", 587 | }, 588 | "a-.-G-E-W-M-A-I" : { 589 | "full": "Gnd/Equip/Weapon/MissileLauncher/Ad/Intermediate Range", 590 | "desc": "INTERMEDIATE RANGE AD MISSILE LAUNCHER", 591 | }, 592 | "a-.-G-E-W-M-A-L" : { 593 | "full": "Gnd/Equip/Weapon/MissileLauncher/Ad/Long Range", 594 | "desc": "LONG RANGE AD MISSILE LAUNCHER", 595 | }, 596 | "a-.-G-E-W-M-A-S" : { 597 | "full": "Gnd/Equip/Weapon/MissileLauncher/Ad/Short Range", 598 | "desc": "SHORT RANGE AD MISSILE LAUNCHER", 599 | }, 600 | "a-.-G-E-W-M-A-T" : { 601 | "full": "Gnd/Equip/Weapon/MissileLauncher/Ad/Theater", 602 | "desc": "AD MISSILE LAUNCHER THEATER", 603 | }, 604 | "a-.-G-E-W-M-S" : { 605 | "full": "Gnd/Equip/Weapon/MissileLauncher/SS/Surface Surf (SS)", 606 | "desc": "SURF SURF (SS) MISSILE LAUNCHER", 607 | }, 608 | "a-.-G-E-W-M-S-I" : { 609 | "full": "Gnd/Equip/Weapon/MissileLauncher/SS/Intermediate Range", 610 | "desc": "INTERMEDIATE RANGE SS MISSILE LAUNCHER", 611 | }, 612 | "a-.-G-E-W-M-S-L" : { 613 | "full": "Gnd/Equip/Weapon/MissileLauncher/SS/Long Range", 614 | "desc": "LONG RANGE SS MISSILE LAUNCHER", 615 | }, 616 | "a-.-G-E-W-M-S-S" : { 617 | "full": "Gnd/Equip/Weapon/MissileLauncher/SS/Short Range", 618 | "desc": "SHORT RANGE SS MISSILE LAUNCHER", 619 | }, 620 | "a-.-G-E-W-M-T" : { 621 | "full": "Gnd/Equip/Weapon/MissileLauncher/AT/Antitank", 622 | "desc": "MISSILE LAUNCHER ANTITANK (AT)", 623 | }, 624 | "a-.-G-E-W-M-T-H" : { 625 | "full": "Gnd/Equip/Weapon/MissileLauncher/AT/Heavy", 626 | "desc": "MISSILE LAUNCHER AT HEAVY", 627 | }, 628 | "a-.-G-E-W-M-T-L" : { 629 | "full": "Gnd/Equip/Weapon/MissileLauncher/AT/Light", 630 | "desc": "MISSILE LAUNCHER AT LIGHT", 631 | }, 632 | "a-.-G-E-W-M-T-M" : { 633 | "full": "Gnd/Equip/Weapon/MissileLauncher/AT/Medium", 634 | "desc": "MISSILE LAUNCHER AT MEDIUM", 635 | }, 636 | "a-.-G-E-W-O" : { 637 | "full": "Gnd/Equip/Weapon/Mortar", 638 | "desc": "MORTAR", 639 | }, 640 | "a-.-G-E-W-O-H" : { 641 | "full": "Gnd/Equip/Weapon/Mortar/Heavy", 642 | "desc": "MORTAR HEAVY", 643 | }, 644 | "a-.-G-E-W-O-L" : { 645 | "full": "Gnd/Equip/Weapon/Mortar/Light", 646 | "desc": "MORTAR LIGHT", 647 | }, 648 | "a-.-G-E-W-O-M" : { 649 | "full": "Gnd/Equip/Weapon/Mortar/Medium", 650 | "desc": "MORTAR MEDIUM", 651 | }, 652 | "a-.-G-E-W-R" : { 653 | "full": "Gnd/Equip/Weapon/Rifle/Automatic Weapon", 654 | "desc": "RIFLE/AUTOMATIC WEAPON", 655 | }, 656 | "a-.-G-E-W-R-H" : { 657 | "full": "Gnd/Equip/Weapon/Rifle/Heavy Machine Gun", 658 | "desc": "HEAVY MACHINE GUN", 659 | }, 660 | "a-.-G-E-W-R-L" : { 661 | "full": "Gnd/Equip/Weapon/Rifle/Light Machine Gun", 662 | "desc": "LIGHT MACHINE GUN", 663 | }, 664 | "a-.-G-E-W-R-R" : { 665 | "full": "Gnd/Equip/Weapon/Rifle/Rifle", 666 | "desc": "RIFLE", 667 | }, 668 | "a-.-G-E-W-S" : { 669 | "full": "Gnd/Equip/Weapon/RocketLauncher/Single/", 670 | "desc": "SINGLE ROCKET LAUNCHER", 671 | }, 672 | "a-.-G-E-W-S-H" : { 673 | "full": "Gnd/Equip/Weapon/RocketLauncher/Single/Heavy", 674 | "desc": "SINGLE ROCKET LAUNCHER HEAVY", 675 | }, 676 | "a-.-G-E-W-S-L" : { 677 | "full": "Gnd/Equip/Weapon/RocketLauncher/Single/Light", 678 | "desc": "SINGLE ROCKET LAUNCHER LIGHT", 679 | }, 680 | "a-.-G-E-W-S-M" : { 681 | "full": "Gnd/Equip/Weapon/RocketLauncher/Single/Medium", 682 | "desc": "SINGLE ROCKET LAUNCHER MEDIUM", 683 | }, 684 | "a-.-G-E-W-T" : { 685 | "full": "Gnd/Equip/Weapon/RocketLauncher/AntiTank", 686 | "desc": "ANTI TANK ROCKET LAUNCHER", 687 | }, 688 | "a-.-G-E-W-T-H" : { 689 | "full": "Gnd/Equip/Weapon/RocketLauncher/AT/Heavy", 690 | "desc": "ANTI TANK ROCKET LAUNCHER HEAVY", 691 | }, 692 | "a-.-G-E-W-T-L" : { 693 | "full": "Gnd/Equip/Weapon/RocketLauncher/AT/Light", 694 | "desc": "ANTI TANK ROCKET LAUNCHER LIGHT", 695 | }, 696 | "a-.-G-E-W-T-M" : { 697 | "full": "Gnd/Equip/Weapon/RocketLauncher/AT/Medium", 698 | "desc": "ANTI TANK ROCKET LAUNCHER MEDIUM", 699 | }, 700 | "a-.-G-E-W-X" : { 701 | "full": "Gnd/Equip/Weapon/RocketLauncher/Multiple ", 702 | "desc": "MULTIPLE ROCKET LAUNCHER", 703 | }, 704 | "a-.-G-E-W-X-H" : { 705 | "full": "Gnd/Equip/Weapon/RocketLauncher/Multiple/Heavy", 706 | "desc": "MULTIPLE ROCKET LAUNCHER HEAVY", 707 | }, 708 | "a-.-G-E-W-X-L" : { 709 | "full": "Gnd/Equip/Weapon/RocketLauncher/Multiple/Light", 710 | "desc": "MULTIPLE ROCKET LAUNCHER LIGHT", 711 | }, 712 | "a-.-G-E-W-X-M" : { 713 | "full": "Gnd/Equip/Weapon/RocketLauncher/Multiple/Medium", 714 | "desc": "MULTIPLE ROCKET LAUNCHER MEDIUM", 715 | }, 716 | "a-.-G-E-W-Z" : { 717 | "full": "Gnd/Equip/Weapon/Grenade Launcher", 718 | "desc": "GRENADE LAUNCHER", 719 | }, 720 | "a-.-G-E-W-Z-H" : { 721 | "full": "Gnd/Equip/Weapon/Grenade Launcher/Heavy", 722 | "desc": "GRENADE LAUNCHER HEAVY", 723 | }, 724 | "a-.-G-E-W-Z-L" : { 725 | "full": "Gnd/Equip/Weapon/Grenade Launcher/Light", 726 | "desc": "GRENADE LAUNCHER LIGHT", 727 | }, 728 | "a-.-G-E-W-Z-M" : { 729 | "full": "Gnd/Equip/Weapon/Grenade Launcher/Medium", 730 | "desc": "GRENADE LAUNCHER MEDIUM", 731 | }, 732 | "a-.-G-E-X" : { 733 | "full": "Gnd/Equip/Special Equipment", 734 | "desc": "SPECIAL EQUIPMENT", 735 | }, 736 | "a-.-G-E-X-F" : { 737 | "full": "Gnd/Equip/Flame Thrower", 738 | "desc": "FLAME THROWER", 739 | }, 740 | "a-.-G-E-X-L" : { 741 | "full": "Gnd/Equip/Laser", 742 | "desc": "LASER", 743 | }, 744 | "a-.-G-E-X-M" : { 745 | "full": "Gnd/Equip/Land Mines", 746 | "desc": "LAND MINES", 747 | }, 748 | "a-.-G-E-X-M-C" : { 749 | "full": "Gnd/Equip/Claymore", 750 | "desc": "CLAYMORE", 751 | }, 752 | "a-.-G-E-X-M-L" : { 753 | "full": "Gnd/Equip/Less Than Lethal", 754 | "desc": "LESS THAN LETHAL", 755 | }, 756 | "a-.-G-E-X-N" : { 757 | "full": "Gnd/Equip/Nbc Equipment", 758 | "desc": "NBC EQUIPMENT", 759 | }, 760 | "a-.-G-I" : { 761 | "full": "Gnd/Building", 762 | "desc": "Building", 763 | }, 764 | "a-.-G-I-B" : { 765 | "full": "Gnd/Structure/Base/Military", 766 | "desc": "MILITARY BASE/FACILITY", 767 | }, 768 | "a-.-G-I-B-A" : { 769 | "full": "Gnd/Structure/Base/Airbase", 770 | "desc": "AIRPORT/AIRBASE", 771 | }, 772 | "a-.-G-I-B-N" : { 773 | "full": "Gnd/Structure/Base/Naval Base", 774 | "desc": "SEAPORT/NAVAL BASE", 775 | }, 776 | "a-.-G-I-c" : { 777 | "full": "Gnd/Structure/Civilian", 778 | "desc": "Civilian", 779 | }, 780 | "a-.-G-I-c-b" : { 781 | "full": "Gnd/Structure/Civilian/Bridge", 782 | "desc": "Bridge", 783 | }, 784 | "a-.-G-I-c-bar" : { 785 | "full": "Gnd/Structure/Civilian/Fence or Wall or Barrier", 786 | "desc": "Fence/Wall/Barrier", 787 | }, 788 | "a-.-G-I-c-can" : { 789 | "full": "Gnd/Structure/Civilian/Canal", 790 | "desc": "Canal", 791 | }, 792 | "a-.-G-I-c-can-l" : { 793 | "full": "Gnd/Structure/Civilian/Canal/Lock", 794 | "desc": "Canal Lock", 795 | }, 796 | "a-.-G-I-c-frm" : { 797 | "full": "Gnd/Structure/Civilian/Farm", 798 | "desc": "Farm", 799 | }, 800 | "a-.-G-I-c-l" : { 801 | "full": "Gnd/Structure/Civilian/Levee", 802 | "desc": "Levy", 803 | }, 804 | "a-.-G-I-c-mon" : { 805 | "full": "Gnd/Structure/Civilian/Monument", 806 | "desc": "Monument", 807 | }, 808 | "a-.-G-I-c-o" : { 809 | "full": "Gnd/Structure/Civilian/Offices", 810 | "desc": "Offices", 811 | }, 812 | "a-.-G-I-c-rah" : { 813 | "full": "Gnd/Structure/Civilian/Residence or Apartment or Hotel", 814 | "desc": "Residence/Apartment/Hotel", 815 | }, 816 | "a-.-G-I-c-rel" : { 817 | "full": "Gnd/Structure/Civilian/Religous", 818 | "desc": "Religous", 819 | }, 820 | "a-.-G-I-c-res" : { 821 | "full": "Gnd/Structure/Civilian/Resevoir", 822 | "desc": "Resevoir", 823 | }, 824 | "a-.-G-I-c-ret" : { 825 | "full": "Gnd/Structure/Civilian/Retail", 826 | "desc": "Retail", 827 | }, 828 | "a-.-G-I-c-sch" : { 829 | "full": "Gnd/Structure/Civilian/School", 830 | "desc": "School", 831 | }, 832 | "a-.-G-I-c-vip" : { 833 | "full": "Gnd/Structure/Civilian/VIP", 834 | "desc": "VIP", 835 | }, 836 | "a-.-G-I-c-whs" : { 837 | "full": "Gnd/Structure/Civilian/Warehouse", 838 | "desc": "Warehouse", 839 | }, 840 | "a-.-G-I-E" : { 841 | "full": "Gnd/Structure/Factory", 842 | "desc": "EQUIPMENT MANUFACTURE", 843 | }, 844 | "a-.-G-I-E-h" : { 845 | "full": "Gnd/Structure/Factory/Heavy", 846 | "desc": "Heavy", 847 | }, 848 | "a-.-G-I-E-l" : { 849 | "full": "Gnd/Structure/Factory/Light", 850 | "desc": "Light", 851 | }, 852 | "a-.-G-I-E-o" : { 853 | "full": "Gnd/Structure/Factory/Plant Other", 854 | "desc": "Plant Other", 855 | }, 856 | "a-.-G-I-G" : { 857 | "full": "Gnd/Structure/Government", 858 | "desc": "GOVERNMENT LEADERSHIP", 859 | }, 860 | "a-.-G-I-i" : { 861 | "full": "Gnd/Structure/IM Facilities", 862 | "desc": "IM Facilities", 863 | }, 864 | "a-.-G-I-i-e" : { 865 | "full": "Gnd/Structure/IM Facilities/Emergency Management", 866 | "desc": "Emergency Management", 867 | }, 868 | "a-.-G-I-i-e-eoc" : { 869 | "full": "Gnd/Structure/IM Facilities/Emergency Management/Emergency Operations Center", 870 | "desc": "Emergency Operations Center", 871 | }, 872 | "a-.-G-I-i-e-ic" : { 873 | "full": "Gnd/Structure/IM Facilities/Emergency Management/Incident Commander", 874 | "desc": "Incident Commander", 875 | }, 876 | "a-.-G-I-i-e-icc" : { 877 | "full": "Gnd/Structure/IM Facilities/Emergency Management/Incident Communications Center", 878 | "desc": "Incident Communications Center", 879 | }, 880 | "a-.-G-I-i-e-icp" : { 881 | "full": "Gnd/Structure/IM Facilities/Emergency Management/Incident Command Post", 882 | "desc": "Incident Command Post", 883 | }, 884 | "a-.-G-I-i-e-wr" : { 885 | "full": "Gnd/Structure/IM Facilities/Emergency Management/War Room", 886 | "desc": "War Room", 887 | }, 888 | "a-.-G-I-i-f" : { 889 | "full": "Gnd/Structure/IM Facilities/Fire and Hazmat", 890 | "desc": "Fire/Hazmat", 891 | }, 892 | "a-.-G-I-i-f-fd" : { 893 | "full": "Gnd/Structure/IM Facilities/Fire and Hazmat/Fire Department", 894 | "desc": "Fire Department", 895 | }, 896 | "a-.-G-I-i-h" : { 897 | "full": "Gnd/Structure/IM Facilities/Health and Medical", 898 | "desc": "Health and Medical", 899 | }, 900 | "a-.-G-I-i-h-md" : { 901 | "full": "Gnd/Structure/IM Facilities/Health and Medical/Medical Dispatch", 902 | "desc": "Medical Dispatch", 903 | }, 904 | "a-.-G-I-i-l" : { 905 | "full": "Gnd/Structure/IM Facilities/Law Enforcement", 906 | "desc": "Law Enforcement", 907 | }, 908 | "a-.-G-I-i-l-cp" : { 909 | "full": "Gnd/Structure/IM Facilities/Law Enforcement/Police Checkpoint", 910 | "desc": "Police Checkpoint", 911 | }, 912 | "a-.-G-I-i-l-hp" : { 913 | "full": "Gnd/Structure/IM Facilities/Law Enforcement/Highway Patrol", 914 | "desc": "Highway Patrol", 915 | }, 916 | "a-.-G-I-i-l-lp" : { 917 | "full": "Gnd/Structure/IM Facilities/Law Enforcement/Local Police", 918 | "desc": "Local Police", 919 | }, 920 | "a-.-G-I-i-l-ntz" : { 921 | "full": "Gnd/Structure/IM Facilities/Law Enforcement/No Trespassing Zone", 922 | "desc": "No Trespassing Zone", 923 | }, 924 | "a-.-G-I-i-l-sd" : { 925 | "full": "Gnd/Structure/IM Facilities/Law Enforcement/Sheriffs Department", 926 | "desc": "Sheriffs Department", 927 | }, 928 | "a-.-G-I-i-l-sp" : { 929 | "full": "Gnd/Structure/IM Facilities/Law Enforcement/State Police", 930 | "desc": "State Police", 931 | }, 932 | "a-.-G-I-i-m" : { 933 | "full": "Gnd/Structure/IM Facilities/Emergency Medical Services", 934 | "desc": "Emergency Medical Services", 935 | }, 936 | "a-.-G-I-i-o" : { 937 | "full": "Gnd/Structure/IM Facilities/Other", 938 | "desc": "Other", 939 | }, 940 | "a-.-G-I-i-o-ad" : { 941 | "full": "Gnd/Structure/IM Facilities/Other/Agency Dispatch", 942 | "desc": "Agency Dispatch", 943 | }, 944 | "a-.-G-I-i-o-ad-ems" : { 945 | "full": "Gnd/Structure/IM Facilities/Other/Agency Dispatch/EMS", 946 | "desc": "EMS", 947 | }, 948 | "a-.-G-I-i-o-ad-f" : { 949 | "full": "Gnd/Structure/IM Facilities/Other/Agency Dispatch/Fire", 950 | "desc": "Fire", 951 | }, 952 | "a-.-G-I-i-o-ad-hwy" : { 953 | "full": "Gnd/Structure/IM Facilities/Other/Agency Dispatch/Highway", 954 | "desc": "Highway", 955 | }, 956 | "a-.-G-I-i-o-ad-mda" : { 957 | "full": "Gnd/Structure/IM Facilities/Other/Agency Dispatch/Media", 958 | "desc": "Media", 959 | }, 960 | "a-.-G-I-i-o-ad-pl" : { 961 | "full": "Gnd/Structure/IM Facilities/Other/Agency Dispatch/Police Local", 962 | "desc": "Police Local", 963 | }, 964 | "a-.-G-I-i-o-ad-ps" : { 965 | "full": "Gnd/Structure/IM Facilities/Other/Agency Dispatch/Police Station", 966 | "desc": "Police Station", 967 | }, 968 | "a-.-G-I-i-o-ad-tow" : { 969 | "full": "Gnd/Structure/IM Facilities/Other/Agency Dispatch/Tow", 970 | "desc": "Tow", 971 | }, 972 | "a-.-G-I-i-o-ad-ts" : { 973 | "full": "Gnd/Structure/IM Facilities/Other/Agency Dispatch/Transit", 974 | "desc": "Transit", 975 | }, 976 | "a-.-G-I-i-o-bcc" : { 977 | "full": "Gnd/Structure/IM Facilities/Other/Border Control Checkpoint", 978 | "desc": "Border Control Checkpoint", 979 | }, 980 | "a-.-G-I-i-o-dmz" : { 981 | "full": "Gnd/Structure/IM Facilities/Other/DMZ", 982 | "desc": "DMZ", 983 | }, 984 | "a-.-G-I-i-o-isp" : { 985 | "full": "Gnd/Structure/IM Facilities/Other/Independent Service Provider", 986 | "desc": "Independent Service Provider", 987 | }, 988 | "a-.-G-I-i-o-mc" : { 989 | "full": "Gnd/Structure/IM Facilities/Other/Mobile Center", 990 | "desc": "Mobile Center", 991 | }, 992 | "a-.-G-I-i-o-mc-f" : { 993 | "full": "Gnd/Structure/IM Facilities/Other/Mobile Center/Fire", 994 | "desc": "Fire", 995 | }, 996 | "a-.-G-I-i-o-mc-h" : { 997 | "full": "Gnd/Structure/IM Facilities/Other/Mobile Center/Medical", 998 | "desc": "Medical", 999 | }, 1000 | "a-.-G-I-i-o-mc-l" : { 1001 | "full": "Gnd/Structure/IM Facilities/Other/Mobile Center/Law Enforcement", 1002 | "desc": "Law Enforcement", 1003 | }, 1004 | "a-.-G-I-i-o-mes" : { 1005 | "full": "Gnd/Structure/IM Facilities/Other/Message Center", 1006 | "desc": "Message Center", 1007 | }, 1008 | "a-.-G-I-i-o-mob" : { 1009 | "full": "Gnd/Structure/IM Facilities/Other/Mobilization Center", 1010 | "desc": "Mobilization Center", 1011 | }, 1012 | "a-.-G-I-i-o-mob-ems" : { 1013 | "full": "Gnd/Structure/IM Facilities/Other/Mobilization Center/EMS", 1014 | "desc": "EMS", 1015 | }, 1016 | "a-.-G-I-i-o-mob-es" : { 1017 | "full": "Gnd/Structure/IM Facilities/Other/Mobilization Center/Transit", 1018 | "desc": "Transit", 1019 | }, 1020 | "a-.-G-I-i-o-mob-f" : { 1021 | "full": "Gnd/Structure/IM Facilities/Other/Mobilization Center/Fire", 1022 | "desc": "Fire", 1023 | }, 1024 | "a-.-G-I-i-o-mob-hwy" : { 1025 | "full": "Gnd/Structure/IM Facilities/Other/Mobilization Center/Highway", 1026 | "desc": "Highway", 1027 | }, 1028 | "a-.-G-I-i-o-mob-mda" : { 1029 | "full": "Gnd/Structure/IM Facilities/Other/Mobilization Center/Media", 1030 | "desc": "Media", 1031 | }, 1032 | "a-.-G-I-i-o-mob-pl" : { 1033 | "full": "Gnd/Structure/IM Facilities/Other/Mobilization Center/Police Local", 1034 | "desc": "Ploce Local", 1035 | }, 1036 | "a-.-G-I-i-o-mob-ps" : { 1037 | "full": "Gnd/Structure/IM Facilities/Other/Mobilization Center/Police Station", 1038 | "desc": "Police Station", 1039 | }, 1040 | "a-.-G-I-i-o-mob-tow" : { 1041 | "full": "Gnd/Structure/IM Facilities/Other/Mobilization Center/Tow", 1042 | "desc": "Tow", 1043 | }, 1044 | "a-.-G-I-i-o-ps" : { 1045 | "full": "Gnd/Structure/IM Facilities/Other/Public Safety", 1046 | "desc": "Public Safety", 1047 | }, 1048 | "a-.-G-I-i-o-rl" : { 1049 | "full": "Gnd/Structure/IM Facilities/Other/Reporting Locations", 1050 | "desc": "Reporting Locations", 1051 | }, 1052 | "a-.-G-I-i-o-sa" : { 1053 | "full": "Gnd/Structure/IM Facilities/Other/Staging Area", 1054 | "desc": "Staging Area", 1055 | }, 1056 | "a-.-G-I-i-o-sa-ems" : { 1057 | "full": "Gnd/Structure/IM Facilities/Other/Staging Area/EMS", 1058 | "desc": "EMS", 1059 | }, 1060 | "a-.-G-I-i-o-sa-f" : { 1061 | "full": "Gnd/Structure/IM Facilities/Other/Staging Area/Fire", 1062 | "desc": "Fire", 1063 | }, 1064 | "a-.-G-I-i-o-sa-hwy" : { 1065 | "full": "Gnd/Structure/IM Facilities/Other/Staging Area/Highway", 1066 | "desc": "Highway", 1067 | }, 1068 | "a-.-G-I-i-o-sa-mda" : { 1069 | "full": "Gnd/Structure/IM Facilities/Other/Staging Area/Media", 1070 | "desc": "Media", 1071 | }, 1072 | "a-.-G-I-i-o-sa-pl" : { 1073 | "full": "Gnd/Structure/IM Facilities/Other/Staging Area/Police Local", 1074 | "desc": "Police Local", 1075 | }, 1076 | "a-.-G-I-i-o-sa-ps" : { 1077 | "full": "Gnd/Structure/IM Facilities/Other/Staging Area/Police Station", 1078 | "desc": "Police Station", 1079 | }, 1080 | "a-.-G-I-i-o-sa-tow" : { 1081 | "full": "Gnd/Structure/IM Facilities/Other/Staging Area/Tow", 1082 | "desc": "Tow", 1083 | }, 1084 | "a-.-G-I-i-o-sa-ts" : { 1085 | "full": "Gnd/Structure/IM Facilities/Other/Staging Area/Transit", 1086 | "desc": "Transit", 1087 | }, 1088 | "a-.-G-I-i-o-sc" : { 1089 | "full": "Gnd/Structure/IM Facilities/Other/Security Checkpoint", 1090 | "desc": "Security Checkpoint", 1091 | }, 1092 | "a-.-G-I-i-o-seg" : { 1093 | "full": "Gnd/Structure/IM Facilities/Other/Segment", 1094 | "desc": "Segment", 1095 | }, 1096 | "a-.-G-I-i-o-t" : { 1097 | "full": "Gnd/Structure/IM Facilities/Other/Transportation", 1098 | "desc": "Transportation", 1099 | }, 1100 | "a-.-G-I-i-o-t-im" : { 1101 | "full": "Gnd/Structure/IM Facilities/Other/Transportation/Transit Incident Management Center", 1102 | "desc": "Transit Incident Management Center", 1103 | }, 1104 | "a-.-G-I-i-o-t-tc" : { 1105 | "full": "Gnd/Structure/IM Facilities/Other/Transportation/Transit Management Center", 1106 | "desc": "Transit Management Center", 1107 | }, 1108 | "a-.-G-I-i-o-t-td" : { 1109 | "full": "Gnd/Structure/IM Facilities/Other/Transportation/Traffic Inc Service Patrol Dispatch", 1110 | "desc": "Traffic Inc Service Patrol Dispatch", 1111 | }, 1112 | "a-.-G-I-i-o-t-tm" : { 1113 | "full": "Gnd/Structure/IM Facilities/Other/Transportation/Traffic Management Center", 1114 | "desc": "Traffic Management Center", 1115 | }, 1116 | "a-.-G-I-i-o-tmp" : { 1117 | "full": "Gnd/Structure/IM Facilities/Other/Temp", 1118 | "desc": "Temporary", 1119 | }, 1120 | "a-.-G-I-i-o-tmp-f" : { 1121 | "full": "Gnd/Structure/IM Facilities/Other/Temp/Fire", 1122 | "desc": "Fire", 1123 | }, 1124 | "a-.-G-I-i-o-tmp-h" : { 1125 | "full": "Gnd/Structure/IM Facilities/Other/Temp/Medical", 1126 | "desc": "Medical", 1127 | }, 1128 | "a-.-G-I-i-o-tmp-l" : { 1129 | "full": "Gnd/Structure/IM Facilities/Other/Temp/Law Enforcement", 1130 | "desc": "Law Enforcement", 1131 | }, 1132 | "a-.-G-I-i-p" : { 1133 | "full": "Gnd/Structure/IM Facilities/Public Works", 1134 | "desc": "Public Works", 1135 | }, 1136 | "a-.-G-I-M" : { 1137 | "full": "Gnd/Structure/Mil/Military Materiel Facility", 1138 | "desc": "MILITARY MATERIEL FACILITY", 1139 | }, 1140 | "a-.-G-I-M-A" : { 1141 | "full": "Gnd/Structure/Mil/Aircraft Production", 1142 | "desc": "AIRCRAFT PRODUCTION/ASSEMBLY", 1143 | }, 1144 | "a-.-G-I-M-C" : { 1145 | "full": "Gnd/Structure/Mil/NBC Warfare Production", 1146 | "desc": "CHEMICAL/BIOLOGICAL WARFARE PRODUCTION", 1147 | }, 1148 | "a-.-G-I-M-E" : { 1149 | "full": "Gnd/Structure/Mil/Ammunition Production", 1150 | "desc": "AMMUNITION AND EXPLOSIVES PRODUCTION", 1151 | }, 1152 | "a-.-G-I-M-F" : { 1153 | "full": "Gnd/Structure/Mil/Nuclear Energy", 1154 | "desc": "NUCLEAR ENERGY", 1155 | }, 1156 | "a-.-G-I-M-F-A" : { 1157 | "full": "Gnd/Structure/Mil/Atomic Energy Reactor", 1158 | "desc": "ATOMIC ENERGY REACTOR", 1159 | }, 1160 | "a-.-G-I-M-F-P" : { 1161 | "full": "Gnd/Structure/Mil/Nuclear Material Production", 1162 | "desc": "NUCLEAR MATERIAL PRODUCTION", 1163 | }, 1164 | "a-.-G-I-M-F-P-W" : { 1165 | "full": "Gnd/Structure/Mil/Nuclear/Weapons Grade", 1166 | "desc": "WEAPONS GRADE", 1167 | }, 1168 | "a-.-G-I-M-F-S" : { 1169 | "full": "Gnd/Structure/Mil/Nuclear Material Storage", 1170 | "desc": "NUCLEAR MATERIAL STORAGE", 1171 | }, 1172 | "a-.-G-I-M-G" : { 1173 | "full": "Gnd/Structure/Mil/Armament Production", 1174 | "desc": "ARMAMENT PRODUCTION", 1175 | }, 1176 | "a-.-G-I-M-M" : { 1177 | "full": "Gnd/Structure/Mil/Missile+Space System Production", 1178 | "desc": "MISSILE/SPACE SYSTEM PRODUCTION", 1179 | }, 1180 | "a-.-G-I-M-N" : { 1181 | "full": "Gnd/Structure/Mil/Engineering Equipment Production", 1182 | "desc": "ENGINEERING EQUIPMENT PRODUCTION", 1183 | }, 1184 | "a-.-G-I-M-N-B" : { 1185 | "full": "Gnd/Structure/Mil/Bridge", 1186 | "desc": "BRIDGE", 1187 | }, 1188 | "a-.-G-I-M-N-B-l" : { 1189 | "full": "Gnd/Structure/Mil/Bridge/Large", 1190 | "desc": "Bridge (Large)", 1191 | }, 1192 | "a-.-G-I-M-N-B-m" : { 1193 | "full": "Gnd/Structure/Mil/Bridge/Med", 1194 | "desc": "Bridge (Med)", 1195 | }, 1196 | "a-.-G-I-M-N-B-s" : { 1197 | "full": "Gnd/Structure/Mil/Bridge/Small", 1198 | "desc": "Bridge (Small)", 1199 | }, 1200 | "a-.-G-I-M-N-c" : { 1201 | "full": "Gnd/Structure/Mil/Canal", 1202 | "desc": "Canal", 1203 | }, 1204 | "a-.-G-I-M-S" : { 1205 | "full": "Gnd/Structure/Mil/Ship Construction", 1206 | "desc": "SHIP CONSTRUCTION", 1207 | }, 1208 | "a-.-G-I-M-V" : { 1209 | "full": "Gnd/Structure/Mil/Military Vehicle Production", 1210 | "desc": "MILITARY VEHICLE PRODUCTION", 1211 | }, 1212 | "a-.-G-I-P" : { 1213 | "full": "Gnd/Structure/Processing Facility", 1214 | "desc": "PROCESSING FACILITY", 1215 | }, 1216 | "a-.-G-I-P-D" : { 1217 | "full": "Gnd/Structure/Decon", 1218 | "desc": "DECON", 1219 | }, 1220 | "a-.-G-I-R" : { 1221 | "full": "Gnd/Structure/Raw Material Production/Storage", 1222 | "desc": "RAW MATERIAL PRODUCTION/STORAGE", 1223 | }, 1224 | "a-.-G-I-R-M" : { 1225 | "full": "Gnd/Structure/Mine", 1226 | "desc": "MINE", 1227 | }, 1228 | "a-.-G-I-R-N" : { 1229 | "full": "Gnd/Structure/NBC", 1230 | "desc": "NBC", 1231 | }, 1232 | "a-.-G-I-R-N-B" : { 1233 | "full": "Gnd/Structure/Biological", 1234 | "desc": "BIOLOGICAL", 1235 | }, 1236 | "a-.-G-I-R-N-C" : { 1237 | "full": "Gnd/Structure/Chemical", 1238 | "desc": "CHEMICAL", 1239 | }, 1240 | "a-.-G-I-R-N-N" : { 1241 | "full": "Gnd/Structure/Nuclear", 1242 | "desc": "NUCLEAR", 1243 | }, 1244 | "a-.-G-I-R-P" : { 1245 | "full": "Gnd/Structure/PETROLEUM/GAS/OIL", 1246 | "desc": "PETROLEUM/GAS/OIL", 1247 | }, 1248 | "a-.-G-I-R-P-r" : { 1249 | "full": "Gnd/Structure/PETROLEUM/GAS/OIL/Refinery", 1250 | "desc": "Refinery", 1251 | }, 1252 | "a-.-G-I-T" : { 1253 | "full": "Gnd/Structure/Transport Facility", 1254 | "desc": "TRANSPORT FACILITY", 1255 | }, 1256 | "a-.-G-I-T-a" : { 1257 | "full": "Gnd/Structure/Transport Facility/Airport", 1258 | "desc": "Airport", 1259 | }, 1260 | "a-.-G-I-T-hb" : { 1261 | "full": "Gnd/Structure/Transport Facility/Helibase", 1262 | "desc": "Helibase", 1263 | }, 1264 | "a-.-G-I-T-hs" : { 1265 | "full": "Gnd/Structure/Transport Facility/Helispot", 1266 | "desc": "Helispot", 1267 | }, 1268 | "a-.-G-I-T-l" : { 1269 | "full": "Gnd/Structure/Transport Facility/Land Port", 1270 | "desc": "Land Port", 1271 | }, 1272 | "a-.-G-I-T-pg" : { 1273 | "full": "Gnd/Structure/Transport Facility/Parking Garage", 1274 | "desc": "Parking Garage", 1275 | }, 1276 | "a-.-G-I-T-r" : { 1277 | "full": "Gnd/Structure/Transport Facility/Railroad", 1278 | "desc": "Railroad", 1279 | }, 1280 | "a-.-G-I-T-s" : { 1281 | "full": "Gnd/Structure/Transport Facility/Seaport", 1282 | "desc": "Seaport", 1283 | }, 1284 | "a-.-G-I-U" : { 1285 | "full": "Gnd/Structure/Utility/Service, Research, Utility Facility", 1286 | "desc": "SERVICE, RESEARCH, UTILITY FACILITY", 1287 | }, 1288 | "a-.-G-I-U-E" : { 1289 | "full": "Gnd/Structure/Utility/Electric Power", 1290 | "desc": "ELECTRIC POWER FACILITY", 1291 | }, 1292 | "a-.-G-I-U-E-c" : { 1293 | "full": "Gnd/Structure/Utility/Electric Power/Coal Power Plant", 1294 | "desc": "Coal Power Plant", 1295 | }, 1296 | "a-.-G-I-U-E-h" : { 1297 | "full": "Gnd/Structure/Utility/Electric Power/Hydroelectric Power Plant", 1298 | "desc": "Hydroelectric Power Plant", 1299 | }, 1300 | "a-.-G-I-U-E-o" : { 1301 | "full": "Gnd/Structure/Utility/Electric Power/Other Power", 1302 | "desc": "Other Power", 1303 | }, 1304 | "a-.-G-I-U-E-ps" : { 1305 | "full": "Gnd/Structure/Utility/Electric Power/Power Substation", 1306 | "desc": "Power Substation", 1307 | }, 1308 | "a-.-G-I-U-E-D" : { 1309 | "full": "Gnd/Structure/Utility/Dam", 1310 | "desc": "DAM", 1311 | }, 1312 | "a-.-G-I-U-E-F" : { 1313 | "full": "Gnd/Structure/Utility/Fossil Fuel", 1314 | "desc": "FOSSIL FUEL", 1315 | }, 1316 | "a-.-G-I-U-E-N" : { 1317 | "full": "Gnd/Structure/Utility/Nuclear Plant", 1318 | "desc": "NUCLEAR PLANT", 1319 | }, 1320 | "a-.-G-I-U-P" : { 1321 | "full": "Gnd/Structure/Utility/Public Water Services", 1322 | "desc": "PUBLIC WATER SERVICES", 1323 | }, 1324 | "a-.-G-I-U-R" : { 1325 | "full": "Gnd/Structure/Utility/Technological Research", 1326 | "desc": "TECHNOLOGICAL RESEARCH FACILITY", 1327 | }, 1328 | "a-.-G-I-U-T" : { 1329 | "full": "Gnd/Structure/Utility/Telecommunications", 1330 | "desc": "TELECOMMUNICATIONS FACILITY", 1331 | }, 1332 | "a-.-G-I-U-T-com" : { 1333 | "full": "Gnd/Structure/Utility/Telecommunications/Communications", 1334 | "desc": "Communications", 1335 | }, 1336 | "a-.-G-I-U-T-com-af" : { 1337 | "full": "Gnd/Structure/Utility/Telecommunications/Communications/Antenna Farm", 1338 | "desc": "Antenna Farm", 1339 | }, 1340 | "a-.-G-I-U-T-com-sat" : { 1341 | "full": "Gnd/Structure/Utility/Telecommunications/Communications/Satellite Communications", 1342 | "desc": "Satellite Communications", 1343 | }, 1344 | "a-.-G-I-U-T-com-tow" : { 1345 | "full": "Gnd/Structure/Utility/Telecommunications/Communications/Tower", 1346 | "desc": "Tower", 1347 | }, 1348 | "a-.-G-I-U-T-r" : { 1349 | "full": "Gnd/Structure/Utility/Telecommunications/Radio", 1350 | "desc": "Radio", 1351 | }, 1352 | "a-.-G-I-U-T-r-s" : { 1353 | "full": "Gnd/Structure/Utility/Telecommunications/Radio/Station", 1354 | "desc": "Station", 1355 | }, 1356 | "a-.-G-I-U-T-tp" : { 1357 | "full": "Gnd/Structure/Utility/Telecommunications/Telephone", 1358 | "desc": "Telephone", 1359 | }, 1360 | "a-.-G-I-U-T-tp-ts" : { 1361 | "full": "Gnd/Structure/Utility/Telecommunications/Telephone/Telephone Switching", 1362 | "desc": "Telephone Switching", 1363 | }, 1364 | "a-.-G-I-U-T-tv" : { 1365 | "full": "Gnd/Structure/Utility/Telecommunications/Television", 1366 | "desc": "Television", 1367 | }, 1368 | "a-.-G-I-U-T-tv-c" : { 1369 | "full": "Gnd/Structure/Utility/Telecommunications/Television/Cable", 1370 | "desc": "Cable", 1371 | }, 1372 | "a-.-G-I-U-T-tv-s" : { 1373 | "full": "Gnd/Structure/Utility/Telecommunications/Television/Station", 1374 | "desc": "Station", 1375 | }, 1376 | "a-.-G-I-X" : { 1377 | "full": "Gnd/Structure/Medical Facility", 1378 | "desc": "MEDICAL FACILITY", 1379 | }, 1380 | "a-.-G-I-X-H" : { 1381 | "full": "Gnd/Structure/Hospital", 1382 | "desc": "HOSPITAL", 1383 | }, 1384 | "a-.-G-I-X-hcf" : { 1385 | "full": "Gnd/Structure/Medical Facility/Hospital/Hospital Care Facility", 1386 | "desc": "Hospital Care Facility", 1387 | }, 1388 | "a-.-G-I-r" : { 1389 | "full": "Gnd/Structure/Road", 1390 | "desc": "Road", 1391 | }, 1392 | "a-.-G-I-r-h" : { 1393 | "full": "Gnd/Structure/Road/Highway", 1394 | "desc": "Road (Highway)", 1395 | }, 1396 | "a-.-G-I-r-i" : { 1397 | "full": "Gnd/Structure/Road/Improved", 1398 | "desc": "Road (Improved)", 1399 | }, 1400 | "a-.-G-I-r-ra" : { 1401 | "full": "Gnd/Structure/Road/Rest Area", 1402 | "desc": "Rest Area", 1403 | }, 1404 | "a-.-G-I-r-u" : { 1405 | "full": "Gnd/Structure/Road/Unimproved", 1406 | "desc": "Road (Un-improved)", 1407 | }, 1408 | "a-.-G-U" : { 1409 | "full": "Gnd/Unit", 1410 | "desc": "UNIT", 1411 | }, 1412 | "a-.-G-U-C" : { 1413 | "full": "Gnd/Combat", 1414 | "desc": "COMBAT", 1415 | }, 1416 | "a-.-G-U-C-A" : { 1417 | "full": "Gnd/Combat/ARMOR", 1418 | "desc": "ARMOR", 1419 | }, 1420 | "a-.-G-U-C-A-A" : { 1421 | "full": "Gnd/Combat/Armor/ANTI ARMOR", 1422 | "desc": "ANTI ARMOR", 1423 | }, 1424 | "a-.-G-U-C-A-A-A" : { 1425 | "full": "Gnd/Combat/Armor/ANTI ARMOR ARMORED", 1426 | "desc": "ANTI ARMOR ARMORED", 1427 | }, 1428 | "a-.-G-U-C-A-A-A-S" : { 1429 | "full": "Gnd/Combat/Armor/ANTI ARMOR ARMORED AIR ASSAULT", 1430 | "desc": "ANTI ARMOR ARMORED AIR ASSAULT", 1431 | }, 1432 | "a-.-G-U-C-A-A-A-T" : { 1433 | "full": "Gnd/Combat/Armor/ANTI ARMOR ARMORED TRACKED", 1434 | "desc": "ANTI ARMOR ARMORED TRACKED", 1435 | }, 1436 | "a-.-G-U-C-A-A-A-W" : { 1437 | "full": "Gnd/Combat/Armor/ANTI ARMOR ARMORED WHEELED", 1438 | "desc": "ANTI ARMOR ARMORED WHEELED", 1439 | }, 1440 | "a-.-G-U-C-A-A-C" : { 1441 | "full": "Gnd/Combat/Armor/ANTI ARMOR ARCTIC", 1442 | "desc": "ANTI ARMOR ARCTIC", 1443 | }, 1444 | "a-.-G-U-C-A-A-D" : { 1445 | "full": "Gnd/Combat/Armor/ANTI ARMOR DISMOUNTED", 1446 | "desc": "ANTI ARMOR DISMOUNTED", 1447 | }, 1448 | "a-.-G-U-C-A-A-L" : { 1449 | "full": "Gnd/Combat/Armor/ANTI ARMOR LIGHT", 1450 | "desc": "ANTI ARMOR LIGHT", 1451 | }, 1452 | "a-.-G-U-C-A-A-M" : { 1453 | "full": "Gnd/Combat/Armor/ANTI ARMOR AIRBORNE", 1454 | "desc": "ANTI ARMOR AIRBORNE", 1455 | }, 1456 | "a-.-G-U-C-A-A-O" : { 1457 | "full": "Gnd/Combat/Armor/ANTI ARMOR MOTORIZED", 1458 | "desc": "ANTI ARMOR MOTORIZED", 1459 | }, 1460 | "a-.-G-U-C-A-A-O-S" : { 1461 | "full": "Gnd/Combat/Armor/ANTI ARMOR MOTORIZED AIR ASSAULT", 1462 | "desc": "ANTI ARMOR MOTORIZED AIR ASSAULT", 1463 | }, 1464 | "a-.-G-U-C-A-A-S" : { 1465 | "full": "Gnd/Combat/Armor/ANTI ARMOR AIR ASSAULT", 1466 | "desc": "ANTI ARMOR AIR ASSAULT", 1467 | }, 1468 | "a-.-G-U-C-A-A-U" : { 1469 | "full": "Gnd/Combat/Armor/ANTI ARMOR MOUNTAIN", 1470 | "desc": "ANTI ARMOR MOUNTAIN", 1471 | }, 1472 | "a-.-G-U-C-A-T" : { 1473 | "full": "Gnd/Combat/Armor/ARMOR TRACK", 1474 | "desc": "ARMOR TRACK", 1475 | }, 1476 | "a-.-G-U-C-A-T-A" : { 1477 | "full": "Gnd/Combat/Armor/ARMOR TRACK AIRBORNE", 1478 | "desc": "ARMOR TRACK AIRBORNE", 1479 | }, 1480 | "a-.-G-U-C-A-T-H" : { 1481 | "full": "Gnd/Combat/Armor/ARMOR TRACK, HEAVY", 1482 | "desc": "ARMOR TRACK, HEAVY", 1483 | }, 1484 | "a-.-G-U-C-A-T-L" : { 1485 | "full": "Gnd/Combat/Armor/ARMOR TRACK, LIGHT", 1486 | "desc": "ARMOR TRACK, LIGHT", 1487 | }, 1488 | "a-.-G-U-C-A-T-M" : { 1489 | "full": "Gnd/Combat/Armor/ARMOR TRACK, MEDIUM", 1490 | "desc": "ARMOR TRACK, MEDIUM", 1491 | }, 1492 | "a-.-G-U-C-A-T-R" : { 1493 | "full": "Gnd/Combat/Armor/ARMOR TRACK, RECOVERY", 1494 | "desc": "ARMOR TRACK, RECOVERY", 1495 | }, 1496 | "a-.-G-U-C-A-T-W" : { 1497 | "full": "Gnd/Combat/Armor/ARMOR TRACK AMPHIBIOUS", 1498 | "desc": "ARMOR TRACK AMPHIBIOUS", 1499 | }, 1500 | "a-.-G-U-C-A-T-W-R" : { 1501 | "full": "Gnd/Combat/Armor/ARMOR TRACK AMPHIBIOUS RECOVERY", 1502 | "desc": "ARMOR TRACK AMPHIBIOUS RECOVERY", 1503 | }, 1504 | "a-.-G-U-C-A-W" : { 1505 | "full": "Gnd/Combat/Armor/ARMOR, WHEELED", 1506 | "desc": "ARMOR, WHEELED", 1507 | }, 1508 | "a-.-G-U-C-A-W-A" : { 1509 | "full": "Gnd/Combat/Armor/ARMOR, WHEELED AIRBORNE", 1510 | "desc": "ARMOR, WHEELED AIRBORNE", 1511 | }, 1512 | "a-.-G-U-C-A-W-H" : { 1513 | "full": "Gnd/Combat/Armor/ARMOR, WHEELED HEAVY", 1514 | "desc": "ARMOR, WHEELED HEAVY", 1515 | }, 1516 | "a-.-G-U-C-A-W-L" : { 1517 | "full": "Gnd/Combat/Armor/ARMOR, WHEELED LIGHT", 1518 | "desc": "ARMOR, WHEELED LIGHT", 1519 | }, 1520 | "a-.-G-U-C-A-W-M" : { 1521 | "full": "Gnd/Combat/Armor/ARMOR, WHEELED MEDIUM", 1522 | "desc": "ARMOR, WHEELED MEDIUM", 1523 | }, 1524 | "a-.-G-U-C-A-W-R" : { 1525 | "full": "Gnd/Combat/Armor/ARMOR, WHEELED RECOVERY", 1526 | "desc": "ARMOR, WHEELED RECOVERY", 1527 | }, 1528 | "a-.-G-U-C-A-W-S" : { 1529 | "full": "Gnd/Combat/Armor/ARMOR, WHEELED AIR ASSAULT", 1530 | "desc": "ARMOR, WHEELED AIR ASSAULT", 1531 | }, 1532 | "a-.-G-U-C-A-W-W" : { 1533 | "full": "Gnd/Combat/Armor/ARMOR, WHEELED AMPHIBIOUS", 1534 | "desc": "ARMOR, WHEELED AMPHIBIOUS", 1535 | }, 1536 | "a-.-G-U-C-A-W-W-R" : { 1537 | "full": "Gnd/Combat/Armor/ARMOR, WHEELED AMPHIBIOUS RECOVERY", 1538 | "desc": "ARMOR, WHEELED AMPHIBIOUS RECOVERY", 1539 | }, 1540 | "a-.-G-U-C-D" : { 1541 | "full": "Gnd/Combat/Defense/AIR DEFENSE", 1542 | "desc": "AIR DEFENSE", 1543 | }, 1544 | "a-.-G-U-C-D-C" : { 1545 | "full": "Gnd/Combat/Defense/COMPOSITE", 1546 | "desc": "COMPOSITE", 1547 | }, 1548 | "a-.-G-U-C-D-G" : { 1549 | "full": "Gnd/Combat/Defense/GUN UNIT", 1550 | "desc": "GUN UNIT", 1551 | }, 1552 | "a-.-G-U-C-D-H" : { 1553 | "full": "Gnd/Combat/Defense/H/MAD", 1554 | "desc": "H/MAD", 1555 | }, 1556 | "a-.-G-U-C-D-H-H" : { 1557 | "full": "Gnd/Combat/Defense/HAWK", 1558 | "desc": "HAWK", 1559 | }, 1560 | "a-.-G-U-C-D-H-P" : { 1561 | "full": "Gnd/Combat/Defense/PATRIOT", 1562 | "desc": "PATRIOT", 1563 | }, 1564 | "a-.-G-U-C-D-M" : { 1565 | "full": "Gnd/Combat/Defense/AIR DEFENSE MISSILE", 1566 | "desc": "AIR DEFENSE MISSILE", 1567 | }, 1568 | "a-.-G-U-C-D-M-H" : { 1569 | "full": "Gnd/Combat/Defense/AIR DEFENSE MISSILE HEAVY", 1570 | "desc": "AIR DEFENSE MISSILE HEAVY", 1571 | }, 1572 | "a-.-G-U-C-D-M-L" : { 1573 | "full": "Gnd/Combat/Defense/AIR DEFENSE MISSILE LIGHT", 1574 | "desc": "AIR DEFENSE MISSILE LIGHT", 1575 | }, 1576 | "a-.-G-U-C-D-M-L-A" : { 1577 | "full": "Gnd/Combat/Defense/AIR DEFENSE MISSILE MOTORIZED (AVENGER)", 1578 | "desc": "AIR DEFENSE MISSILE MOTORIZED (AVENGER)", 1579 | }, 1580 | "a-.-G-U-C-D-M-M" : { 1581 | "full": "Gnd/Combat/Defense/AIR DEFENSE MISSILE MEDIUM", 1582 | "desc": "AIR DEFENSE MISSILE MEDIUM", 1583 | }, 1584 | "a-.-G-U-C-D-O" : { 1585 | "full": "Gnd/Combat/Defense/THEATER MISSILE DEFENSE UNIT", 1586 | "desc": "THEATER MISSILE DEFENSE UNIT", 1587 | }, 1588 | "a-.-G-U-C-D-S" : { 1589 | "full": "Gnd/Combat/Defense/SHORT RANGE", 1590 | "desc": "SHORT RANGE", 1591 | }, 1592 | "a-.-G-U-C-D-S-S" : { 1593 | "full": "Gnd/Combat/Defense/STINGER", 1594 | "desc": "STINGER", 1595 | }, 1596 | "a-.-G-U-C-D-S-V" : { 1597 | "full": "Gnd/Combat/Defense/VULCAN", 1598 | "desc": "VULCAN", 1599 | }, 1600 | "a-.-G-U-C-D-T" : { 1601 | "full": "Gnd/Combat/Defense/TARGETING UNIT", 1602 | "desc": "TARGETING UNIT", 1603 | }, 1604 | "a-.-G-U-C-E" : { 1605 | "full": "Gnd/Combat/Engineer/ENGINEER", 1606 | "desc": "ENGINEER", 1607 | }, 1608 | "a-.-G-U-C-E-C" : { 1609 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT", 1610 | "desc": "ENGINEER COMBAT", 1611 | }, 1612 | "a-.-G-U-C-E-C-A" : { 1613 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT AIRBORNE", 1614 | "desc": "ENGINEER COMBAT AIRBORNE", 1615 | }, 1616 | "a-.-G-U-C-E-C-C" : { 1617 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT ARCTIC", 1618 | "desc": "ENGINEER COMBAT ARCTIC", 1619 | }, 1620 | "a-.-G-U-C-E-C-H" : { 1621 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT HEAVY", 1622 | "desc": "ENGINEER COMBAT HEAVY", 1623 | }, 1624 | "a-.-G-U-C-E-C-L" : { 1625 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT LIGHT (SAPPER)", 1626 | "desc": "ENGINEER COMBAT LIGHT (SAPPER)", 1627 | }, 1628 | "a-.-G-U-C-E-C-M" : { 1629 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT MEDIUM", 1630 | "desc": "ENGINEER COMBAT MEDIUM", 1631 | }, 1632 | "a-.-G-U-C-E-C-O" : { 1633 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT MOUNTAIN", 1634 | "desc": "ENGINEER COMBAT MOUNTAIN", 1635 | }, 1636 | "a-.-G-U-C-E-C-R" : { 1637 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT RECON", 1638 | "desc": "ENGINEER COMBAT RECON", 1639 | }, 1640 | "a-.-G-U-C-E-C-S" : { 1641 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT AIR ASSAULT", 1642 | "desc": "ENGINEER COMBAT AIR ASSAULT", 1643 | }, 1644 | "a-.-G-U-C-E-C-T" : { 1645 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT MECHANIZED (TRACK)", 1646 | "desc": "ENGINEER COMBAT MECHANIZED (TRACK)", 1647 | }, 1648 | "a-.-G-U-C-E-C-W" : { 1649 | "full": "Gnd/Combat/Engineer/ENGINEER COMBAT MOTORIZED", 1650 | "desc": "ENGINEER COMBAT MOTORIZED", 1651 | }, 1652 | "a-.-G-U-C-E-N" : { 1653 | "full": "Gnd/Combat/Engineer/ENGINEER CONSTRUCTION", 1654 | "desc": "ENGINEER CONSTRUCTION", 1655 | }, 1656 | "a-.-G-U-C-E-N-N" : { 1657 | "full": "Gnd/Combat/Engineer/ENGINEER NAVAL CONSTRUCTION", 1658 | "desc": "ENGINEER NAVAL CONSTRUCTION", 1659 | }, 1660 | "a-.-G-U-C-F" : { 1661 | "full": "Gnd/Combat/Artillery (Fixed)", 1662 | "desc": "Artillery (Fixed)", 1663 | }, 1664 | "a-.-G-U-C-F-H" : { 1665 | "full": "Gnd/Combat/HOWITZER/GUN", 1666 | "desc": "HOWITZER/GUN", 1667 | }, 1668 | "a-.-G-U-C-F-H-A" : { 1669 | "full": "Gnd/Combat/AIRBORNE", 1670 | "desc": "AIRBORNE", 1671 | }, 1672 | "a-.-G-U-C-F-H-C" : { 1673 | "full": "Gnd/Combat/ARCTIC", 1674 | "desc": "ARCTIC", 1675 | }, 1676 | "a-.-G-U-C-F-H-E" : { 1677 | "full": "Gnd/Combat/Artillery (Mobile)", 1678 | "desc": "Artillery (Mobile)", 1679 | }, 1680 | "a-.-G-U-C-F-H-H" : { 1681 | "full": "Gnd/Combat/HEAVY", 1682 | "desc": "HEAVY", 1683 | }, 1684 | "a-.-G-U-C-F-H-L" : { 1685 | "full": "Gnd/Combat/LIGHT", 1686 | "desc": "LIGHT", 1687 | }, 1688 | "a-.-G-U-C-F-H-M" : { 1689 | "full": "Gnd/Combat/MEDIUM", 1690 | "desc": "MEDIUM", 1691 | }, 1692 | "a-.-G-U-C-F-H-O" : { 1693 | "full": "Gnd/Combat/MOUNTAIN", 1694 | "desc": "MOUNTAIN", 1695 | }, 1696 | "a-.-G-U-C-F-H-S" : { 1697 | "full": "Gnd/Combat/AIR ASSAULT", 1698 | "desc": "AIR ASSAULT", 1699 | }, 1700 | "a-.-G-U-C-F-H-X" : { 1701 | "full": "Gnd/Combat/AMPHIBIOUS", 1702 | "desc": "AMPHIBIOUS", 1703 | }, 1704 | "a-.-G-U-C-F-M" : { 1705 | "full": "Gnd/Combat/MORTAR", 1706 | "desc": "MORTAR", 1707 | }, 1708 | "a-.-G-U-C-F-M-L" : { 1709 | "full": "Gnd/Combat/AMPHIBIOUS MORTAR", 1710 | "desc": "AMPHIBIOUS MORTAR", 1711 | }, 1712 | "a-.-G-U-C-F-M-S" : { 1713 | "full": "Gnd/Combat/SELF PROPELLED (SP) TRACKED MORTAR", 1714 | "desc": "SELF PROPELLED (SP) TRACKED MORTAR", 1715 | }, 1716 | "a-.-G-U-C-F-M-T" : { 1717 | "full": "Gnd/Combat/TOWED MORTAR", 1718 | "desc": "TOWED MORTAR", 1719 | }, 1720 | "a-.-G-U-C-F-M-T-A" : { 1721 | "full": "Gnd/Combat/TOWED AIRBORNE MORTAR", 1722 | "desc": "TOWED AIRBORNE MORTAR", 1723 | }, 1724 | "a-.-G-U-C-F-M-T-C" : { 1725 | "full": "Gnd/Combat/TOWED ARCTIC MORTAR", 1726 | "desc": "TOWED ARCTIC MORTAR", 1727 | }, 1728 | "a-.-G-U-C-F-M-T-O" : { 1729 | "full": "Gnd/Combat/TOWED MOUNTAIN MORTAR", 1730 | "desc": "TOWED MOUNTAIN MORTAR", 1731 | }, 1732 | "a-.-G-U-C-F-M-T-S" : { 1733 | "full": "Gnd/Combat/TOWED AIR ASSAULT MORTAR", 1734 | "desc": "TOWED AIR ASSAULT MORTAR", 1735 | }, 1736 | "a-.-G-U-C-F-M-W" : { 1737 | "full": "Gnd/Combat/SP WHEELED MORTAR", 1738 | "desc": "SP WHEELED MORTAR", 1739 | }, 1740 | "a-.-G-U-C-F-O" : { 1741 | "full": "Gnd/Combat/METEOROLOGICAL", 1742 | "desc": "METEOROLOGICAL", 1743 | }, 1744 | "a-.-G-U-C-F-O-A" : { 1745 | "full": "Gnd/Combat/AIRBORNE METEOROLOGICAL", 1746 | "desc": "AIRBORNE METEOROLOGICAL", 1747 | }, 1748 | "a-.-G-U-C-F-O-L" : { 1749 | "full": "Gnd/Combat/LIGHT METEOROLOGICAL", 1750 | "desc": "LIGHT METEOROLOGICAL", 1751 | }, 1752 | "a-.-G-U-C-F-O-O" : { 1753 | "full": "Gnd/Combat/MOUNTAIN METEOROLOGICAL", 1754 | "desc": "MOUNTAIN METEOROLOGICAL", 1755 | }, 1756 | "a-.-G-U-C-F-O-S" : { 1757 | "full": "Gnd/Combat/AIR ASSAULT METEOROLOGICAL", 1758 | "desc": "AIR ASSAULT METEOROLOGICAL", 1759 | }, 1760 | "a-.-G-U-C-F-R" : { 1761 | "full": "Gnd/Combat/ROCKET", 1762 | "desc": "ROCKET", 1763 | }, 1764 | "a-.-G-U-C-F-R-M" : { 1765 | "full": "Gnd/Combat/Rockets (Fixed)", 1766 | "desc": "Rockets (Fixed)", 1767 | }, 1768 | "a-.-G-U-C-F-R-M-R" : { 1769 | "full": "Gnd/Combat/Rockets (Mobile)", 1770 | "desc": "Rockets (Mobile)", 1771 | }, 1772 | "a-.-G-U-C-F-R-M-S" : { 1773 | "full": "Gnd/Combat/MULTI ROCKET SELF PROPELLED", 1774 | "desc": "MULTI ROCKET SELF PROPELLED", 1775 | }, 1776 | "a-.-G-U-C-F-R-M-T" : { 1777 | "full": "Gnd/Combat/MULTI ROCKET TOWED", 1778 | "desc": "MULTI ROCKET TOWED", 1779 | }, 1780 | "a-.-G-U-C-F-R-S" : { 1781 | "full": "Gnd/Combat/SINGLE ROCKET LAUNCHER", 1782 | "desc": "SINGLE ROCKET LAUNCHER", 1783 | }, 1784 | "a-.-G-U-C-F-R-S-R" : { 1785 | "full": "Gnd/Combat/SINGLE ROCKET TRUCK", 1786 | "desc": "SINGLE ROCKET TRUCK", 1787 | }, 1788 | "a-.-G-U-C-F-R-S-S" : { 1789 | "full": "Gnd/Combat/SINGLE ROCKET SELF PROPELLED", 1790 | "desc": "SINGLE ROCKET SELF PROPELLED", 1791 | }, 1792 | "a-.-G-U-C-F-R-S-T" : { 1793 | "full": "Gnd/Combat/SINGLE ROCKET TOWED", 1794 | "desc": "SINGLE ROCKET TOWED", 1795 | }, 1796 | "a-.-G-U-C-F-S" : { 1797 | "full": "Gnd/Combat/ARTILLERY SURVEY", 1798 | "desc": "ARTILLERY SURVEY", 1799 | }, 1800 | "a-.-G-U-C-F-S-A" : { 1801 | "full": "Gnd/Combat/AIRBORNE", 1802 | "desc": "AIRBORNE", 1803 | }, 1804 | "a-.-G-U-C-F-S-L" : { 1805 | "full": "Gnd/Combat/LIGHT", 1806 | "desc": "LIGHT", 1807 | }, 1808 | "a-.-G-U-C-F-S-O" : { 1809 | "full": "Gnd/Combat/MOUNTAIN", 1810 | "desc": "MOUNTAIN", 1811 | }, 1812 | "a-.-G-U-C-F-S-S" : { 1813 | "full": "Gnd/Combat/AIR ASSAULT", 1814 | "desc": "AIR ASSAULT", 1815 | }, 1816 | "a-.-G-U-C-F-T" : { 1817 | "full": "Gnd/Combat/TARGET ACQUISITION", 1818 | "desc": "TARGET ACQUISITION", 1819 | }, 1820 | "a-.-G-U-C-F-T-A" : { 1821 | "full": "Gnd/Combat/ANGLICO", 1822 | "desc": "ANGLICO", 1823 | }, 1824 | "a-.-G-U-C-F-T-C" : { 1825 | "full": "Gnd/Combat/COLT/FIST", 1826 | "desc": "COLT/FIST", 1827 | }, 1828 | "a-.-G-U-C-F-T-C-D" : { 1829 | "full": "Gnd/Combat/DISMOUNTED COLT/FIST", 1830 | "desc": "DISMOUNTED COLT/FIST", 1831 | }, 1832 | "a-.-G-U-C-F-T-C-M" : { 1833 | "full": "Gnd/Combat/TRACKED COLT/FIST", 1834 | "desc": "TRACKED COLT/FIST", 1835 | }, 1836 | "a-.-G-U-C-F-T-F" : { 1837 | "full": "Gnd/Combat/FLASH (OPTICAL)", 1838 | "desc": "FLASH (OPTICAL)", 1839 | }, 1840 | "a-.-G-U-C-F-T-R" : { 1841 | "full": "Gnd/Combat/RADAR", 1842 | "desc": "RADAR", 1843 | }, 1844 | "a-.-G-U-C-F-T-S" : { 1845 | "full": "Gnd/Combat/SOUND", 1846 | "desc": "SOUND", 1847 | }, 1848 | "a-.-G-U-C-I" : { 1849 | "full": "Gnd/Combat/Infantry/Troops (Open)", 1850 | "desc": "Troops (Open)", 1851 | }, 1852 | "a-.-G-U-C-I-A" : { 1853 | "full": "Gnd/Combat/Infantry/Airborne", 1854 | "desc": "INFANTRY AIRBORNE", 1855 | }, 1856 | "a-.-G-U-C-I-C" : { 1857 | "full": "Gnd/Combat/Infantry/Arctic", 1858 | "desc": "INFANTRY ARCTIC", 1859 | }, 1860 | "a-.-G-U-C-I-I" : { 1861 | "full": "Gnd/Combat/Infantry/Fighting Vehicle", 1862 | "desc": "INFANTRY FIGHTING VEHICLE", 1863 | }, 1864 | "a-.-G-U-C-I-L" : { 1865 | "full": "Gnd/Combat/Infantry/Light", 1866 | "desc": "INFANTRY LIGHT", 1867 | }, 1868 | "a-.-G-U-C-I-M" : { 1869 | "full": "Gnd/Combat/Infantry/Motorized", 1870 | "desc": "INFANTRY MOTORIZED", 1871 | }, 1872 | "a-.-G-U-C-I-N" : { 1873 | "full": "Gnd/Combat/Infantry/Naval", 1874 | "desc": "INFANTRY NAVAL", 1875 | }, 1876 | "a-.-G-U-C-I-O" : { 1877 | "full": "Gnd/Combat/Infantry/Mountain", 1878 | "desc": "INFANTRY MOUNTAIN", 1879 | }, 1880 | "a-.-G-U-C-I-S" : { 1881 | "full": "Gnd/Combat/Infantry/Air Assault", 1882 | "desc": "INFANTRY AIR ASSAULT", 1883 | }, 1884 | "a-.-G-U-C-I-Z" : { 1885 | "full": "Gnd/Combat/Infantry/Mechanized", 1886 | "desc": "INFANTRY MECHANIZED", 1887 | }, 1888 | "a-.-G-U-C-I-d" : { 1889 | "full": "Gnd/Combat/Infantry/DugIn", 1890 | "desc": "Troops (DugIn)", 1891 | }, 1892 | "a-.-G-U-C-M" : { 1893 | "full": "Gnd/Combat/MISSILE (SURF SURF)", 1894 | "desc": "MISSILE (SURF SURF)", 1895 | }, 1896 | "a-.-G-U-C-M-S" : { 1897 | "full": "Gnd/Combat/MISSILE (SURF SURF) STRATEGIC", 1898 | "desc": "MISSILE (SURF SURF) STRATEGIC", 1899 | }, 1900 | "a-.-G-U-C-M-T" : { 1901 | "full": "Gnd/Combat/MISSILE (SURF SURF) TACTICAL", 1902 | "desc": "MISSILE (SURF SURF) TACTICAL", 1903 | }, 1904 | "a-.-G-U-C-R" : { 1905 | "full": "Gnd/Combat/Recon/", 1906 | "desc": "RECONNAISSANCE", 1907 | }, 1908 | "a-.-G-U-C-R-A" : { 1909 | "full": "Gnd/Combat/Recon/AIRBORNE", 1910 | "desc": "RECONNAISSANCE AIRBORNE", 1911 | }, 1912 | "a-.-G-U-C-R-C" : { 1913 | "full": "Gnd/Combat/Recon/ARCTIC", 1914 | "desc": "RECONNAISSANCE ARCTIC", 1915 | }, 1916 | "a-.-G-U-C-R-H" : { 1917 | "full": "Gnd/Combat/Recon/HORSE", 1918 | "desc": "RECONNAISSANCE HORSE", 1919 | }, 1920 | "a-.-G-U-C-R-L" : { 1921 | "full": "Gnd/Combat/Recon/LIGHT", 1922 | "desc": "RECONNAISSANCE LIGHT", 1923 | }, 1924 | "a-.-G-U-C-R-O" : { 1925 | "full": "Gnd/Combat/Recon/MOUNTAIN", 1926 | "desc": "RECONNAISSANCE MOUNTAIN", 1927 | }, 1928 | "a-.-G-U-C-R-R" : { 1929 | "full": "Gnd/Combat/Recon/MARINE", 1930 | "desc": "RECONNAISSANCE MARINE", 1931 | }, 1932 | "a-.-G-U-C-R-R-D" : { 1933 | "full": "Gnd/Combat/Recon/MARINE DIVISION", 1934 | "desc": "RECONNAISSANCE MARINE DIVISION", 1935 | }, 1936 | "a-.-G-U-C-R-R-F" : { 1937 | "full": "Gnd/Combat/Recon/MARINE FORCE", 1938 | "desc": "RECONNAISSANCE MARINE FORCE", 1939 | }, 1940 | "a-.-G-U-C-R-R-L" : { 1941 | "full": "Gnd/Combat/Recon/MARINE LIGHT ARMORED", 1942 | "desc": "RECONNAISSANCE MARINE LIGHT ARMORED", 1943 | }, 1944 | "a-.-G-U-C-R-S" : { 1945 | "full": "Gnd/Combat/Recon/AIR ASSAULT", 1946 | "desc": "RECONNAISSANCE AIR ASSAULT", 1947 | }, 1948 | "a-.-G-U-C-R-V" : { 1949 | "full": "Gnd/Combat/Recon/CAVALRY", 1950 | "desc": "RECONNAISSANCE CAVALRY", 1951 | }, 1952 | "a-.-G-U-C-R-V-A" : { 1953 | "full": "Gnd/Combat/Recon/CAVALRY ARMORED", 1954 | "desc": "RECONNAISSANCE CAVALRY ARMORED", 1955 | }, 1956 | "a-.-G-U-C-R-V-G" : { 1957 | "full": "Gnd/Combat/Recon/CAVALRY GROUND", 1958 | "desc": "RECONNAISSANCE CAVALRY GROUND", 1959 | }, 1960 | "a-.-G-U-C-R-V-M" : { 1961 | "full": "Gnd/Combat/Recon/CAVALRY MOTORIZED", 1962 | "desc": "RECONNAISSANCE CAVALRY MOTORIZED", 1963 | }, 1964 | "a-.-G-U-C-R-V-O" : { 1965 | "full": "Gnd/Combat/Recon/CAVALRY AIR", 1966 | "desc": "RECONNAISSANCE CAVALRY AIR", 1967 | }, 1968 | "a-.-G-U-C-R-X" : { 1969 | "full": "Gnd/Combat/Recon/LONG RANGE SURVEILLANCE", 1970 | "desc": "RECONNAISSANCE LONG RANGE SURVEILLANCE", 1971 | }, 1972 | "a-.-G-U-C-S" : { 1973 | "full": "Gnd/Combat/Security/INTERNAL SECURITY FORCES", 1974 | "desc": "INTERNAL SECURITY FORCES", 1975 | }, 1976 | "a-.-G-U-C-S-A" : { 1977 | "full": "Gnd/Combat/Security/AVIATION", 1978 | "desc": "AVIATION", 1979 | }, 1980 | "a-.-G-U-C-S-G" : { 1981 | "full": "Gnd/Combat/Security/GROUND", 1982 | "desc": "GROUND", 1983 | }, 1984 | "a-.-G-U-C-S-G-A" : { 1985 | "full": "Gnd/Combat/Security/MECHANIZED GROUND", 1986 | "desc": "MECHANIZED GROUND", 1987 | }, 1988 | "a-.-G-U-C-S-G-D" : { 1989 | "full": "Gnd/Combat/Security/DISMOUNTED GROUND", 1990 | "desc": "DISMOUNTED GROUND", 1991 | }, 1992 | "a-.-G-U-C-S-G-M" : { 1993 | "full": "Gnd/Combat/Security/MOTORIZED GROUND", 1994 | "desc": "MOTORIZED GROUND", 1995 | }, 1996 | "a-.-G-U-C-S-M" : { 1997 | "full": "Gnd/Combat/Security/WHEELED MECHANIZED", 1998 | "desc": "WHEELED MECHANIZED", 1999 | }, 2000 | "a-.-G-U-C-S-R" : { 2001 | "full": "Gnd/Combat/Security/Rail", 2002 | "desc": "Rail", 2003 | }, 2004 | "a-.-G-U-C-S-W" : { 2005 | "full": "Gnd/Combat/Security/RIVERINE", 2006 | "desc": "RIVERINE", 2007 | }, 2008 | "a-.-G-U-C-V" : { 2009 | "full": "Gnd/Combat/Aviation/AVIATION", 2010 | "desc": "AVIATION", 2011 | }, 2012 | "a-.-G-U-C-V-C" : { 2013 | "full": "Gnd/Combat/Aviation/COMPOSITE", 2014 | "desc": "COMPOSITE", 2015 | }, 2016 | "a-.-G-U-C-V-F" : { 2017 | "full": "Gnd/Combat/Aviation/FIXED WING", 2018 | "desc": "FIXED WING", 2019 | }, 2020 | "a-.-G-U-C-V-F-A" : { 2021 | "full": "Gnd/Combat/Aviation/ATTACK FIXED WING", 2022 | "desc": "ATTACK FIXED WING", 2023 | }, 2024 | "a-.-G-U-C-V-F-R" : { 2025 | "full": "Gnd/Combat/Aviation/RECON FIXED WING", 2026 | "desc": "RECON FIXED WING", 2027 | }, 2028 | "a-.-G-U-C-V-F-U" : { 2029 | "full": "Gnd/Combat/Aviation/UTILITY FIXED WING", 2030 | "desc": "UTILITY FIXED WING", 2031 | }, 2032 | "a-.-G-U-C-V-R" : { 2033 | "full": "Gnd/Combat/Aviation/ROTARY WING", 2034 | "desc": "ROTARY WING", 2035 | }, 2036 | "a-.-G-U-C-V-R-A" : { 2037 | "full": "Gnd/Combat/Aviation/ATTACK ROTARY WING", 2038 | "desc": "ATTACK ROTARY WING", 2039 | }, 2040 | "a-.-G-U-C-V-R-M" : { 2041 | "full": "Gnd/Combat/Aviation/MINE COUNTERMEASURE ROTARY WING", 2042 | "desc": "MINE COUNTERMEASURE ROTARY WING", 2043 | }, 2044 | "a-.-G-U-C-V-R-S" : { 2045 | "full": "Gnd/Combat/Aviation/SCOUT ROTARY WING", 2046 | "desc": "SCOUT ROTARY WING", 2047 | }, 2048 | "a-.-G-U-C-V-R-U" : { 2049 | "full": "Gnd/Combat/Aviation/UTILITY ROTARY WING", 2050 | "desc": "UTILITY ROTARY WING", 2051 | }, 2052 | "a-.-G-U-C-V-R-U-C" : { 2053 | "full": "Gnd/Combat/Aviation/C2 ROTARY WING", 2054 | "desc": "C2 ROTARY WING", 2055 | }, 2056 | "a-.-G-U-C-V-R-U-E" : { 2057 | "full": "Gnd/Combat/Aviation/MEDEVAC ROTARY WING", 2058 | "desc": "MEDEVAC ROTARY WING", 2059 | }, 2060 | "a-.-G-U-C-V-R-U-H" : { 2061 | "full": "Gnd/Combat/Aviation/HEAVY UTILITY ROTARY WING", 2062 | "desc": "HEAVY UTILITY ROTARY WING", 2063 | }, 2064 | "a-.-G-U-C-V-R-U-L" : { 2065 | "full": "Gnd/Combat/Aviation/LIGHT UTILITY ROTARY WING", 2066 | "desc": "LIGHT UTILITY ROTARY WING", 2067 | }, 2068 | "a-.-G-U-C-V-R-U-M" : { 2069 | "full": "Gnd/Combat/Aviation/MEDIUM UTILITY ROTARY WING", 2070 | "desc": "MEDIUM UTILITY ROTARY WING", 2071 | }, 2072 | "a-.-G-U-C-V-R-W" : { 2073 | "full": "Gnd/Combat/Aviation/ANTISUBMARINE WARFARE ROTARY WING", 2074 | "desc": "ANTISUBMARINE WARFARE ROTARY WING", 2075 | }, 2076 | "a-.-G-U-C-V-R-d" : { 2077 | "full": "Gnd/Combat/Aviation/Helo/Dual", 2078 | "desc": "Helo ground unit (Dual)", 2079 | }, 2080 | "a-.-G-U-C-V-R-s" : { 2081 | "full": "Gnd/Combat/Aviation/Helo/Single", 2082 | "desc": "Helo ground unit (Single)", 2083 | }, 2084 | "a-.-G-U-C-V-S" : { 2085 | "full": "Gnd/Combat/Aviation/SEARCH AND RESCUE", 2086 | "desc": "SEARCH AND RESCUE", 2087 | }, 2088 | "a-.-G-U-C-V-U" : { 2089 | "full": "Gnd/Combat/Aviation/UNMANNED AERIAL VEHICLE", 2090 | "desc": "UNMANNED AERIAL VEHICLE", 2091 | }, 2092 | "a-.-G-U-C-V-U-F" : { 2093 | "full": "Gnd/Combat/Aviation/UNMANNED AERIAL VEHICLE FIXED WING", 2094 | "desc": "UNMANNED AERIAL VEHICLE FIXED WING", 2095 | }, 2096 | "a-.-G-U-C-V-U-R" : { 2097 | "full": "Gnd/Combat/Aviation/UNMANNED AERIAL VEHICLE ROTARY WING", 2098 | "desc": "UNMANNED AERIAL VEHICLE ROTARY WING", 2099 | }, 2100 | "a-.-G-U-C-V-V" : { 2101 | "full": "Gnd/Combat/Aviation/VERTICAL/SHORT TAKEOFF AND LANDING", 2102 | "desc": "VERTICAL/SHORT TAKEOFF AND LANDING", 2103 | }, 2104 | "a-.-G-U-H" : { 2105 | "full": "Gnd/SPECIAL C2 HEADQUARTERS COMPONENT", 2106 | "desc": "SPECIAL C2 HEADQUARTERS COMPONENT", 2107 | }, 2108 | "a-.-G-U-S" : { 2109 | "full": "Gnd/COMBAT SERVICE SUPPORT", 2110 | "desc": "COMBAT SERVICE SUPPORT", 2111 | }, 2112 | "a-.-G-U-S-A" : { 2113 | "full": "Gnd/ADMINISTRATIVE (ADMIN)", 2114 | "desc": "ADMINISTRATIVE (ADMIN)", 2115 | }, 2116 | "a-.-G-U-S-A-C" : { 2117 | "full": "Gnd/ADMIN CORPS", 2118 | "desc": "ADMIN CORPS", 2119 | }, 2120 | "a-.-G-U-S-A-F" : { 2121 | "full": "Gnd/FINANCE", 2122 | "desc": "FINANCE", 2123 | }, 2124 | "a-.-G-U-S-A-F-C" : { 2125 | "full": "Gnd/FINANCE CORPS", 2126 | "desc": "FINANCE CORPS", 2127 | }, 2128 | "a-.-G-U-S-A-F-T" : { 2129 | "full": "Gnd/FINANCE THEATER", 2130 | "desc": "FINANCE THEATER", 2131 | }, 2132 | "a-.-G-U-S-A-J" : { 2133 | "full": "Gnd/JUDGE ADVOCATE GENERAL (JAG)", 2134 | "desc": "JUDGE ADVOCATE GENERAL (JAG)", 2135 | }, 2136 | "a-.-G-U-S-A-J-C" : { 2137 | "full": "Gnd/JAG CORPS", 2138 | "desc": "JAG CORPS", 2139 | }, 2140 | "a-.-G-U-S-A-J-T" : { 2141 | "full": "Gnd/JAG THEATER", 2142 | "desc": "JAG THEATER", 2143 | }, 2144 | "a-.-G-U-S-A-L" : { 2145 | "full": "Gnd/LABOR", 2146 | "desc": "LABOR", 2147 | }, 2148 | "a-.-G-U-S-A-L-C" : { 2149 | "full": "Gnd/LABOR CORPS", 2150 | "desc": "LABOR CORPS", 2151 | }, 2152 | "a-.-G-U-S-A-L-T" : { 2153 | "full": "Gnd/LABOR THEATER", 2154 | "desc": "LABOR THEATER", 2155 | }, 2156 | "a-.-G-U-S-A-M" : { 2157 | "full": "Gnd/MORTUARY/GRAVES REGISTRY", 2158 | "desc": "MORTUARY/GRAVES REGISTRY", 2159 | }, 2160 | "a-.-G-U-S-A-M-C" : { 2161 | "full": "Gnd/MORTUARY/GRAVES REGISTRY CORPS", 2162 | "desc": "MORTUARY/GRAVES REGISTRY CORPS", 2163 | }, 2164 | "a-.-G-U-S-A-M-T" : { 2165 | "full": "Gnd/MORTUARY/GRAVES REGISTRY THEATER", 2166 | "desc": "MORTUARY/GRAVES REGISTRY THEATER", 2167 | }, 2168 | "a-.-G-U-S-A-O" : { 2169 | "full": "Gnd/POSTAL", 2170 | "desc": "POSTAL", 2171 | }, 2172 | "a-.-G-U-S-A-O-C" : { 2173 | "full": "Gnd/POSTAL CORPS", 2174 | "desc": "POSTAL CORPS", 2175 | }, 2176 | "a-.-G-U-S-A-O-T" : { 2177 | "full": "Gnd/POSTAL THEATER", 2178 | "desc": "POSTAL THEATER", 2179 | }, 2180 | "a-.-G-U-S-A-P" : { 2181 | "full": "Gnd/PUBLIC AFFAIRS", 2182 | "desc": "PUBLIC AFFAIRS", 2183 | }, 2184 | "a-.-G-U-S-A-P-B" : { 2185 | "full": "Gnd/PUBLIC AFFAIRS BROADCAST", 2186 | "desc": "PUBLIC AFFAIRS BROADCAST", 2187 | }, 2188 | "a-.-G-U-S-A-P-B-C" : { 2189 | "full": "Gnd/PUBLIC AFFAIRS BROADCAST CORPS", 2190 | "desc": "PUBLIC AFFAIRS BROADCAST CORPS", 2191 | }, 2192 | "a-.-G-U-S-A-P-B-T" : { 2193 | "full": "Gnd/PUBLIC AFFAIRS BROADCAST THEATER", 2194 | "desc": "PUBLIC AFFAIRS BROADCAST THEATER", 2195 | }, 2196 | "a-.-G-U-S-A-P-C" : { 2197 | "full": "Gnd/PUBLIC AFFAIRS CORPS", 2198 | "desc": "PUBLIC AFFAIRS CORPS", 2199 | }, 2200 | "a-.-G-U-S-A-P-M" : { 2201 | "full": "Gnd/PUBLIC AFFAIRS JOINT INFORMATION BUREAU", 2202 | "desc": "PUBLIC AFFAIRS JOINT INFORMATION BUREAU", 2203 | }, 2204 | "a-.-G-U-S-A-P-M-C" : { 2205 | "full": "Gnd/PUBLIC AFFAIRS JIB CORPS", 2206 | "desc": "PUBLIC AFFAIRS JIB CORPS", 2207 | }, 2208 | "a-.-G-U-S-A-P-M-T" : { 2209 | "full": "Gnd/PUBLIC AFFAIRS JIB THEATER", 2210 | "desc": "PUBLIC AFFAIRS JIB THEATER", 2211 | }, 2212 | "a-.-G-U-S-A-P-T" : { 2213 | "full": "Gnd/PUBLIC AFFAIRS THEATER", 2214 | "desc": "PUBLIC AFFAIRS THEATER", 2215 | }, 2216 | "a-.-G-U-S-A-Q" : { 2217 | "full": "Gnd/QUARTERMASTER (SUPPLY)", 2218 | "desc": "QUARTERMASTER (SUPPLY)", 2219 | }, 2220 | "a-.-G-U-S-A-Q-C" : { 2221 | "full": "Gnd/QUARTERMASTER (SUPPLY) CORPS", 2222 | "desc": "QUARTERMASTER (SUPPLY) CORPS", 2223 | }, 2224 | "a-.-G-U-S-A-Q-T" : { 2225 | "full": "Gnd/QUARTERMASTER (SUPPLY) THEATER", 2226 | "desc": "QUARTERMASTER (SUPPLY) THEATER", 2227 | }, 2228 | "a-.-G-U-S-A-R" : { 2229 | "full": "Gnd/RELIGIOUS/CHAPLAIN", 2230 | "desc": "RELIGIOUS/CHAPLAIN", 2231 | }, 2232 | "a-.-G-U-S-A-R-C" : { 2233 | "full": "Gnd/RELIGIOUS/CHAPLAIN CORPS", 2234 | "desc": "RELIGIOUS/CHAPLAIN CORPS", 2235 | }, 2236 | "a-.-G-U-S-A-R-T" : { 2237 | "full": "Gnd/RELIGIOUS/CHAPLAIN THEATER", 2238 | "desc": "RELIGIOUS/CHAPLAIN THEATER", 2239 | }, 2240 | "a-.-G-U-S-A-S" : { 2241 | "full": "Gnd/PERSONNEL SERVICES", 2242 | "desc": "PERSONNEL SERVICES", 2243 | }, 2244 | "a-.-G-U-S-A-S-C" : { 2245 | "full": "Gnd/PERSONNEL CORPS", 2246 | "desc": "PERSONNEL CORPS", 2247 | }, 2248 | "a-.-G-U-S-A-S-T" : { 2249 | "full": "Gnd/PERSONNEL THEATER", 2250 | "desc": "PERSONNEL THEATER", 2251 | }, 2252 | "a-.-G-U-S-A-T" : { 2253 | "full": "Gnd/ADMIN THEATER", 2254 | "desc": "ADMIN THEATER", 2255 | }, 2256 | "a-.-G-U-S-A-W" : { 2257 | "full": "Gnd/MORALE, WELFARE, RECREATION (MWR)", 2258 | "desc": "MORALE, WELFARE, RECREATION (MWR)", 2259 | }, 2260 | "a-.-G-U-S-A-W-C" : { 2261 | "full": "Gnd/MWR CORPS", 2262 | "desc": "MWR CORPS", 2263 | }, 2264 | "a-.-G-U-S-A-W-T" : { 2265 | "full": "Gnd/MWR THEATER", 2266 | "desc": "MWR THEATER", 2267 | }, 2268 | "a-.-G-U-S-A-X" : { 2269 | "full": "Gnd/REPLACEMENT HOLDING UNIT (RHU)", 2270 | "desc": "REPLACEMENT HOLDING UNIT (RHU)", 2271 | }, 2272 | "a-.-G-U-S-A-X-C" : { 2273 | "full": "Gnd/RHU CORPS", 2274 | "desc": "RHU CORPS", 2275 | }, 2276 | "a-.-G-U-S-A-X-T" : { 2277 | "full": "Gnd/RHU THEATER", 2278 | "desc": "RHU THEATER", 2279 | }, 2280 | "a-.-G-U-S-M" : { 2281 | "full": "Gnd/MEDICAL", 2282 | "desc": "MEDICAL", 2283 | }, 2284 | "a-.-G-U-S-M-C" : { 2285 | "full": "Gnd/MEDICAL CORPS", 2286 | "desc": "MEDICAL CORPS", 2287 | }, 2288 | "a-.-G-U-S-M-D" : { 2289 | "full": "Gnd/MEDICAL DENTAL", 2290 | "desc": "MEDICAL DENTAL", 2291 | }, 2292 | "a-.-G-U-S-M-D-C" : { 2293 | "full": "Gnd/MEDICAL DENTAL CORPS", 2294 | "desc": "MEDICAL DENTAL CORPS", 2295 | }, 2296 | "a-.-G-U-S-M-D-T" : { 2297 | "full": "Gnd/MEDICAL DENTAL THEATER", 2298 | "desc": "MEDICAL DENTAL THEATER", 2299 | }, 2300 | "a-.-G-U-S-M-M" : { 2301 | "full": "Gnd/MEDICAL TREATMENT FACILITY", 2302 | "desc": "MEDICAL TREATMENT FACILITY", 2303 | }, 2304 | "a-.-G-U-S-M-M-C" : { 2305 | "full": "Gnd/MEDICAL TREATMENT FACILITY CORPS", 2306 | "desc": "MEDICAL TREATMENT FACILITY CORPS", 2307 | }, 2308 | "a-.-G-U-S-M-M-T" : { 2309 | "full": "Gnd/MEDICAL TREATMENT FACILITY THEATER", 2310 | "desc": "MEDICAL TREATMENT FACILITY THEATER", 2311 | }, 2312 | "a-.-G-U-S-M-P" : { 2313 | "full": "Gnd/MEDICAL PSYCHOLOGICAL", 2314 | "desc": "MEDICAL PSYCHOLOGICAL", 2315 | }, 2316 | "a-.-G-U-S-M-P-C" : { 2317 | "full": "Gnd/MEDICAL PSYCHOLOGICAL CORPS", 2318 | "desc": "MEDICAL PSYCHOLOGICAL CORPS", 2319 | }, 2320 | "a-.-G-U-S-M-P-T" : { 2321 | "full": "Gnd/MEDICAL PSYCHOLOGICAL THEATER", 2322 | "desc": "MEDICAL PSYCHOLOGICAL THEATER", 2323 | }, 2324 | "a-.-G-U-S-M-T" : { 2325 | "full": "Gnd/MEDICAL THEATER", 2326 | "desc": "MEDICAL THEATER", 2327 | }, 2328 | "a-.-G-U-S-M-V" : { 2329 | "full": "Gnd/MEDICAL VETERINARY", 2330 | "desc": "MEDICAL VETERINARY", 2331 | }, 2332 | "a-.-G-U-S-M-V-C" : { 2333 | "full": "Gnd/MEDICAL VETERINARY CORPS", 2334 | "desc": "MEDICAL VETERINARY CORPS", 2335 | }, 2336 | "a-.-G-U-S-M-V-T" : { 2337 | "full": "Gnd/MEDICAL VETERINARY THEATER", 2338 | "desc": "MEDICAL VETERINARY THEATER", 2339 | }, 2340 | "a-.-G-U-S-S" : { 2341 | "full": "Gnd/SUPPLY", 2342 | "desc": "SUPPLY", 2343 | }, 2344 | "a-.-G-U-S-S-1" : { 2345 | "full": "Gnd/SUPPLY CLASS I", 2346 | "desc": "SUPPLY CLASS I", 2347 | }, 2348 | "a-.-G-U-S-S-1-C" : { 2349 | "full": "Gnd/SUPPLY CLASS I CORPS", 2350 | "desc": "SUPPLY CLASS I CORPS", 2351 | }, 2352 | "a-.-G-U-S-S-1-T" : { 2353 | "full": "Gnd/SUPPLY CLASS I THEATER", 2354 | "desc": "SUPPLY CLASS I THEATER", 2355 | }, 2356 | "a-.-G-U-S-S-2" : { 2357 | "full": "Gnd/SUPPLY CLASS II", 2358 | "desc": "SUPPLY CLASS II", 2359 | }, 2360 | "a-.-G-U-S-S-2-C" : { 2361 | "full": "Gnd/SUPPLY CLASS II CORPS", 2362 | "desc": "SUPPLY CLASS II CORPS", 2363 | }, 2364 | "a-.-G-U-S-S-2-T" : { 2365 | "full": "Gnd/SUPPLY CLASS II THEATER", 2366 | "desc": "SUPPLY CLASS II THEATER", 2367 | }, 2368 | "a-.-G-U-S-S-3" : { 2369 | "full": "Gnd/SUPPLY CLASS III", 2370 | "desc": "SUPPLY CLASS III", 2371 | }, 2372 | "a-.-G-U-S-S-3-A" : { 2373 | "full": "Gnd/SUPPLY CLASS III AVIATION", 2374 | "desc": "SUPPLY CLASS III AVIATION", 2375 | }, 2376 | "a-.-G-U-S-S-3-A-C" : { 2377 | "full": "Gnd/SUPPLY CLASS III AVIATION CORPS", 2378 | "desc": "SUPPLY CLASS III AVIATION CORPS", 2379 | }, 2380 | "a-.-G-U-S-S-3-A-T" : { 2381 | "full": "Gnd/SUPPLY CLASS III AVIATION THEATER", 2382 | "desc": "SUPPLY CLASS III AVIATION THEATER", 2383 | }, 2384 | "a-.-G-U-S-S-3-C" : { 2385 | "full": "Gnd/SUPPLY CLASS III CORPS", 2386 | "desc": "SUPPLY CLASS III CORPS", 2387 | }, 2388 | "a-.-G-U-S-S-3-T" : { 2389 | "full": "Gnd/SUPPLY CLASS III THEATER", 2390 | "desc": "SUPPLY CLASS III THEATER", 2391 | }, 2392 | "a-.-G-U-S-S-4" : { 2393 | "full": "Gnd/SUPPLY CLASS IV", 2394 | "desc": "SUPPLY CLASS IV", 2395 | }, 2396 | "a-.-G-U-S-S-4-C" : { 2397 | "full": "Gnd/SUPPLY CLASS IV CORPS", 2398 | "desc": "SUPPLY CLASS IV CORPS", 2399 | }, 2400 | "a-.-G-U-S-S-4-T" : { 2401 | "full": "Gnd/SUPPLY CLASS IV THEATER", 2402 | "desc": "SUPPLY CLASS IV THEATER", 2403 | }, 2404 | "a-.-G-U-S-S-5" : { 2405 | "full": "Gnd/SUPPLY CLASS V", 2406 | "desc": "SUPPLY CLASS V", 2407 | }, 2408 | "a-.-G-U-S-S-5-C" : { 2409 | "full": "Gnd/SUPPLY CLASS V CORPS", 2410 | "desc": "SUPPLY CLASS V CORPS", 2411 | }, 2412 | "a-.-G-U-S-S-5-T" : { 2413 | "full": "Gnd/SUPPLY CLASS V THEATER", 2414 | "desc": "SUPPLY CLASS V THEATER", 2415 | }, 2416 | "a-.-G-U-S-S-6" : { 2417 | "full": "Gnd/SUPPLY CLASS VI", 2418 | "desc": "SUPPLY CLASS VI", 2419 | }, 2420 | "a-.-G-U-S-S-6-C" : { 2421 | "full": "Gnd/SUPPLY CLASS VI CORPS", 2422 | "desc": "SUPPLY CLASS VI CORPS", 2423 | }, 2424 | "a-.-G-U-S-S-6-T" : { 2425 | "full": "Gnd/SUPPLY CLASS VI THEATER", 2426 | "desc": "SUPPLY CLASS VI THEATER", 2427 | }, 2428 | "a-.-G-U-S-S-7" : { 2429 | "full": "Gnd/SUPPLY CLASS VII", 2430 | "desc": "SUPPLY CLASS VII", 2431 | }, 2432 | "a-.-G-U-S-S-7-C" : { 2433 | "full": "Gnd/SUPPLY CLASS VII CORPS", 2434 | "desc": "SUPPLY CLASS VII CORPS", 2435 | }, 2436 | "a-.-G-U-S-S-7-T" : { 2437 | "full": "Gnd/SUPPLY CLASS VII THEATER", 2438 | "desc": "SUPPLY CLASS VII THEATER", 2439 | }, 2440 | "a-.-G-U-S-S-8" : { 2441 | "full": "Gnd/SUPPLY CLASS VIII", 2442 | "desc": "SUPPLY CLASS VIII", 2443 | }, 2444 | "a-.-G-U-S-S-8-C" : { 2445 | "full": "Gnd/SUPPLY CLASS VIII CORPS", 2446 | "desc": "SUPPLY CLASS VIII CORPS", 2447 | }, 2448 | "a-.-G-U-S-S-8-T" : { 2449 | "full": "Gnd/SUPPLY CLASS VIII THEATER", 2450 | "desc": "SUPPLY CLASS VIII THEATER", 2451 | }, 2452 | "a-.-G-U-S-S-9" : { 2453 | "full": "Gnd/SUPPLY CLASS IX", 2454 | "desc": "SUPPLY CLASS IX", 2455 | }, 2456 | "a-.-G-U-S-S-9-C" : { 2457 | "full": "Gnd/SUPPLY CLASS IX CORPS", 2458 | "desc": "SUPPLY CLASS IX CORPS", 2459 | }, 2460 | "a-.-G-U-S-S-9-T" : { 2461 | "full": "Gnd/SUPPLY CLASS IX THEATER", 2462 | "desc": "SUPPLY CLASS IX THEATER", 2463 | }, 2464 | "a-.-G-U-S-S-C" : { 2465 | "full": "Gnd/SUPPLY CORPS", 2466 | "desc": "SUPPLY CORPS", 2467 | }, 2468 | "a-.-G-U-S-S-L" : { 2469 | "full": "Gnd/SUPPLY LAUNDRY/BATH", 2470 | "desc": "SUPPLY LAUNDRY/BATH", 2471 | }, 2472 | "a-.-G-U-S-S-L-C" : { 2473 | "full": "Gnd/SUPPLY LAUNDRY/BATH CORPS", 2474 | "desc": "SUPPLY LAUNDRY/BATH CORPS", 2475 | }, 2476 | "a-.-G-U-S-S-L-T" : { 2477 | "full": "Gnd/SUPPLY LAUNDRY/BATH THEATER", 2478 | "desc": "SUPPLY LAUNDRY/BATH THEATER", 2479 | }, 2480 | "a-.-G-U-S-S-T" : { 2481 | "full": "Gnd/SUPPLY THEATER", 2482 | "desc": "SUPPLY THEATER", 2483 | }, 2484 | "a-.-G-U-S-S-W" : { 2485 | "full": "Gnd/SUPPLY WATER", 2486 | "desc": "SUPPLY WATER", 2487 | }, 2488 | "a-.-G-U-S-S-W-C" : { 2489 | "full": "Gnd/SUPPLY WATER CORPS", 2490 | "desc": "SUPPLY WATER CORPS", 2491 | }, 2492 | "a-.-G-U-S-S-W-P" : { 2493 | "full": "Gnd/SUPPLY WATER PURIFICATION", 2494 | "desc": "SUPPLY WATER PURIFICATION", 2495 | }, 2496 | "a-.-G-U-S-S-W-P-C" : { 2497 | "full": "Gnd/SUPPLY WATER PURIFICATION CORPS", 2498 | "desc": "SUPPLY WATER PURIFICATION CORPS", 2499 | }, 2500 | "a-.-G-U-S-S-W-P-T" : { 2501 | "full": "Gnd/SUPPLY WATER PURIFICATION THEATER", 2502 | "desc": "SUPPLY WATER PURIFICATION THEATER", 2503 | }, 2504 | "a-.-G-U-S-S-W-T" : { 2505 | "full": "Gnd/SUPPLY WATER THEATER", 2506 | "desc": "SUPPLY WATER THEATER", 2507 | }, 2508 | "a-.-G-U-S-S-X" : { 2509 | "full": "Gnd/SUPPLY CLASS X", 2510 | "desc": "SUPPLY CLASS X", 2511 | }, 2512 | "a-.-G-U-S-S-X-C" : { 2513 | "full": "Gnd/SUPPLY CLASS X CORPS", 2514 | "desc": "SUPPLY CLASS X CORPS", 2515 | }, 2516 | "a-.-G-U-S-S-X-T" : { 2517 | "full": "Gnd/SUPPLY CLASS X THEATER", 2518 | "desc": "SUPPLY CLASS X THEATER", 2519 | }, 2520 | "a-.-G-U-S-S-d" : { 2521 | "full": "Gnd/SupplyDepot", 2522 | "desc": "SupplyDepot", 2523 | }, 2524 | "a-.-G-U-S-T" : { 2525 | "full": "Gnd/TRANSPORTATION", 2526 | "desc": "TRANSPORTATION", 2527 | }, 2528 | "a-.-G-U-S-T-A" : { 2529 | "full": "Gnd/APOD/APOE", 2530 | "desc": "APOD/APOE", 2531 | }, 2532 | "a-.-G-U-S-T-A-C" : { 2533 | "full": "Gnd/APOD/APOE CORPS", 2534 | "desc": "APOD/APOE CORPS", 2535 | }, 2536 | "a-.-G-U-S-T-A-T" : { 2537 | "full": "Gnd/APOD/APOE THEATER", 2538 | "desc": "APOD/APOE THEATER", 2539 | }, 2540 | "a-.-G-U-S-T-C" : { 2541 | "full": "Gnd/TRANSPORTATION CORPS", 2542 | "desc": "TRANSPORTATION CORPS", 2543 | }, 2544 | "a-.-G-U-S-T-I" : { 2545 | "full": "Gnd/MISSILE", 2546 | "desc": "MISSILE", 2547 | }, 2548 | "a-.-G-U-S-T-I-C" : { 2549 | "full": "Gnd/MISSILE CORPS", 2550 | "desc": "MISSILE CORPS", 2551 | }, 2552 | "a-.-G-U-S-T-I-T" : { 2553 | "full": "Gnd/MISSILE THEATER", 2554 | "desc": "MISSILE THEATER", 2555 | }, 2556 | "a-.-G-U-S-T-M" : { 2557 | "full": "Gnd/MOVEMENT CONTROL CENTER(MCC)", 2558 | "desc": "MOVEMENT CONTROL CENTER(MCC)", 2559 | }, 2560 | "a-.-G-U-S-T-M-C" : { 2561 | "full": "Gnd/MCC CORPS", 2562 | "desc": "MCC CORPS", 2563 | }, 2564 | "a-.-G-U-S-T-M-T" : { 2565 | "full": "Gnd/MCC THEATER", 2566 | "desc": "MCC THEATER", 2567 | }, 2568 | "a-.-G-U-S-T-R" : { 2569 | "full": "Gnd/RAILHEAD", 2570 | "desc": "RAILHEAD", 2571 | }, 2572 | "a-.-G-U-S-T-R-C" : { 2573 | "full": "Gnd/RAILHEAD CORPS", 2574 | "desc": "RAILHEAD CORPS", 2575 | }, 2576 | "a-.-G-U-S-T-R-T" : { 2577 | "full": "Gnd/RAILHEAD THEATER", 2578 | "desc": "RAILHEAD THEATER", 2579 | }, 2580 | "a-.-G-U-S-T-S" : { 2581 | "full": "Gnd/SPOD/SPOE", 2582 | "desc": "SPOD/SPOE", 2583 | }, 2584 | "a-.-G-U-S-T-S-C" : { 2585 | "full": "Gnd/SPOD/SPOE CORPS", 2586 | "desc": "SPOD/SPOE CORPS", 2587 | }, 2588 | "a-.-G-U-S-T-S-T" : { 2589 | "full": "Gnd/SPOD/SPOE THEATER", 2590 | "desc": "SPOD/SPOE THEATER", 2591 | }, 2592 | "a-.-G-U-S-T-T" : { 2593 | "full": "Gnd/TRANSPORTATION THEATER", 2594 | "desc": "TRANSPORTATION THEATER", 2595 | }, 2596 | "a-.-G-U-S-X" : { 2597 | "full": "Gnd/MAINTENANCE", 2598 | "desc": "MAINTENANCE", 2599 | }, 2600 | "a-.-G-U-S-X-C" : { 2601 | "full": "Gnd/MAINTENANCE CORPS", 2602 | "desc": "MAINTENANCE CORPS", 2603 | }, 2604 | "a-.-G-U-S-X-E" : { 2605 | "full": "Gnd/ELECTRO OPTICAL", 2606 | "desc": "ELECTRO OPTICAL", 2607 | }, 2608 | "a-.-G-U-S-X-E-C" : { 2609 | "full": "Gnd/ELECTRO OPTICAL CORPS", 2610 | "desc": "ELECTRO OPTICAL CORPS", 2611 | }, 2612 | "a-.-G-U-S-X-E-T" : { 2613 | "full": "Gnd/ELECTRO OPTICAL THEATER", 2614 | "desc": "ELECTRO OPTICAL THEATER", 2615 | }, 2616 | "a-.-G-U-S-X-H" : { 2617 | "full": "Gnd/MAINTENANCE HEAVY", 2618 | "desc": "MAINTENANCE HEAVY", 2619 | }, 2620 | "a-.-G-U-S-X-H-C" : { 2621 | "full": "Gnd/MAINTENANCE HEAVY CORPS", 2622 | "desc": "MAINTENANCE HEAVY CORPS", 2623 | }, 2624 | "a-.-G-U-S-X-H-T" : { 2625 | "full": "Gnd/MAINTENANCE HEAVY THEATER", 2626 | "desc": "MAINTENANCE HEAVY THEATER", 2627 | }, 2628 | "a-.-G-U-S-X-O" : { 2629 | "full": "Gnd/ORDNANCE", 2630 | "desc": "ORDNANCE", 2631 | }, 2632 | "a-.-G-U-S-X-O-C" : { 2633 | "full": "Gnd/ORDNANCE CORPS", 2634 | "desc": "ORDNANCE CORPS", 2635 | }, 2636 | "a-.-G-U-S-X-O-M" : { 2637 | "full": "Gnd/ORDNANCE MISSILE", 2638 | "desc": "ORDNANCE MISSILE", 2639 | }, 2640 | "a-.-G-U-S-X-O-M-C" : { 2641 | "full": "Gnd/ORDNANCE MISSILE CORPS", 2642 | "desc": "ORDNANCE MISSILE CORPS", 2643 | }, 2644 | "a-.-G-U-S-X-O-M-T" : { 2645 | "full": "Gnd/ORDNANCE MISSILE THEATER", 2646 | "desc": "ORDNANCE MISSILE THEATER", 2647 | }, 2648 | "a-.-G-U-S-X-O-T" : { 2649 | "full": "Gnd/ORDNANCE THEATER", 2650 | "desc": "ORDNANCE THEATER", 2651 | }, 2652 | "a-.-G-U-S-X-R" : { 2653 | "full": "Gnd/MAINTENANCE RECOVERY", 2654 | "desc": "MAINTENANCE RECOVERY", 2655 | }, 2656 | "a-.-G-U-S-X-R-C" : { 2657 | "full": "Gnd/MAINTENANCE RECOVERY CORPS", 2658 | "desc": "MAINTENANCE RECOVERY CORPS", 2659 | }, 2660 | "a-.-G-U-S-X-R-T" : { 2661 | "full": "Gnd/MAINTENANCE RECOVERY THEATER", 2662 | "desc": "MAINTENANCE RECOVERY THEATER", 2663 | }, 2664 | "a-.-G-U-S-X-T" : { 2665 | "full": "Gnd/MAINTENANCE THEATER", 2666 | "desc": "MAINTENANCE THEATER", 2667 | }, 2668 | "a-.-G-U-U" : { 2669 | "full": "Gnd/COMBAT SUPPORT", 2670 | "desc": "COMBAT SUPPORT", 2671 | }, 2672 | "a-.-G-U-U-A" : { 2673 | "full": "Gnd/COMBAT SUPPORT NBC", 2674 | "desc": "COMBAT SUPPORT NBC", 2675 | }, 2676 | "a-.-G-U-U-A-B" : { 2677 | "full": "Gnd/BIOLOGICAL", 2678 | "desc": "BIOLOGICAL", 2679 | }, 2680 | "a-.-G-U-U-A-B-R" : { 2681 | "full": "Gnd/RECON EQUIPPED", 2682 | "desc": "RECON EQUIPPED", 2683 | }, 2684 | "a-.-G-U-U-A-C" : { 2685 | "full": "Gnd/CHEMICAL", 2686 | "desc": "CHEMICAL", 2687 | }, 2688 | "a-.-G-U-U-A-C-C" : { 2689 | "full": "Gnd/SMOKE/DECON", 2690 | "desc": "SMOKE/DECON", 2691 | }, 2692 | "a-.-G-U-U-A-C-C-K" : { 2693 | "full": "Gnd/MECHANIZED SMOKE/DECON", 2694 | "desc": "MECHANIZED SMOKE/DECON", 2695 | }, 2696 | "a-.-G-U-U-A-C-C-M" : { 2697 | "full": "Gnd/MOTORIZED SMOKE/DECON", 2698 | "desc": "MOTORIZED SMOKE/DECON", 2699 | }, 2700 | "a-.-G-U-U-A-C-R" : { 2701 | "full": "Gnd/CHEMICAL RECON", 2702 | "desc": "CHEMICAL RECON", 2703 | }, 2704 | "a-.-G-U-U-A-C-R-S" : { 2705 | "full": "Gnd/CHEMICAL WHEELED ARMORED VEHICLE", 2706 | "desc": "CHEMICAL WHEELED ARMORED VEHICLE", 2707 | }, 2708 | "a-.-G-U-U-A-C-R-W" : { 2709 | "full": "Gnd/CHEMICAL WHEELED ARMORED VEHICLE", 2710 | "desc": "CHEMICAL WHEELED ARMORED VEHICLE", 2711 | }, 2712 | "a-.-G-U-U-A-C-S" : { 2713 | "full": "Gnd/SMOKE", 2714 | "desc": "SMOKE", 2715 | }, 2716 | "a-.-G-U-U-A-C-S-A" : { 2717 | "full": "Gnd/ARMOR SMOKE", 2718 | "desc": "ARMOR SMOKE", 2719 | }, 2720 | "a-.-G-U-U-A-C-S-M" : { 2721 | "full": "Gnd/MOTORIZED SMOKE", 2722 | "desc": "MOTORIZED SMOKE", 2723 | }, 2724 | "a-.-G-U-U-A-D" : { 2725 | "full": "Gnd/DECONTAMINATION", 2726 | "desc": "DECONTAMINATION", 2727 | }, 2728 | "a-.-G-U-U-A-N" : { 2729 | "full": "Gnd/NUCLEAR", 2730 | "desc": "NUCLEAR", 2731 | }, 2732 | "a-.-G-U-U-E" : { 2733 | "full": "Gnd/EXPLOSIVE ORDINANCE DISPOSAL", 2734 | "desc": "EXPLOSIVE ORDINANCE DISPOSAL", 2735 | }, 2736 | "a-.-G-U-U-I" : { 2737 | "full": "Gnd/INFORMATION WARFARE UNIT", 2738 | "desc": "INFORMATION WARFARE UNIT", 2739 | }, 2740 | "a-.-G-U-U-L" : { 2741 | "full": "Gnd/LAW ENFORCEMENT UNIT", 2742 | "desc": "LAW ENFORCEMENT UNIT", 2743 | }, 2744 | "a-.-G-U-U-L-C" : { 2745 | "full": "Gnd/CIVILIAN LAW ENFORCEMENT", 2746 | "desc": "CIVILIAN LAW ENFORCEMENT", 2747 | }, 2748 | "a-.-G-U-U-L-D" : { 2749 | "full": "Gnd/CENTRAL INTELLIGENCE DIVISION (CID)", 2750 | "desc": "CENTRAL INTELLIGENCE DIVISION (CID)", 2751 | }, 2752 | "a-.-G-U-U-L-F" : { 2753 | "full": "Gnd/SECURITY POLICE (AIR)", 2754 | "desc": "SECURITY POLICE (AIR)", 2755 | }, 2756 | "a-.-G-U-U-L-M" : { 2757 | "full": "Gnd/MILITARY POLICE", 2758 | "desc": "MILITARY POLICE", 2759 | }, 2760 | "a-.-G-U-U-L-S" : { 2761 | "full": "Gnd/SHORE PATROL", 2762 | "desc": "SHORE PATROL", 2763 | }, 2764 | "a-.-G-U-U-M" : { 2765 | "full": "Gnd/MILITARY INTELLIGENCE", 2766 | "desc": "MILITARY INTELLIGENCE", 2767 | }, 2768 | "a-.-G-U-U-M-A" : { 2769 | "full": "Gnd/AERIAL EXPLOITATION", 2770 | "desc": "AERIAL EXPLOITATION", 2771 | }, 2772 | "a-.-G-U-U-M-C" : { 2773 | "full": "Gnd/COUNTER INTELLIGENCE", 2774 | "desc": "COUNTER INTELLIGENCE", 2775 | }, 2776 | "a-.-G-U-U-M-J" : { 2777 | "full": "Gnd/JOINT INTELLIGENCE CENTER", 2778 | "desc": "JOINT INTELLIGENCE CENTER", 2779 | }, 2780 | "a-.-G-U-U-M-M-O" : { 2781 | "full": "Gnd/METEOROLOGICAL", 2782 | "desc": "METEOROLOGICAL", 2783 | }, 2784 | "a-.-G-U-U-M-O" : { 2785 | "full": "Gnd/OPERATIONS", 2786 | "desc": "OPERATIONS", 2787 | }, 2788 | "a-.-G-U-U-M-Q" : { 2789 | "full": "Gnd/INTERROGATION", 2790 | "desc": "INTERROGATION", 2791 | }, 2792 | "a-.-G-U-U-M-R" : { 2793 | "full": "Gnd/SURVEILLANCE", 2794 | "desc": "SURVEILLANCE", 2795 | }, 2796 | "a-.-G-U-U-M-R-G" : { 2797 | "full": "Gnd/GROUND SURVEILLANCE RADAR", 2798 | "desc": "GROUND SURVEILLANCE RADAR", 2799 | }, 2800 | "a-.-G-U-U-M-R-S" : { 2801 | "full": "Gnd/SENSOR", 2802 | "desc": "SENSOR", 2803 | }, 2804 | "a-.-G-U-U-M-R-S-S" : { 2805 | "full": "Gnd/SENSOR SCM", 2806 | "desc": "SENSOR SCM", 2807 | }, 2808 | "a-.-G-U-U-M-R-X" : { 2809 | "full": "Gnd/GROUND STATION MODULE", 2810 | "desc": "GROUND STATION MODULE", 2811 | }, 2812 | "a-.-G-U-U-M-S" : { 2813 | "full": "Gnd/SIGNAL INTELLIGENCE (SIGINT)", 2814 | "desc": "SIGNAL INTELLIGENCE (SIGINT)", 2815 | }, 2816 | "a-.-G-U-U-M-S-E" : { 2817 | "full": "Gnd/ELECTRONIC WARFARE", 2818 | "desc": "ELECTRONIC WARFARE", 2819 | }, 2820 | "a-.-G-U-U-M-S-E-A" : { 2821 | "full": "Gnd/ARMORED WHEELED VEHICLE", 2822 | "desc": "ARMORED WHEELED VEHICLE", 2823 | }, 2824 | "a-.-G-U-U-M-S-E-C" : { 2825 | "full": "Gnd/CORPS", 2826 | "desc": "CORPS", 2827 | }, 2828 | "a-.-G-U-U-M-S-E-D" : { 2829 | "full": "Gnd/DIRECTION FINDING", 2830 | "desc": "DIRECTION FINDING", 2831 | }, 2832 | "a-.-G-U-U-M-S-E-I" : { 2833 | "full": "Gnd/INTERCEPT", 2834 | "desc": "INTERCEPT", 2835 | }, 2836 | "a-.-G-U-U-M-S-E-J" : { 2837 | "full": "Gnd/JAMMING", 2838 | "desc": "JAMMING", 2839 | }, 2840 | "a-.-G-U-U-M-S-E-T" : { 2841 | "full": "Gnd/THEATER", 2842 | "desc": "THEATER", 2843 | }, 2844 | "a-.-G-U-U-M-T" : { 2845 | "full": "Gnd/TACTICAL EXPLOIT", 2846 | "desc": "TACTICAL EXPLOIT", 2847 | }, 2848 | "a-.-G-U-U-P" : { 2849 | "full": "Gnd/LANDING SUPPORT", 2850 | "desc": "LANDING SUPPORT", 2851 | }, 2852 | "a-.-G-U-U-S" : { 2853 | "full": "Gnd/SIGNAL UNIT", 2854 | "desc": "SIGNAL UNIT", 2855 | }, 2856 | "a-.-G-U-U-S-A" : { 2857 | "full": "Gnd/AREA", 2858 | "desc": "AREA", 2859 | }, 2860 | "a-.-G-U-U-S-C" : { 2861 | "full": "Gnd/COMMUNICATION CONFIGURED PACKAGE", 2862 | "desc": "COMMUNICATION CONFIGURED PACKAGE", 2863 | }, 2864 | "a-.-G-U-U-S-C-L" : { 2865 | "full": "Gnd/LARGE COMMUNICATION CONFIGURED PACKAGE", 2866 | "desc": "LARGE COMMUNICATION CONFIGURED PACKAGE", 2867 | }, 2868 | "a-.-G-U-U-S-F" : { 2869 | "full": "Gnd/FORWARD COMMUNICATIONS", 2870 | "desc": "FORWARD COMMUNICATIONS", 2871 | }, 2872 | "a-.-G-U-U-S-M" : { 2873 | "full": "Gnd/MULTIPLE SUBSCRIBER ELEMENT", 2874 | "desc": "MULTIPLE SUBSCRIBER ELEMENT", 2875 | }, 2876 | "a-.-G-U-U-S-M-L" : { 2877 | "full": "Gnd/LARGE EXTENSION NODE", 2878 | "desc": "LARGE EXTENSION NODE", 2879 | }, 2880 | "a-.-G-U-U-S-M-N" : { 2881 | "full": "Gnd/NODE CENTER", 2882 | "desc": "NODE CENTER", 2883 | }, 2884 | "a-.-G-U-U-S-M-S" : { 2885 | "full": "Gnd/SMALL EXTENSION NODE", 2886 | "desc": "SMALL EXTENSION NODE", 2887 | }, 2888 | "a-.-G-U-U-S-O" : { 2889 | "full": "Gnd/COMMAND OPERATIONS", 2890 | "desc": "COMMAND OPERATIONS", 2891 | }, 2892 | "a-.-G-U-U-S-R" : { 2893 | "full": "Gnd/RADIO UNIT", 2894 | "desc": "RADIO UNIT", 2895 | }, 2896 | "a-.-G-U-U-S-R-S" : { 2897 | "full": "Gnd/TACTICAL SATELLITE", 2898 | "desc": "TACTICAL SATELLITE", 2899 | }, 2900 | "a-.-G-U-U-S-R-T" : { 2901 | "full": "Gnd/TELETYPE CENTER", 2902 | "desc": "TELETYPE CENTER", 2903 | }, 2904 | "a-.-G-U-U-S-R-W" : { 2905 | "full": "Gnd/RELAY", 2906 | "desc": "RELAY", 2907 | }, 2908 | "a-.-G-U-U-S-S" : { 2909 | "full": "Gnd/SIGNAL SUPPORT", 2910 | "desc": "SIGNAL SUPPORT", 2911 | }, 2912 | "a-.-G-U-U-S-W" : { 2913 | "full": "Gnd/TELEPHONE SWITCH", 2914 | "desc": "TELEPHONE SWITCH", 2915 | }, 2916 | "a-.-G-U-U-S-X" : { 2917 | "full": "Gnd/ELECTRONIC RANGING", 2918 | "desc": "ELECTRONIC RANGING", 2919 | }, 2920 | "a-.-G-U-i" : { 2921 | "full": "Gnd/IM Resources", 2922 | "desc": "Incident Management Resources", 2923 | }, 2924 | "a-.-G-U-i-a" : { 2925 | "full": "Gnd/IM Resources/Animal Health", 2926 | "desc": "Animal Health", 2927 | }, 2928 | "a-.-G-U-i-a-lar" : { 2929 | "full": "Gnd/Large Animal Rescue Strike Team", 2930 | "desc": "Large Animal Rescue Strike Team", 2931 | }, 2932 | "a-.-G-U-i-a-las" : { 2933 | "full": "Gnd/Large Animal Sheltering Team", 2934 | "desc": "Large Animal Sheltering Team", 2935 | }, 2936 | "a-.-G-U-i-a-lat" : { 2937 | "full": "Gnd/Large Animal Transport Team", 2938 | "desc": "Large Animal Transport Team", 2939 | }, 2940 | "a-.-G-U-i-a-sar" : { 2941 | "full": "Gnd/Small Animal Rescue Strike Team", 2942 | "desc": "Small Animal Rescue Strike Team", 2943 | }, 2944 | "a-.-G-U-i-a-sas" : { 2945 | "full": "Gnd/Small Animal Sheltering Team", 2946 | "desc": "Small Animal Sheltering Team", 2947 | }, 2948 | "a-.-G-U-i-a-sat" : { 2949 | "full": "Gnd/Small Animal Transport Team", 2950 | "desc": "Small Animal Transport Team", 2951 | }, 2952 | "a-.-G-U-i-a-imt" : { 2953 | "full": "Gnd/Incident Management Team Animal Protection", 2954 | "desc": "Incident Management Team Animal Protection", 2955 | }, 2956 | "a-.-G-U-i-e" : { 2957 | "full": "Gnd/IM Resources/Emergency Management", 2958 | "desc": "Emergency Management", 2959 | }, 2960 | "a-.-G-U-i-e-acrc" : { 2961 | "full": "Gnd/Airborne Communications Relay (CAP)", 2962 | "desc": "Airborne Communications Relay(CAP)", 2963 | }, 2964 | "a-.-G-U-i-e-acrt" : { 2965 | "full": "Gnd/Airborne Communications Relay Team", 2966 | "desc": "Airborne Communications Relay Team", 2967 | }, 2968 | "a-.-G-U-i-e-att" : { 2969 | "full": "Gnd/Airborne Transport Team", 2970 | "desc": "Airborne Transport Team", 2971 | }, 2972 | "a-.-G-U-i-e-cis" : { 2973 | "full": "Gnd/Critical Incident Stress Management Team", 2974 | "desc": "Critical Incident Stress Management Team", 2975 | }, 2976 | "a-.-G-U-i-e-cst" : { 2977 | "full": "Gnd/Communications Support Team", 2978 | "desc": "Communications Support Team", 2979 | }, 2980 | "a-.-G-U-i-e-dc" : { 2981 | "full": "Gnd/Donations Coordinator", 2982 | "desc": "Donations Coordinator", 2983 | }, 2984 | "a-.-G-U-i-e-dmt" : { 2985 | "full": "Gnd/Donations Management Personnel Team", 2986 | "desc": "Donations Management Personnel Team", 2987 | }, 2988 | "a-.-G-U-i-e-ect" : { 2989 | "full": "Gnd/Evacuation Coordination Team", 2990 | "desc": "Evacuation Coordination Team", 2991 | }, 2992 | "a-.-G-U-i-e-efa" : { 2993 | "full": "Gnd/EOC Finance Administration", 2994 | "desc": "EOC Finance Administration", 2995 | }, 2996 | "a-.-G-U-i-e-elt" : { 2997 | "full": "Gnd/Evacuation Liaison Team", 2998 | "desc": "Evacuation Liaison Team", 2999 | }, 3000 | "a-.-G-U-i-e-ems" : { 3001 | "full": "Gnd/EOC Management Support Team", 3002 | "desc": "EOC Management Support Team", 3003 | }, 3004 | "a-.-G-U-i-e-eos" : { 3005 | "full": "Gnd/EOC Operations Section Chief", 3006 | "desc": "EOC Operations Section Chief", 3007 | }, 3008 | "a-.-G-U-i-e-eps" : { 3009 | "full": "Gnd/EOC Planning Section Chief", 3010 | "desc": "EOC Planning Section Chief", 3011 | }, 3012 | "a-.-G-U-i-e-ial" : { 3013 | "full": "Gnd/Individual Assistance Disaster Assessment Team Leader", 3014 | "desc": "Individual Assistance Disaster Assessment Team Leader", 3015 | }, 3016 | "a-.-G-U-i-e-iat" : { 3017 | "full": "Gnd/Individual Assistance Disaster Assessment Team", 3018 | "desc": "Individual Assistance Disaster Assessment Team", 3019 | }, 3020 | "a-.-G-U-i-e-imt" : { 3021 | "full": "Gnd/Incident Management Team", 3022 | "desc": "Incident Management Team", 3023 | }, 3024 | "a-.-G-U-i-e-mcc" : { 3025 | "full": "Gnd/Mobile Communications Center", 3026 | "desc": "Mobile Communications Center", 3027 | }, 3028 | "a-.-G-U-i-e-mfk" : { 3029 | "full": "Gnd/Mobile Feeding Kitchen", 3030 | "desc": "Mobile Feeding Kitchen", 3031 | }, 3032 | "a-.-G-U-i-e-pac" : { 3033 | "full": "Gnd/Public Assistance Coordinator", 3034 | "desc": "Public Assistance Coordinator", 3035 | }, 3036 | "a-.-G-U-i-e-rna" : { 3037 | "full": "Gnd/Rapid Needs Assessment Team", 3038 | "desc": "Rapid Needs Assessment Team", 3039 | }, 3040 | "a-.-G-U-i-e-smt" : { 3041 | "full": "Gnd/Shelter Management Team", 3042 | "desc": "Shelter Management Team", 3043 | }, 3044 | "a-.-G-U-i-e-val" : { 3045 | "full": "Gnd/Volunteer Agency Liaison", 3046 | "desc": "Volunteer Agency Liaison", 3047 | }, 3048 | "a-.-G-U-i-m" : { 3049 | "full": "Gnd/IM Resources/Emergency Medical Services", 3050 | "desc": "Emergency Medical Services", 3051 | }, 3052 | "a-.-G-U-i-m-aaf" : { 3053 | "full": "Gnd/Air Ambulance (Fixed-Wing)", 3054 | "desc": "Air Ambulance (Fixed-Wing)", 3055 | }, 3056 | "a-.-G-U-i-m-aar" : { 3057 | "full": "Gnd/Air Ambulance (Rotary-Wing)", 3058 | "desc": "Air Ambulance (Rotary-Wing)", 3059 | }, 3060 | "a-.-G-U-i-m-ag" : { 3061 | "full": "Gnd/Ambulances (Ground)", 3062 | "desc": "Ambulances (Ground)", 3063 | }, 3064 | "a-.-G-U-i-m-ast" : { 3065 | "full": "Gnd/Ambulance Strike Team", 3066 | "desc": "Ambulance Strike Team", 3067 | }, 3068 | "a-.-G-U-i-m-atf" : { 3069 | "full": "Gnd/Ambulance Task Force", 3070 | "desc": "Ambulance Task Force", 3071 | }, 3072 | "a-.-G-U-i-m-etf" : { 3073 | "full": "Gnd/Emergency Medical Task Force", 3074 | "desc": "Emergency Medical Task Force", 3075 | }, 3076 | "a-.-G-U-i-f" : { 3077 | "full": "Gnd/IM Resources/Fire HAZMAT", 3078 | "desc": "Fire HAZMAT", 3079 | }, 3080 | "a-.-G-U-i-f-act" : { 3081 | "full": "Gnd/Area Command Team, Firefighting", 3082 | "desc": "Area Command Team, Firefighting", 3083 | }, 3084 | "a-.-G-U-i-f-bp" : { 3085 | "full": "Gnd/Brush Patrol", 3086 | "desc": "Brush Patrol", 3087 | }, 3088 | "a-.-G-U-i-f-ct" : { 3089 | "full": "Gnd/Crew Transport", 3090 | "desc": "Crew Transport", 3091 | }, 3092 | "a-.-G-U-i-f-efp" : { 3093 | "full": "Gnd/Engine, Fire (Pumper)", 3094 | "desc": "Engine, Fire (Pumper)", 3095 | }, 3096 | "a-.-G-U-i-f-fb" : { 3097 | "full": "Gnd/Fire Boat", 3098 | "desc": "Fire Boat", 3099 | }, 3100 | "a-.-G-U-i-f-ft" : { 3101 | "full": "Gnd/Fuel Tender", 3102 | "desc": "Fuel Tender", 3103 | }, 3104 | "a-.-G-U-i-f-fta" : { 3105 | "full": "Gnd/Fire Truck", 3106 | "desc": "Fire Truck", 3107 | }, 3108 | "a-.-G-U-i-f-ftf" : { 3109 | "full": "Gnd/Foam Tender", 3110 | "desc": "Foam Tender", 3111 | }, 3112 | "a-.-G-U-i-f-hc" : { 3113 | "full": "Gnd/Hand Crew", 3114 | "desc": "Hand Crew", 3115 | }, 3116 | "a-.-G-U-i-f-het" : { 3117 | "full": "Gnd/HazMat Entry Team", 3118 | "desc": "HazMat Entry Team", 3119 | }, 3120 | "a-.-G-U-i-f-hf" : { 3121 | "full": "Gnd/Helicopters Firefighting", 3122 | "desc": "Helicopters, Firefighting", 3123 | }, 3124 | "a-.-G-U-i-f-ht" : { 3125 | "full": "Gnd/Helitanker ", 3126 | "desc": "Helitanker", 3127 | }, 3128 | "a-.-G-U-i-f-imt" : { 3129 | "full": "Gnd/Incident Management Team Firefighting", 3130 | "desc": "Incident Management Team Firefighting", 3131 | }, 3132 | "a-.-G-U-i-f-ibt" : { 3133 | "full": "Gnd/Interagency Buying Team Firefighting", 3134 | "desc": "Interagency Buying Team Firefighting", 3135 | }, 3136 | "a-.-G-U-i-f-mcu" : { 3137 | "full": "Gnd/Mobile Communications Unit", 3138 | "desc": "Mobile Communications Unit", 3139 | }, 3140 | "a-.-G-U-i-f-nsf" : { 3141 | "full": "Gnd/USCG National Strike Force", 3142 | "desc": "USCG National Strike Force", 3143 | }, 3144 | "a-.-G-U-i-f-pp" : { 3145 | "full": "Gnd/Portable Pump", 3146 | "desc": "Portable Pump", 3147 | }, 3148 | "a-.-G-U-i-f-st" : { 3149 | "full": "Gnd/Strike Team, Engine (Fire)", 3150 | "desc": "Strike Team, Engine (Fire)", 3151 | }, 3152 | "a-.-G-U-i-f-wt" : { 3153 | "full": "Gnd/Water Tender, Firefighting (Tanker)", 3154 | "desc": "Water Tender, Firefighting (Tanker)", 3155 | }, 3156 | "a-.-G-U-i-h" : { 3157 | "full": "Gnd/IM Resources/Health and Medical", 3158 | "desc": "Health and Medical", 3159 | }, 3160 | "a-.-G-U-i-h-dmb" : { 3161 | "full": "Gnd/Disaster Medical Assistance Team - Basic", 3162 | "desc": "Disaster Medical Assistance Team - Basic", 3163 | }, 3164 | "a-.-G-U-i-h-dmc" : { 3165 | "full": "Gnd/Disaster Medical Assistance Team - Crush Injury Specialty", 3166 | "desc": "Disaster Medical Assistance Team - Crush Injury Specialty", 3167 | }, 3168 | "a-.-G-U-i-h-dmm" : { 3169 | "full": "Gnd/Disaster Medical Assistance Team - Mental Health", 3170 | "desc": "Disaster Medical Assistance Team - Mental Health", 3171 | }, 3172 | "a-.-G-U-i-h-dmp" : { 3173 | "full": "Gnd/Disaster Medical Assistance Team - Pediatric", 3174 | "desc": "Disaster Medical Assistance Team - Pediatric", 3175 | }, 3176 | "a-.-G-U-i-h-dms" : { 3177 | "full": "Gnd/Disaster Medical Assistance Team - Burn", 3178 | "desc": "Disaster Medical Assistance Team - Burn", 3179 | }, 3180 | "a-.-G-U-i-h-mor" : { 3181 | "full": "Gnd/Disaster Mortuary Operational Response Team", 3182 | "desc": "Disaster Mortuary Operational Response Team", 3183 | }, 3184 | "a-.-G-U-i-h-msr" : { 3185 | "full": "Gnd/International Medical Surgical Response Team", 3186 | "desc": "International Medical Surgical Response Team", 3187 | }, 3188 | "a-.-G-U-i-h-mst" : { 3189 | "full": "Gnd/NDMS Management Support Team", 3190 | "desc": "NDMS Management Support Team", 3191 | }, 3192 | "a-.-G-U-i-h-vma" : { 3193 | "full": "Gnd/Veterinary Medical Assistance Team", 3194 | "desc": "Veterinary Medical Assistance Team", 3195 | }, 3196 | "a-.-G-U-i-l" : { 3197 | "full": "Gnd/IM Resources/Law Enforcement", 3198 | "desc": "Law Enforcement", 3199 | }, 3200 | "a-.-G-U-i-l-bs" : { 3201 | "full": "Gnd/Bomb Squad Explosives Team", 3202 | "desc": "Bomb Squad Explosives Team", 3203 | }, 3204 | "a-.-G-U-i-l-cct" : { 3205 | "full": "Gnd/Crowd Control Team", 3206 | "desc": "Crowd Control Team", 3207 | }, 3208 | "a-.-G-U-i-l-dt" : { 3209 | "full": "Gnd/Public Safety Dive Team", 3210 | "desc": "Public Safety Dive Team", 3211 | }, 3212 | "a-.-G-U-i-l-hps" : { 3213 | "full": "Gnd/Aviation-Helicopters Patrol Surveillance", 3214 | "desc": "Aviation-Helicopters Patrol Surveillance", 3215 | }, 3216 | "a-.-G-U-i-l-oa" : { 3217 | "full": "Gnd/Observation Aircraft", 3218 | "desc": "Observation Aircraft", 3219 | }, 3220 | "a-.-G-U-i-l-tt" : { 3221 | "full": "Gnd/SWAT Tactical Team", 3222 | "desc": "SWAT Tactical Team", 3223 | }, 3224 | "a-.-G-U-i-p" : { 3225 | "full": "Gnd/IM Resources/Public Works", 3226 | "desc": "Public Works", 3227 | }, 3228 | "a-.-G-U-i-p-acf" : { 3229 | "full": "Gnd/Air Curtain Burners (Above Ground)", 3230 | "desc": "Air Curtain Burners (Above Ground)", 3231 | }, 3232 | "a-.-G-U-i-p-ach" : { 3233 | "full": "Gnd/Air Conditioner Heater", 3234 | "desc": "Air Conditioner Heater", 3235 | }, 3236 | "a-.-G-U-i-p-act" : { 3237 | "full": "Gnd/Air Curtain Burners (In Ground)", 3238 | "desc": "Air Curtain Burners (In Ground)", 3239 | }, 3240 | "a-.-G-U-i-p-atc" : { 3241 | "full": "Gnd/All Terrain Cranes", 3242 | "desc": "All Terrain Cranes", 3243 | }, 3244 | "a-.-G-U-i-p-bh" : { 3245 | "full": "Gnd/Backhoe Loader", 3246 | "desc": "Backhoe Loader", 3247 | }, 3248 | "a-.-G-U-i-p-cah" : { 3249 | "full": "Gnd/Chillers Air Handlers", 3250 | "desc": "Chillers Air Handlers", 3251 | }, 3252 | "a-.-G-U-i-p-cc" : { 3253 | "full": "Gnd/Crawler Cranes", 3254 | "desc": "Crawler Cranes", 3255 | }, 3256 | "a-.-G-U-i-p-cce" : { 3257 | "full": "Gnd/Concrete Cutter Multi-Processor for Hydraulic Excavator", 3258 | "desc": "Concrete Cutter Multi-Processor for Hydraulic Excavator", 3259 | }, 3260 | "a-.-G-U-i-p-dat" : { 3261 | "full": "Gnd/Disaster Assessment Team", 3262 | "desc": "Disaster Assessment Team", 3263 | }, 3264 | "a-.-G-U-i-p-dmm" : { 3265 | "full": "Gnd/Debris Management Monitoring Team", 3266 | "desc": "Debris Management Monitoring Team", 3267 | }, 3268 | "a-.-G-U-i-p-dmr" : { 3269 | "full": "Gnd/Debris Management Site Reduction Team", 3270 | "desc": "Debris Management Site Reduction Team", 3271 | }, 3272 | "a-.-G-U-i-p-dmt" : { 3273 | "full": "Gnd/Debris Management Team", 3274 | "desc": "Debris Management Team", 3275 | }, 3276 | "a-.-G-U-i-p-drt" : { 3277 | "full": "Gnd/Disaster Recovery Team", 3278 | "desc": "Disaster Recovery Team", 3279 | }, 3280 | "a-.-G-U-i-p-dt" : { 3281 | "full": "Gnd/Dump Trailer", 3282 | "desc": "Dump Trailer", 3283 | }, 3284 | "a-.-G-U-i-p-dtf" : { 3285 | "full": "Gnd/Dump Truck Off Road", 3286 | "desc": "Dump Truck Off Road", 3287 | }, 3288 | "a-.-G-U-i-p-dtn" : { 3289 | "full": "Gnd/Dump Truck On Road", 3290 | "desc": "Dump Truck On Road", 3291 | }, 3292 | "a-.-G-U-i-p-epr" : { 3293 | "full": "Gnd/Electrical Power Restoration Team", 3294 | "desc": "Electrical Power Restoration Team", 3295 | }, 3296 | "a-.-G-U-i-p-es" : { 3297 | "full": "Gnd/Engineering Services", 3298 | "desc": "Engineering Services", 3299 | }, 3300 | "a-.-G-U-i-p-fbt" : { 3301 | "full": "Gnd/Flat Bed Trailer Truck", 3302 | "desc": "Flat Bed Trailer Truck", 3303 | }, 3304 | "a-.-G-U-i-p-gen" : { 3305 | "full": "Gnd/Generators ", 3306 | "desc": "Generators", 3307 | }, 3308 | "a-.-G-U-i-p-hel" : { 3309 | "full": "Gnd/Hydraulic Excavator (Large)", 3310 | "desc": "Hydraulic Excavator (Large)", 3311 | }, 3312 | "a-.-G-U-i-p-hem" : { 3313 | "full": "Gnd/Hydraulic Excavator (Medium)", 3314 | "desc": "Hydraulic Excavator (Medium)", 3315 | }, 3316 | "a-.-G-U-i-p-htc" : { 3317 | "full": "Gnd/Hydraulic Truck Cranes", 3318 | "desc": "Hydraulic Truck Cranes", 3319 | }, 3320 | "a-.-G-U-i-p-ltc" : { 3321 | "full": "Gnd/Lattice Truck Cranes", 3322 | "desc": "Lattice Truck Cranes", 3323 | }, 3324 | "a-.-G-U-i-p-tb" : { 3325 | "full": "Gnd/Tug Boat", 3326 | "desc": "Tug Boat", 3327 | }, 3328 | "a-.-G-U-i-p-td" : { 3329 | "full": "Gnd/Track Dozer", 3330 | "desc": "Track Dozer", 3331 | }, 3332 | "a-.-G-U-i-p-tg" : { 3333 | "full": "Gnd/Tub Grinder", 3334 | "desc": "Tub Grinder", 3335 | }, 3336 | "a-.-G-U-i-p-tt" : { 3337 | "full": "Gnd/Tractor Trailer", 3338 | "desc": "Tractor Trailer", 3339 | }, 3340 | "a-.-G-U-i-p-wd" : { 3341 | "full": "Gnd/Wheel Dozer", 3342 | "desc": "Wheel Dozer", 3343 | }, 3344 | "a-.-G-U-i-p-wll" : { 3345 | "full": "Gnd/Wheel Loaders (Large)", 3346 | "desc": "Wheel Loaders (Large)", 3347 | }, 3348 | "a-.-G-U-i-p-wlm" : { 3349 | "full": "Gnd/Wheel Loaders (Medium)", 3350 | "desc": "Wheel Loaders (Medium)", 3351 | }, 3352 | "a-.-G-U-i-p-wls" : { 3353 | "full": "Gnd/Wheel Loaders (Small)", 3354 | "desc": "Wheel Loaders (Small)", 3355 | }, 3356 | "a-.-G-U-i-p-wpt" : { 3357 | "full": "Gnd/Water Purification Team", 3358 | "desc": "Water Purification Team", 3359 | }, 3360 | "a-.-G-U-i-p-wt" : { 3361 | "full": "Gnd/Water Truck", 3362 | "desc": "Water Truck", 3363 | }, 3364 | "a-.-G-U-i-s" : { 3365 | "full": "Gnd/IM Resources/Search and Rescue", 3366 | "desc": "Search and Rescue", 3367 | }, 3368 | "a-.-G-U-i-s-ar" : { 3369 | "full": "Gnd/Airborne Reconnaissance", 3370 | "desc": "Airborne Reconnaissance", 3371 | }, 3372 | "a-.-G-U-i-s-ast" : { 3373 | "full": "Gnd/Air Search Team", 3374 | "desc": "Air Search Team", 3375 | }, 3376 | "a-.-G-U-i-s-cas" : { 3377 | "full": "Gnd/Canine SAR Team Avalanche Snow", 3378 | "desc": "Canine SAR Team Avalanche Snow", 3379 | }, 3380 | "a-.-G-U-i-s-cav" : { 3381 | "full": "Gnd/Cave SAR Team", 3382 | "desc": "Cave SAR Team", 3383 | }, 3384 | "a-.-G-U-i-s-cdr" : { 3385 | "full": "Gnd/Canine SAR Team Disaster Response", 3386 | "desc": "Canine SAR Team Disaster Response", 3387 | }, 3388 | "a-.-G-U-i-s-clc" : { 3389 | "full": "Gnd/Canine SAR Team Land Cadaver", 3390 | "desc": "Canine SAR Team Land Cadaver", 3391 | }, 3392 | "a-.-G-U-i-s-col" : { 3393 | "full": "Gnd/Collapse SAR Team", 3394 | "desc": "Collapse SAR Team", 3395 | }, 3396 | "a-.-G-U-i-s-cwa" : { 3397 | "full": "Gnd/Canine SAR Team Water", 3398 | "desc": "Canine SAR Team Water", 3399 | }, 3400 | "a-.-G-U-i-s-cwi" : { 3401 | "full": "Gnd/Canine SAR Team Wilderness", 3402 | "desc": "Canine SAR Team Wilderness", 3403 | }, 3404 | "a-.-G-U-i-s-cwt" : { 3405 | "full": "Gnd/Canine SAR Team Wilderness Tracking", 3406 | "desc": "Canine SAR Team Wilderness Tracking", 3407 | }, 3408 | "a-.-G-U-i-s-mt" : { 3409 | "full": "Gnd/Mine Tunnel SAR Team", 3410 | "desc": "Mine Tunnel SAR Team", 3411 | }, 3412 | "a-.-G-U-i-s-mnt" : { 3413 | "full": "Gnd/Mountain SAR Team", 3414 | "desc": "Mountain SAR Team", 3415 | }, 3416 | "a-.-G-U-i-s-rdf" : { 3417 | "full": "Gnd/Radio Direction Finding Team", 3418 | "desc": "Radio Direction Finding Team", 3419 | }, 3420 | "a-.-G-U-i-s-sfd" : { 3421 | "full": "Gnd/Swiftwater Flood Search and Dive Rescue Team", 3422 | "desc": "Swiftwater Flood Search and Dive Rescue Team", 3423 | }, 3424 | "a-.-G-U-i-s-uis" : { 3425 | "full": "Gnd/USAR Incident Support Team", 3426 | "desc": "USAR Incident Support Team", 3427 | }, 3428 | "a-.-G-U-i-s-utf" : { 3429 | "full": "Gnd/USAR Task Force", 3430 | "desc": "USAR Task Force", 3431 | }, 3432 | "a-.-G-U-i-s-wi" : { 3433 | "full": "Gnd/Wilderness SAR Team", 3434 | "desc": "Wilderness SAR Team", 3435 | }, 3436 | "a-.-G-U-i-o" : { 3437 | "full": "Gnd/IM Resources/Other", 3438 | "desc": "Other", 3439 | }, 3440 | "a-.-S" : { 3441 | "full": "Surface/SEA SURFACE TRACK", 3442 | "desc": "SEA SURFACE TRACK", 3443 | }, 3444 | "a-.-S-C" : { 3445 | "full": "Surface/COMBATANT", 3446 | "desc": "COMBATANT", 3447 | }, 3448 | "a-.-S-C-A" : { 3449 | "full": "Surface/AMPHIBIOUS WARFARE SHIP", 3450 | "desc": "AMPHIBIOUS WARFARE SHIP", 3451 | }, 3452 | "a-.-S-C-A-L-A" : { 3453 | "full": "Surface/ASSAULT VESSEL", 3454 | "desc": "ASSAULT VESSEL", 3455 | }, 3456 | "a-.-S-C-A-L-C" : { 3457 | "full": "Surface/LANDING CRAFT", 3458 | "desc": "LANDING CRAFT", 3459 | }, 3460 | "a-.-S-C-A-L-S" : { 3461 | "full": "Surface/LANDING SHIP", 3462 | "desc": "LANDING SHIP", 3463 | }, 3464 | "a-.-S-C-H" : { 3465 | "full": "Surface/HOVERCRAFT", 3466 | "desc": "HOVERCRAFT", 3467 | }, 3468 | "a-.-S-C-L" : { 3469 | "full": "Surface/LINE", 3470 | "desc": "LINE", 3471 | }, 3472 | "a-.-S-C-L-B-B" : { 3473 | "full": "Surface/BATTLESHIP", 3474 | "desc": "BATTLESHIP", 3475 | }, 3476 | "a-.-S-C-L-C-C" : { 3477 | "full": "Surface/CRUISER", 3478 | "desc": "CRUISER", 3479 | }, 3480 | "a-.-S-C-L-C-V" : { 3481 | "full": "Surface/CARRIER", 3482 | "desc": "CARRIER", 3483 | }, 3484 | "a-.-S-C-L-D-D" : { 3485 | "full": "Surface/DESTROYER", 3486 | "desc": "DESTROYER", 3487 | }, 3488 | "a-.-S-C-L-F-F" : { 3489 | "full": "Surface/FRIGATE/CORVETTE", 3490 | "desc": "FRIGATE/CORVETTE", 3491 | }, 3492 | "a-.-S-C-M" : { 3493 | "full": "Surface/MINE WARFARE VESSEL", 3494 | "desc": "MINE WARFARE VESSEL", 3495 | }, 3496 | "a-.-S-C-M-M-A" : { 3497 | "full": "Surface/MCM SUPPORT", 3498 | "desc": "MCM SUPPORT", 3499 | }, 3500 | "a-.-S-C-M-M-D" : { 3501 | "full": "Surface/MCM DRONE", 3502 | "desc": "MCM DRONE", 3503 | }, 3504 | "a-.-S-C-M-M-H" : { 3505 | "full": "Surface/MINEHUNTER", 3506 | "desc": "MINEHUNTER", 3507 | }, 3508 | "a-.-S-C-M-M-L" : { 3509 | "full": "Surface/MINELAYER", 3510 | "desc": "MINELAYER", 3511 | }, 3512 | "a-.-S-C-M-M-S" : { 3513 | "full": "Surface/MINESWEEPER", 3514 | "desc": "MINESWEEPER", 3515 | }, 3516 | "a-.-S-C-P" : { 3517 | "full": "Surface/PATROL", 3518 | "desc": "PATROL", 3519 | }, 3520 | "a-.-S-C-P-S-B" : { 3521 | "full": "Surface/ANTISUBMARINE WARFARE", 3522 | "desc": "ANTISUBMARINE WARFARE", 3523 | }, 3524 | "a-.-S-C-P-S-U" : { 3525 | "full": "Surface/ANTISURFACE WARFARE", 3526 | "desc": "ANTISURFACE WARFARE", 3527 | }, 3528 | "a-.-S-G" : { 3529 | "full": "Surface/NAVY GROUP", 3530 | "desc": "NAVY GROUP", 3531 | }, 3532 | "a-.-S-G-C" : { 3533 | "full": "Surface/CONVOY", 3534 | "desc": "CONVOY", 3535 | }, 3536 | "a-.-S-G-G" : { 3537 | "full": "Surface/NAVY TASK GROUP", 3538 | "desc": "NAVY TASK GROUP", 3539 | }, 3540 | "a-.-S-G-T" : { 3541 | "full": "Surface/NAVY TASK FORCE", 3542 | "desc": "NAVY TASK FORCE", 3543 | }, 3544 | "a-.-S-G-U" : { 3545 | "full": "Surface/NAVY TASK UNIT", 3546 | "desc": "NAVY TASK UNIT", 3547 | }, 3548 | "a-.-S-N" : { 3549 | "full": "Surface/NONCOMBATANT", 3550 | "desc": "NONCOMBATANT", 3551 | }, 3552 | "a-.-S-N-F" : { 3553 | "full": "Surface/FLEET SUPPORT", 3554 | "desc": "FLEET SUPPORT", 3555 | }, 3556 | "a-.-S-N-H" : { 3557 | "full": "Surface/HOVERCRAFT", 3558 | "desc": "HOVERCRAFT", 3559 | }, 3560 | "a-.-S-N-I" : { 3561 | "full": "Surface/INTELLIGENCE", 3562 | "desc": "INTELLIGENCE", 3563 | }, 3564 | "a-.-S-N-M" : { 3565 | "full": "Surface/HOSPITAL SHIP", 3566 | "desc": "HOSPITAL SHIP", 3567 | }, 3568 | "a-.-S-N-N" : { 3569 | "full": "Surface/STATION", 3570 | "desc": "STATION", 3571 | }, 3572 | "a-.-S-N-N-R" : { 3573 | "full": "Surface/RESCUE", 3574 | "desc": "RESCUE", 3575 | }, 3576 | "a-.-S-N-R" : { 3577 | "full": "Surface/UNDERWAY REPLENISHMENT", 3578 | "desc": "UNDERWAY REPLENISHMENT", 3579 | }, 3580 | "a-.-S-N-S" : { 3581 | "full": "Surface/SERVICE/SUPPORT HARBOR", 3582 | "desc": "SERVICE/SUPPORT HARBOR", 3583 | }, 3584 | "a-.-S-O" : { 3585 | "full": "Surface/OWN TRACK", 3586 | "desc": "OWN TRACK", 3587 | }, 3588 | "a-.-S-S" : { 3589 | "full": "Surface/STATION", 3590 | "desc": "STATION", 3591 | }, 3592 | "a-.-S-S-A" : { 3593 | "full": "Surface/ASW SHIP", 3594 | "desc": "ASW SHIP", 3595 | }, 3596 | "a-.-S-S-P" : { 3597 | "full": "Surface/PICKET", 3598 | "desc": "PICKET", 3599 | }, 3600 | "a-.-S-X" : { 3601 | "full": "Surface/NON MILITARY", 3602 | "desc": "NON MILITARY", 3603 | }, 3604 | "a-.-S-X-F" : { 3605 | "full": "Surface/FISHING", 3606 | "desc": "FISHING", 3607 | }, 3608 | "a-.-S-X-F-D-F" : { 3609 | "full": "Surface/DRIFTER", 3610 | "desc": "DRIFTER", 3611 | }, 3612 | "a-.-S-X-F-D-R" : { 3613 | "full": "Surface/DREDGE", 3614 | "desc": "DREDGE", 3615 | }, 3616 | "a-.-S-X-F-T-R" : { 3617 | "full": "Surface/TRAWLER", 3618 | "desc": "TRAWLER", 3619 | }, 3620 | "a-.-S-X-H" : { 3621 | "full": "Surface/HOVERCRAFT", 3622 | "desc": "HOVERCRAFT", 3623 | }, 3624 | "a-.-S-X-L" : { 3625 | "full": "Surface/LAW ENFORCEMENT VESSEL", 3626 | "desc": "LAW ENFORCEMENT VESSEL", 3627 | }, 3628 | "a-.-S-X-M" : { 3629 | "full": "Surface/MERCHANT", 3630 | "desc": "MERCHANT", 3631 | }, 3632 | "a-.-S-X-M-C" : { 3633 | "full": "Surface/CARGO", 3634 | "desc": "CARGO", 3635 | }, 3636 | "a-.-S-X-M-F" : { 3637 | "full": "Surface/FERRY", 3638 | "desc": "FERRY", 3639 | }, 3640 | "a-.-S-X-M-H" : { 3641 | "full": "Surface/HAZARDOUS MATERIALS (HAZMAT)", 3642 | "desc": "HAZARDOUS MATERIALS (HAZMAT)", 3643 | }, 3644 | "a-.-S-X-M-O" : { 3645 | "full": "Surface/OILER/TANKER", 3646 | "desc": "OILER/TANKER", 3647 | }, 3648 | "a-.-S-X-M-P" : { 3649 | "full": "Surface/PASSENGER", 3650 | "desc": "PASSENGER", 3651 | }, 3652 | "a-.-S-X-M-R" : { 3653 | "full": "Surface/ROLL ON/ROLL OFF", 3654 | "desc": "ROLL ON/ROLL OFF", 3655 | }, 3656 | "a-.-S-X-M-T-O" : { 3657 | "full": "Surface/TOWING VESSEL", 3658 | "desc": "TOWING VESSEL", 3659 | }, 3660 | "a-.-S-X-M-T-U" : { 3661 | "full": "Surface/TUG", 3662 | "desc": "TUG", 3663 | }, 3664 | "a-.-S-X-R" : { 3665 | "full": "Surface/LEISURE CRAFT", 3666 | "desc": "LEISURE CRAFT", 3667 | }, 3668 | "a-.-U" : { 3669 | "full": "SubSurf/SUBSURFACE TRACK", 3670 | "desc": "SUBSURFACE TRACK", 3671 | }, 3672 | "a-.-U-N" : { 3673 | "full": "SubSurf/NON SUBMARINE", 3674 | "desc": "NON SUBMARINE", 3675 | }, 3676 | "a-.-U-N-D" : { 3677 | "full": "SubSurf/DIVER", 3678 | "desc": "DIVER", 3679 | }, 3680 | "a-.-U-S" : { 3681 | "full": "SubSurf/SUBMARINE", 3682 | "desc": "SUBMARINE", 3683 | }, 3684 | "a-.-U-S-C" : { 3685 | "full": "SubSurf/SUBMARINE CONVENTIONAL PROPULSION", 3686 | "desc": "SUBMARINE CONVENTIONAL PROPULSION", 3687 | }, 3688 | "a-.-U-S-N" : { 3689 | "full": "SubSurf/SUBMARINE NUCLEAR PROPULSION", 3690 | "desc": "SUBMARINE NUCLEAR PROPULSION", 3691 | }, 3692 | "a-.-U-S-O" : { 3693 | "full": "SubSurf/OTHER SUBMERSIBLE", 3694 | "desc": "OTHER SUBMERSIBLE", 3695 | }, 3696 | "a-.-U-S-S" : { 3697 | "full": "SubSurf/STATION", 3698 | "desc": "STATION", 3699 | }, 3700 | "a-.-U-S-S-A" : { 3701 | "full": "SubSurf/ASW SUBMARINE", 3702 | "desc": "ASW SUBMARINE", 3703 | }, 3704 | "a-.-U-S-U" : { 3705 | "full": "SubSurf/UNMANNED UNDERWATER VEHICLE (UUV)", 3706 | "desc": "UNMANNED UNDERWATER VEHICLE (UUV)", 3707 | }, 3708 | "a-.-U-W" : { 3709 | "full": "SubSurf/UNDERWATER WEAPON", 3710 | "desc": "UNDERWATER WEAPON", 3711 | }, 3712 | "a-.-U-W-D" : { 3713 | "full": "SubSurf/UNDERWATER DECOY", 3714 | "desc": "UNDERWATER DECOY", 3715 | }, 3716 | "a-.-U-W-D-M" : { 3717 | "full": "SubSurf/SEA MINE DECOY", 3718 | "desc": "SEA MINE DECOY", 3719 | }, 3720 | "a-.-U-W-M" : { 3721 | "full": "SubSurf/SEA MINE", 3722 | "desc": "SEA MINE", 3723 | }, 3724 | "a-.-U-W-M-D" : { 3725 | "full": "SubSurf/SEA MINE DEALT", 3726 | "desc": "SEA MINE DEALT", 3727 | }, 3728 | "a-.-U-W-M-F" : { 3729 | "full": "SubSurf/SEA MINE (FLOATING)", 3730 | "desc": "SEA MINE (FLOATING)", 3731 | }, 3732 | "a-.-U-W-M-F-D" : { 3733 | "full": "SubSurf/SEA MINE (FLOATING) DEALT", 3734 | "desc": "SEA MINE (FLOATING) DEALT", 3735 | }, 3736 | "a-.-U-W-M-G" : { 3737 | "full": "SubSurf/SEA MINE (GROUND)", 3738 | "desc": "SEA MINE (GROUND)", 3739 | }, 3740 | "a-.-U-W-M-G-D" : { 3741 | "full": "SubSurf/SEA MINE (GROUND) DEALT", 3742 | "desc": "SEA MINE (GROUND) DEALT", 3743 | }, 3744 | "a-.-U-W-M-M" : { 3745 | "full": "SubSurf/SEA MINE (MOORED)", 3746 | "desc": "SEA MINE (MOORED)", 3747 | }, 3748 | "a-.-U-W-M-M-D" : { 3749 | "full": "SubSurf/SEA MINE (MOORED) DEALT", 3750 | "desc": "SEA MINE (MOORED) DEALT", 3751 | }, 3752 | "a-.-U-W-M-O" : { 3753 | "full": "SubSurf/SEA MINE (IN OTHER POSITION)", 3754 | "desc": "SEA MINE (IN OTHER POSITION)", 3755 | }, 3756 | "a-.-U-W-M-O-D" : { 3757 | "full": "SubSurf/SEA MINE (IN OTHER POSITION) DEALT", 3758 | "desc": "SEA MINE (IN OTHER POSITION) DEALT", 3759 | }, 3760 | "a-.-U-W-T" : { 3761 | "full": "SubSurf/TORPEDO", 3762 | "desc": "TORPEDO", 3763 | }, 3764 | "a-.-X" : { 3765 | "full": "Other", 3766 | "desc": "Other", 3767 | }, 3768 | "a-.-X-i" : { 3769 | "full": "Other/INCIDENT", 3770 | "desc": "Incident", 3771 | }, 3772 | "a-.-X-i-g" : { 3773 | "full": "Other/INCIDENT/GEO", 3774 | "desc": "Geophysical", 3775 | }, 3776 | "a-.-X-i-g-a" : { 3777 | "full": "Other/INCIDENT/GEO/AVALANCHE", 3778 | "desc": "Geophysical Avalanche", 3779 | }, 3780 | "a-.-X-i-g-e" : { 3781 | "full": "Other/INCIDENT/GEO/EARTHQUAKE", 3782 | "desc": "Geophysical Earthquake", 3783 | }, 3784 | "a-.-X-i-g-e-a" : { 3785 | "full": "Other/INCIDENT/GEO/AFTERSHOCK", 3786 | "desc": "Geophysical Earthquake Aftershock", 3787 | }, 3788 | "a-.-X-i-g-e-e" : { 3789 | "full": "Other/INCIDENT/GEO/EPICENTER", 3790 | "desc": "Geophysical Earthquake Epicenter", 3791 | }, 3792 | "a-.-X-i-g-l" : { 3793 | "full": "Other/INCIDENT/GEO/LANDSLIDE", 3794 | "desc": "Geophysical Landslide", 3795 | }, 3796 | "a-.-X-i-g-s" : { 3797 | "full": "Other/INCIDENT/GEO/SUBSISTANCE", 3798 | "desc": "Geophysical Subsistance", 3799 | }, 3800 | "a-.-X-i-g-v" : { 3801 | "full": "Other/INCIDENT/GEO/VOLCANO", 3802 | "desc": "Geophysical Volcano", 3803 | }, 3804 | "a-.-X-i-g-v-e" : { 3805 | "full": "Other/INCIDENT/GEO/ERUPTION", 3806 | "desc": "Geophysical Volcano Eruption", 3807 | }, 3808 | "a-.-X-i-g-v-t" : { 3809 | "full": "Other/INCIDENT/GEO/VOLCANO THREAT", 3810 | "desc": "Geophysical Volcano Threat", 3811 | }, 3812 | "a-.-X-i-m" : { 3813 | "full": "Other/INCIDENT/MET", 3814 | "desc": "Meteorological", 3815 | }, 3816 | "a-.-X-i-m-z" : { 3817 | "full": "Other/INCIDENT/MET/DRIZZLE", 3818 | "desc": "Meteorological Drizzle", 3819 | }, 3820 | "a-.-X-i-m-d" : { 3821 | "full": "Other/INCIDENT/MET/DROUGHT", 3822 | "desc": "Meteorological Drought", 3823 | }, 3824 | "a-.-X-i-m-f" : { 3825 | "full": "Other/INCIDENT/MET/FLOOD", 3826 | "desc": "Meteorological Flood", 3827 | }, 3828 | "a-.-X-i-m-g" : { 3829 | "full": "Other/INCIDENT/MET/FOG", 3830 | "desc": "Meteorological Fog", 3831 | }, 3832 | "a-.-X-i-m-h" : { 3833 | "full": "Other/INCIDENT/MET/HAIL", 3834 | "desc": "Meteorological Hail", 3835 | }, 3836 | "a-.-X-i-m-i" : { 3837 | "full": "Other/INCIDENT/MET/INVERSION", 3838 | "desc": "Meteorological Inversion", 3839 | }, 3840 | "a-.-X-i-m-r" : { 3841 | "full": "Other/INCIDENT/MET/RAIN", 3842 | "desc": "Meteorological Rain", 3843 | }, 3844 | "a-.-X-i-m-a" : { 3845 | "full": "Other/INCIDENT/MET/SANDSTORM", 3846 | "desc": "Meteorological Sandstorm", 3847 | }, 3848 | "a-.-X-i-m-s" : { 3849 | "full": "Other/INCIDENT/MET/SNOW", 3850 | "desc": "Meteorological Snow", 3851 | }, 3852 | "a-.-X-i-m-u" : { 3853 | "full": "Other/INCIDENT/METTHUNDERSTORM", 3854 | "desc": "Meteorological Thunderstorm", 3855 | }, 3856 | "a-.-X-i-m-t" : { 3857 | "full": "Other/INCIDENT/MET/TORNADO", 3858 | "desc": "Meteorological Tornado", 3859 | }, 3860 | "a-.-X-i-m-c" : { 3861 | "full": "Other/INCIDENT/MET/CYCLONE", 3862 | "desc": "Meteorological Cyclone", 3863 | }, 3864 | "a-.-X-i-m-n" : { 3865 | "full": "Other/INCIDENT/MET/TSUNAMI", 3866 | "desc": "Meteorological Tsunami", 3867 | }, 3868 | "a-.-X-i-s" : { 3869 | "full": "Other/INCIDENT/SAFETY", 3870 | "desc": "Safety", 3871 | }, 3872 | "a-.-X-i-l" : { 3873 | "full": "Other/INCIDENT/SECURITY", 3874 | "desc": "Security", 3875 | }, 3876 | "a-.-X-i-l-c" : { 3877 | "full": "Other/INCIDENT/SECURITY/CIVIL DISTURB", 3878 | "desc": "Security Civil Disturbance", 3879 | }, 3880 | "a-.-X-i-l-c-d" : { 3881 | "full": "Other/INCIDENT/SECURITY/CIVIL DISTURB/DEMONSTRATION", 3882 | "desc": "Security Civil Disturbance Demonstration", 3883 | }, 3884 | "a-.-X-i-l-c-p" : { 3885 | "full": "Other/INCIDENT/SECURITY/CIVIL DISTURB/DISPLACED", 3886 | "desc": "Security Civil Disturbance Displaced Population", 3887 | }, 3888 | "a-.-X-i-l-c-r" : { 3889 | "full": "Other/INCIDENT/SECURITY/CIVIL DISTURB/RIOTING", 3890 | "desc": "Security Civil Disturbance Rioting", 3891 | }, 3892 | "a-.-X-i-l-l" : { 3893 | "full": "Other/INCIDENT/SECURITY/LAW ENFORCEMENT", 3894 | "desc": "Security Law Enforcement Activity", 3895 | }, 3896 | "a-.-X-i-l-l-b" : { 3897 | "full": "Other/INCIDENT/SECURITY/LAW ENFORCEMENT/BOMBING", 3898 | "desc": "Security Law Enforcement Activity Bombing", 3899 | }, 3900 | "a-.-X-i-l-l-b-e" : { 3901 | "full": "Other/INCIDENT/SECURITY/LAW ENFORCEMENT/BOMB EXPLOSION", 3902 | "desc": "Security Law Enforcement Activity Bombing Explosion", 3903 | }, 3904 | "a-.-X-i-l-l-b-t" : { 3905 | "full": "Other/INCIDENT/SECURITY/LAW ENFORCEMENTBOMB THREAT", 3906 | "desc": "Security Law Enforcement Activity Bombing Threat", 3907 | }, 3908 | "a-.-X-i-l-l-l" : { 3909 | "full": "Other/INCIDENT/SECURITY/LAW ENFORCEMENT/LOOTING", 3910 | "desc": "Security Law Enforcement Activity Looting", 3911 | }, 3912 | "a-.-X-i-l-l-p" : { 3913 | "full": "Other/INCIDENT/SECURITY/LAW ENFORCEMENT/POISONING", 3914 | "desc": "Security Law Enforcement Activity Poisoning", 3915 | }, 3916 | "a-.-X-i-l-l-s" : { 3917 | "full": "Other/INCIDENT/SECURITY/LAW ENFORCEMENT/SHOOTING", 3918 | "desc": "Security Law Enforcement Activity Shooting", 3919 | }, 3920 | "a-.-X-i-r" : { 3921 | "full": "Other/INCIDENT/RESCUE", 3922 | "desc": "Rescue", 3923 | }, 3924 | "a-.-X-i-f" : { 3925 | "full": "Other/INCIDENT/FIRE", 3926 | "desc": "Incident Fire", 3927 | }, 3928 | "a-.-X-i-f-w" : { 3929 | "full": "Other/INCIDENT/FIRE/WILD", 3930 | "desc": "Incident Fire Wild", 3931 | }, 3932 | "a-.-X-i-f-n" : { 3933 | "full": "Other/INCIDENT/FIRE/NON RESIDENTIAL", 3934 | "desc": "Incident Fire Non-residential", 3935 | }, 3936 | "a-.-X-i-f-n-h" : { 3937 | "full": "Other/INCIDENT/FIRE/NON RESIDENTIAL SPECIAL NEED", 3938 | "desc": "Incident Fire Non-residential Special Need", 3939 | }, 3940 | "a-.-X-i-f-n-s" : { 3941 | "full": "Other/INCIDENT/FIRE/NON RESIDENTIAL SCHOOL", 3942 | "desc": "Incident Fire Non-residential School", 3943 | }, 3944 | "a-.-X-i-f-r" : { 3945 | "full": "Other/INCIDENT/FIRE/RESIDENTIAL", 3946 | "desc": "Incident Fire Residential", 3947 | }, 3948 | "a-.-X-i-f-h" : { 3949 | "full": "Other/INCIDENT/FIRE/HOT SPOT", 3950 | "desc": "Incident Fire Hot Spot", 3951 | }, 3952 | "a-.-X-i-f-o" : { 3953 | "full": "Other/INCIDENT/FIRE/ORIGIN", 3954 | "desc": "Incident Fire Origin", 3955 | }, 3956 | "a-.-X-i-f-s" : { 3957 | "full": "Other/INCIDENT/FIRE/SMOKE", 3958 | "desc": "Incident Fire Smoke", 3959 | }, 3960 | "a-.-X-i-f-p" : { 3961 | "full": "Other/INCIDENT/FIRE/SPECIAL NEEDS", 3962 | "desc": "Incident Fire Special Needs", 3963 | }, 3964 | "a-.-X-i-h" : { 3965 | "full": "Other/INCIDENT/MEDICAL PUBLIC HEALTH", 3966 | "desc": "Medical and Public Health", 3967 | }, 3968 | "a-.-X-i-e" : { 3969 | "full": "Other/INCIDENT/POLLUTION ENVIRONMENTAL", 3970 | "desc": "Pollution and other Environmental", 3971 | }, 3972 | "a-.-X-i-t" : { 3973 | "full": "Other/INCIDENT/TRANSPORTATION/", 3974 | "desc": "Public and Private transportation", 3975 | }, 3976 | "a-.-X-i-t-a" : { 3977 | "full": "Other/INCIDENT/TRANSPORTATION/AIR", 3978 | "desc": "Public and Private transportation Air Incident", 3979 | }, 3980 | "a-.-X-i-t-a-a" : { 3981 | "full": "Other/INCIDENT/TRANSPORTATION/AIR ACCIDENT", 3982 | "desc": "Public and Private transportation Air Accident", 3983 | }, 3984 | "a-.-X-i-t-a-h" : { 3985 | "full": "Other/INCIDENT/TRANSPORTATION/AIR HIJACKING", 3986 | "desc": "Public and Private transportation Air Hijacking", 3987 | }, 3988 | "a-.-X-i-t-m" : { 3989 | "full": "Other/INCIDENT/TRANSPORTATION/MARITIME", 3990 | "desc": "Public and Private transportation Maritime Incident", 3991 | }, 3992 | "a-.-X-i-t-m-a" : { 3993 | "full": "Other/INCIDENT/TRANSPORTATION/MARITIME ACCIDENT", 3994 | "desc": "Public and Private transportation Maritime Accident", 3995 | }, 3996 | "a-.-X-i-t-m-h" : { 3997 | "full": "Other/INCIDENT/TRANSPORTATION/MARITIME HIJACKING", 3998 | "desc": "Public and Private transportation Maritime Hijacking", 3999 | }, 4000 | "a-.-X-i-t-r" : { 4001 | "full": "Other/INCIDENT/TRANSPORTATION/RAIL", 4002 | "desc": "Public and Private transportation Rail Incident", 4003 | }, 4004 | "a-.-X-i-t-r-a" : { 4005 | "full": "Other/INCIDENT/TRANSPORTATION/RAIL ACCIDENT", 4006 | "desc": "Public and Private transportation Rail Accident", 4007 | }, 4008 | "a-.-X-i-t-r-h" : { 4009 | "full": "Other/INCIDENT/TRANSPORTATION/RAIL HIJACKING", 4010 | "desc": "Public and Private transportation Rail Hijacking", 4011 | }, 4012 | "a-.-X-i-t-v" : { 4013 | "full": "Other/INCIDENT/TRANSPORTATION/VEHICLE", 4014 | "desc": "Public and Private transportation Vehicle Incident", 4015 | }, 4016 | "a-.-X-i-t-v-a" : { 4017 | "full": "Other/INCIDENT/TRANSPORTATION/VEHICLE ACCIDENT", 4018 | "desc": "Public and Private transportation Vehicle Accident", 4019 | }, 4020 | "a-.-X-i-t-v-h" : { 4021 | "full": "Other/INCIDENT/TRANSPORTATION/VEHICLE HIJACKING", 4022 | "desc": "Public and Private transportation Vehicle Hijacking", 4023 | }, 4024 | "a-.-X-i-i" : { 4025 | "full": "Other/INCIDENT/INFRASTRUCTURE", 4026 | "desc": "Infrastructure", 4027 | }, 4028 | "a-.-X-i-c" : { 4029 | "full": "Other/INCIDENT/CBRNE", 4030 | "desc": "CBRNE", 4031 | }, 4032 | "a-.-X-i-o" : { 4033 | "full": "Other/INCIDENT/OTHER", 4034 | "desc": "Other", 4035 | }, 4036 | } 4037 | 4038 | # https://github.com/FreeTAKTeam/FreeTakServer/blob/master/FreeTAKServer/model/RestMessages/RestEnumerations.py#L199-L230 4039 | # https://github.com/deptofdefense/AndroidTacticalAssaultKit-CIV/blob/889eee292c43d3d2eafdd1f2fbf378ad5cd89ecc/takcot/mitre/types.txt 4040 | 4041 | CoTHow = { 4042 | # Human entered or modified coordinates 4043 | "h": "human", # human entered or modified (someone typed the coordinates) 4044 | "h-e": "estimated", # estimated (a SWAG by the user) 4045 | "h-c": "calculated", # calculated (user probably calculated value by hand) 4046 | "h-t": "transcribed", # transcribed (from voice, paper, ...) 4047 | "h-p": "pasted", # cut and paste from another window 4048 | "h-g-i-g-o": "gigo", # a highly suspect track... e.g., TACP-M ;-) 4049 | 4050 | # Machine generated coordinates 4051 | "m": "machine", # machine generated 4052 | "m-a": "algorithmic", # prediction from an algorithmic tracker 4053 | "m-c": "configured", # out of a configuration file 4054 | "m-f": "fused", # corroborated from multiple sources 4055 | "m-g": "gps", # derived from GPS receiver 4056 | "m-g-n": "ins+gps", # augmented INS+GPS 4057 | "m-g-d": "dgps", # differential GPS 4058 | "m-i": "mensurated", # mensurated (from imagery) 4059 | "m-l": "laser", # laser designated 4060 | "m-m": "magnetic", # derived from magnetic sources 4061 | "m-n": "ins", # derived from inertial navigation system 4062 | "m-p": "passed", # imported from another system (gateway) w/o pedigree 4063 | "m-r": "radio", # radio positioning system (non GPS) 4064 | "m-r-d": "doppler", # doppler radar 4065 | "m-r-e": "eplrs", # enhanced position location reporting system 4066 | "m-r-p": "plrs", # position location reporting system 4067 | "m-r-t": "tadil", # tactical digital information link 4068 | "m-r-t-a": "tadila", # tadil a 4069 | "m-r-t-b": "tadilb", # tadil b 4070 | "m-r-t-j": "tadilj", # tadil j 4071 | "m-r-v": "vhf", # VHF radio 4072 | "m-s": "simulated", # out of a simulation 4073 | "m-v": "computed", # computed using geometric means 4074 | "m-v-o": "optical", # computed using optical means 4075 | "m-v-u": "acoustic", # computed using acoustic means 4076 | "m-v-ou": "flash", # computed using combined acoustic and optical flash 4077 | 4078 | # Special case 4079 | "a-f-G-E-V-9-1-1": "mayday" # emergency signal 4080 | } -------------------------------------------------------------------------------- /CoT/utils.py: -------------------------------------------------------------------------------- 1 | import datetime 2 | from datetime import datetime 3 | 4 | from pydantic import BaseModel, ConfigDict, field_serializer, model_serializer 5 | 6 | TIME_FORMAT = "{:%Y-%m-%dT%H:%M:%S}.{:02.0f}Z" 7 | 8 | from datetime import datetime, timedelta, timezone 9 | from typing import Any, Callable, Self 10 | 11 | from pydantic import BaseModel, model_serializer 12 | 13 | 14 | class CustomModel(BaseModel): 15 | model_config = ConfigDict(populate_by_name=True) 16 | 17 | @model_serializer(mode="wrap") 18 | def serialize( 19 | self, original_serializer: Callable[[Self], dict[str, Any]] 20 | ) -> dict[str, Any]: 21 | for field_name, field_info in self.model_fields.items(): 22 | if isinstance(getattr(self, field_name), datetime): 23 | setattr( 24 | self, 25 | field_name, 26 | TIME_FORMAT.format( 27 | getattr(self, field_name), 28 | getattr(self, field_name).microsecond / 10000.0, 29 | ), 30 | ) 31 | 32 | elif isinstance(getattr(self, field_name), timedelta): 33 | result[field_name] = getattr(self, field_name).total_seconds() 34 | 35 | result = original_serializer(self) 36 | 37 | return result 38 | 39 | @classmethod 40 | def deep_prefix_add(self, obj, prefix="@"): 41 | second_dict = obj.copy() 42 | 43 | 44 | for key, value in obj.items(): 45 | if isinstance(value, dict): 46 | second_dict[key] = CustomModel.deep_prefix_add(value) 47 | continue 48 | 49 | if key == "text": 50 | second_dict[f'#{key}'] = value 51 | else: 52 | second_dict[f"{prefix}{key}"] = value 53 | 54 | del second_dict[key] 55 | print(second_dict) 56 | return second_dict 57 | -------------------------------------------------------------------------------- /CoT/xml/__init__.py: -------------------------------------------------------------------------------- 1 | from xmltodict import parse as _parse 2 | from xmltodict import unparse 3 | 4 | 5 | def parse(xml: str): 6 | return _parse(xml, attr_prefix="")["event"] 7 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Apache License 2 | Version 2.0, January 2004 3 | http://www.apache.org/licenses/ 4 | 5 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 6 | 7 | 1. Definitions. 8 | 9 | "License" shall mean the terms and conditions for use, reproduction, 10 | and distribution as defined by Sections 1 through 9 of this document. 11 | 12 | "Licensor" shall mean the copyright owner or entity authorized by 13 | the copyright owner that is granting the License. 14 | 15 | "Legal Entity" shall mean the union of the acting entity and all 16 | other entities that control, are controlled by, or are under common 17 | control with that entity. For the purposes of this definition, 18 | "control" means (i) the power, direct or indirect, to cause the 19 | direction or management of such entity, whether by contract or 20 | otherwise, or (ii) ownership of fifty percent (50%) or more of the 21 | outstanding shares, or (iii) beneficial ownership of such entity. 22 | 23 | "You" (or "Your") shall mean an individual or Legal Entity 24 | exercising permissions granted by this License. 25 | 26 | "Source" form shall mean the preferred form for making modifications, 27 | including but not limited to software source code, documentation 28 | source, and configuration files. 29 | 30 | "Object" form shall mean any form resulting from mechanical 31 | transformation or translation of a Source form, including but 32 | not limited to compiled object code, generated documentation, 33 | and conversions to other media types. 34 | 35 | "Work" shall mean the work of authorship, whether in Source or 36 | Object form, made available under the License, as indicated by a 37 | copyright notice that is included in or attached to the work 38 | (an example is provided in the Appendix below). 39 | 40 | "Derivative Works" shall mean any work, whether in Source or Object 41 | form, that is based on (or derived from) the Work and for which the 42 | editorial revisions, annotations, elaborations, or other modifications 43 | represent, as a whole, an original work of authorship. For the purposes 44 | of this License, Derivative Works shall not include works that remain 45 | separable from, or merely link (or bind by name) to the interfaces of, 46 | the Work and Derivative Works thereof. 47 | 48 | "Contribution" shall mean any work of authorship, including 49 | the original version of the Work and any modifications or additions 50 | to that Work or Derivative Works thereof, that is intentionally 51 | submitted to Licensor for inclusion in the Work by the copyright owner 52 | or by an individual or Legal Entity authorized to submit on behalf of 53 | the copyright owner. For the purposes of this definition, "submitted" 54 | means any form of electronic, verbal, or written communication sent 55 | to the Licensor or its representatives, including but not limited to 56 | communication on electronic mailing lists, source code control systems, 57 | and issue tracking systems that are managed by, or on behalf of, the 58 | Licensor for the purpose of discussing and improving the Work, but 59 | excluding communication that is conspicuously marked or otherwise 60 | designated in writing by the copyright owner as "Not a Contribution." 61 | 62 | "Contributor" shall mean Licensor and any individual or Legal Entity 63 | on behalf of whom a Contribution has been received by Licensor and 64 | subsequently incorporated within the Work. 65 | 66 | 2. Grant of Copyright License. Subject to the terms and conditions of 67 | this License, each Contributor hereby grants to You a perpetual, 68 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 69 | copyright license to reproduce, prepare Derivative Works of, 70 | publicly display, publicly perform, sublicense, and distribute the 71 | Work and such Derivative Works in Source or Object form. 72 | 73 | 3. Grant of Patent License. Subject to the terms and conditions of 74 | this License, each Contributor hereby grants to You a perpetual, 75 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 76 | (except as stated in this section) patent license to make, have made, 77 | use, offer to sell, sell, import, and otherwise transfer the Work, 78 | where such license applies only to those patent claims licensable 79 | by such Contributor that are necessarily infringed by their 80 | Contribution(s) alone or by combination of their Contribution(s) 81 | with the Work to which such Contribution(s) was submitted. If You 82 | institute patent litigation against any entity (including a 83 | cross-claim or counterclaim in a lawsuit) alleging that the Work 84 | or a Contribution incorporated within the Work constitutes direct 85 | or contributory patent infringement, then any patent licenses 86 | granted to You under this License for that Work shall terminate 87 | as of the date such litigation is filed. 88 | 89 | 4. Redistribution. You may reproduce and distribute copies of the 90 | Work or Derivative Works thereof in any medium, with or without 91 | modifications, and in Source or Object form, provided that You 92 | meet the following conditions: 93 | 94 | (a) You must give any other recipients of the Work or 95 | Derivative Works a copy of this License; and 96 | 97 | (b) You must cause any modified files to carry prominent notices 98 | stating that You changed the files; and 99 | 100 | (c) You must retain, in the Source form of any Derivative Works 101 | that You distribute, all copyright, patent, trademark, and 102 | attribution notices from the Source form of the Work, 103 | excluding those notices that do not pertain to any part of 104 | the Derivative Works; and 105 | 106 | (d) If the Work includes a "NOTICE" text file as part of its 107 | distribution, then any Derivative Works that You distribute must 108 | include a readable copy of the attribution notices contained 109 | within such NOTICE file, excluding those notices that do not 110 | pertain to any part of the Derivative Works, in at least one 111 | of the following places: within a NOTICE text file distributed 112 | as part of the Derivative Works; within the Source form or 113 | documentation, if provided along with the Derivative Works; or, 114 | within a display generated by the Derivative Works, if and 115 | wherever such third-party notices normally appear. The contents 116 | of the NOTICE file are for informational purposes only and 117 | do not modify the License. You may add Your own attribution 118 | notices within Derivative Works that You distribute, alongside 119 | or as an addendum to the NOTICE text from the Work, provided 120 | that such additional attribution notices cannot be construed 121 | as modifying the License. 122 | 123 | You may add Your own copyright statement to Your modifications and 124 | may provide additional or different license terms and conditions 125 | for use, reproduction, or distribution of Your modifications, or 126 | for any such Derivative Works as a whole, provided Your use, 127 | reproduction, and distribution of the Work otherwise complies with 128 | the conditions stated in this License. 129 | 130 | 5. Submission of Contributions. Unless You explicitly state otherwise, 131 | any Contribution intentionally submitted for inclusion in the Work 132 | by You to the Licensor shall be under the terms and conditions of 133 | this License, without any additional terms or conditions. 134 | Notwithstanding the above, nothing herein shall supersede or modify 135 | the terms of any separate license agreement you may have executed 136 | with Licensor regarding such Contributions. 137 | 138 | 6. Trademarks. This License does not grant permission to use the trade 139 | names, trademarks, service marks, or product names of the Licensor, 140 | except as required for reasonable and customary use in describing the 141 | origin of the Work and reproducing the content of the NOTICE file. 142 | 143 | 7. Disclaimer of Warranty. Unless required by applicable law or 144 | agreed to in writing, Licensor provides the Work (and each 145 | Contributor provides its Contributions) on an "AS IS" BASIS, 146 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 147 | implied, including, without limitation, any warranties or conditions 148 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 149 | PARTICULAR PURPOSE. You are solely responsible for determining the 150 | appropriateness of using or redistributing the Work and assume any 151 | risks associated with Your exercise of permissions under this License. 152 | 153 | 8. Limitation of Liability. In no event and under no legal theory, 154 | whether in tort (including negligence), contract, or otherwise, 155 | unless required by applicable law (such as deliberate and grossly 156 | negligent acts) or agreed to in writing, shall any Contributor be 157 | liable to You for damages, including any direct, indirect, special, 158 | incidental, or consequential damages of any character arising as a 159 | result of this License or out of the use or inability to use the 160 | Work (including but not limited to damages for loss of goodwill, 161 | work stoppage, computer failure or malfunction, or any and all 162 | other commercial damages or losses), even if such Contributor 163 | has been advised of the possibility of such damages. 164 | 165 | 9. Accepting Warranty or Additional Liability. While redistributing 166 | the Work or Derivative Works thereof, You may choose to offer, 167 | and charge a fee for, acceptance of support, warranty, indemnity, 168 | or other liability obligations and/or rights consistent with this 169 | License. However, in accepting such obligations, You may act only 170 | on Your own behalf and on Your sole responsibility, not on behalf 171 | of any other Contributor, and only if You agree to indemnify, 172 | defend, and hold each Contributor harmless for any liability 173 | incurred by, or claims asserted against, such Contributor by reason 174 | of your accepting any such warranty or additional liability. 175 | 176 | END OF TERMS AND CONDITIONS 177 | 178 | APPENDIX: How to apply the Apache License to your work. 179 | 180 | To apply the Apache License to your work, attach the following 181 | boilerplate notice, with the fields enclosed by brackets "[]" 182 | replaced with your own identifying information. (Don't include 183 | the brackets!) The text should be enclosed in the appropriate 184 | comment syntax for the file format. We also recommend that a 185 | file or class name and description of purpose be included on the 186 | same "printed page" as the copyright notice for easier 187 | identification within third-party archives. 188 | 189 | Copyright [yyyy] [name of copyright owner] 190 | 191 | Licensed under the Apache License, Version 2.0 (the "License"); 192 | you may not use this file except in compliance with the License. 193 | You may obtain a copy of the License at 194 | 195 | http://www.apache.org/licenses/LICENSE-2.0 196 | 197 | Unless required by applicable law or agreed to in writing, software 198 | distributed under the License is distributed on an "AS IS" BASIS, 199 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 200 | See the License for the specific language governing permissions and 201 | limitations under the License. -------------------------------------------------------------------------------- /MITRE-MP090284.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wcrum/py-cot/ed58867b41347c5974d1468c3312717cccf3311c/MITRE-MP090284.pdf -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 |
2 | 3 |

PyCot

4 | Python Cursor on Target Library 5 |
6 | 7 | # Summary 8 | 9 | PyCot is developed to assist and streamline integration with programs that utilize Cursor on Target (CoT). This tool seeks to help generate, validate, and parse XML data that is defined from either MITRE or the MIL-STD. 10 | 11 | ## Why? 12 | 13 | I needed an easy way to interface with CoT messages, I could not find one available. 14 | 15 | ## Usage 16 | 17 | ```shell 18 | pipx install PyCot 19 | ``` 20 | 21 | ```python 22 | import CoT 23 | import datetime 24 | import socket 25 | 26 | now = datetime.datetime.now(datetime.timezone.utc) 27 | stale = now + datetime.timedelta(minutes=2) 28 | 29 | # Generate new Cursor on Target Event 30 | py_cot = CoT.Event( 31 | version="2.0", 32 | type="a-u-G-U-U-S-R-S", 33 | access="Undefined", 34 | uid="Debug.Python", 35 | time=now, 36 | start=now, 37 | stale=stale, 38 | how="h-g-i-g-o", 39 | qos="2-i-c", 40 | point=CoT.Point(lat=90, lon=90, hae=9999999, ce=9999999, le=9999999), 41 | detail={"contact": {"callsign": "Debug.Python"}}, 42 | ) 43 | 44 | # Your TAK IPv4 / Port 45 | TAK_IP = "x.x.x.x" 46 | TAK_PORT = 9000 47 | 48 | # Sending UDP -> TAK Insecure Anonymous Port 49 | sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 50 | sock.connect((TAK_IP, TAK_PORT)) 51 | 52 | sock.sendall(bytes(py_cot.xml(), encoding="utf-8")) 53 | ``` -------------------------------------------------------------------------------- /examples/admin.p12: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wcrum/py-cot/ed58867b41347c5974d1468c3312717cccf3311c/examples/admin.p12 -------------------------------------------------------------------------------- /examples/pyais-to-tak-with-cert.py: -------------------------------------------------------------------------------- 1 | import socket 2 | import pyais 3 | import CoT 4 | import datetime 5 | import ssl 6 | from cryptography.hazmat.primitives.serialization import Encoding, PrivateFormat, NoEncryption 7 | from cryptography.hazmat.primitives.serialization.pkcs12 import load_key_and_certificates 8 | 9 | UDP_IP = "0.0.0.0" # Listen on all interfaces 10 | UDP_PORT = 9009 11 | 12 | TAK_HOSTNAME = 'x.x.x.x' 13 | TAK_PORT = 8089 14 | 15 | # Load the .p12 file 16 | p12_file_path = '/admin.p12' 17 | p12_password = b'atakatak' 18 | 19 | with open(p12_file_path, 'rb') as f: 20 | p12_data = f.read() 21 | 22 | private_key, certificate, additional_certificates = load_key_and_certificates(p12_data, p12_password) 23 | 24 | # Save cert and key to temp files 25 | with open('client_cert.pem', 'wb') as cert_file: 26 | cert_file.write(certificate.public_bytes(Encoding.PEM)) 27 | 28 | with open('client_key.pem', 'wb') as key_file: 29 | key_file.write(private_key.private_bytes(Encoding.PEM, PrivateFormat.TraditionalOpenSSL, NoEncryption())) 30 | 31 | # Insecure context 32 | context = ssl._create_unverified_context() 33 | context.load_cert_chain(certfile='client_cert.pem', keyfile='client_key.pem') 34 | 35 | sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) # UDP 36 | sock.bind((UDP_IP, UDP_PORT)) 37 | 38 | print(f"Listening on {UDP_IP}:{UDP_PORT}") 39 | 40 | while True: 41 | try: 42 | data, addr = sock.recvfrom(1024) # buffer size is 1024 bytes 43 | 44 | decoded = pyais.decode(data) 45 | 46 | 47 | ais_dict = decoded.asdict() 48 | 49 | 50 | # {'msg_type': 1, 'repeat': 0, 'mmsi': 368088610, 'status': , 'turn': 0.0, 'speed': 28.0, 'accuracy': False, 'lon': -122.383025, 'lat': 37.806888, 'course': 159.7, 'heading': 156, 'second': 54, 'maneuver': , 'spare_1': b'\x00', 'raim': False, 'radio': 100365} 51 | 52 | now = datetime.datetime.now(datetime.timezone.utc) 53 | stale = now + datetime.timedelta(minutes=2) 54 | 55 | event = CoT.Event( 56 | version="2.0", 57 | type="a-u-S-X-M", 58 | access="Undefined", 59 | uid="MMSI-{}".format(ais_dict['mmsi']), 60 | time=now, 61 | start=now, 62 | stale=stale, 63 | how="m-f", 64 | qos="2-i-c", 65 | point=CoT.Point(lat=float(ais_dict['lat']), lon=float(ais_dict['lon']), hae=9999999, ce=9999999, le=9999999), 66 | detail={"contact": {"callsign": "MMSI-{}".format(ais_dict['mmsi'])}}, 67 | ) 68 | 69 | data = event.xml() 70 | b = bytes(data, encoding="utf-8") 71 | 72 | 73 | with socket.create_connection((TAK_HOSTNAME, TAK_PORT)) as tcp_sock: 74 | with context.wrap_socket(tcp_sock, server_hostname=TAK_HOSTNAME) as send_sock: 75 | send_sock.sendall(b) 76 | data = send_sock.recv(1024) 77 | except: 78 | print("Failed to parse ship.") 79 | continue -------------------------------------------------------------------------------- /examples/pycot-aisstream.py: -------------------------------------------------------------------------------- 1 | import socket 2 | import ssl 3 | from cryptography.hazmat.primitives.serialization import Encoding, PrivateFormat, NoEncryption 4 | from cryptography.hazmat.primitives.serialization.pkcs12 import load_key_and_certificates 5 | import asyncio 6 | import websockets 7 | import json 8 | import datetime 9 | import CoT 10 | 11 | 12 | # Load the .p12 file 13 | p12_file_path = 'examples/admin.p12' 14 | p12_password = b'atakatak' 15 | 16 | with open(p12_file_path, 'rb') as f: 17 | p12_data = f.read() 18 | 19 | private_key, certificate, additional_certificates = load_key_and_certificates(p12_data, p12_password) 20 | 21 | # Save cert and key to temp files 22 | with open('client_cert.pem', 'wb') as cert_file: 23 | cert_file.write(certificate.public_bytes(Encoding.PEM)) 24 | 25 | with open('client_key.pem', 'wb') as key_file: 26 | key_file.write(private_key.private_bytes(Encoding.PEM, PrivateFormat.TraditionalOpenSSL, NoEncryption())) 27 | 28 | # Insecure context 29 | context = ssl._create_unverified_context() 30 | context.load_cert_chain(certfile='client_cert.pem', keyfile='client_key.pem') 31 | 32 | # Connect to server 33 | hostname = '134.199.213.125' 34 | port = 9009 35 | 36 | def get_sar(mmsi: str) -> bool: 37 | """Get the AIS Search-And-Rescue (SAR) status of a given MMSI. 38 | 39 | Search and Rescue Aircraft: 40 | AIS and DSC equipment used on search and rescue aircraft use the format 41 | 111213M4I5D6X7X8X9 where the digits 4, 5 and 6 represent the MID and X 42 | is any figure from 0 to 9. In the United States, these MMSIs are 43 | currently only used by the U.S. Coast Guard. 44 | Src: https://www.navcen.uscg.gov/?pageName=mtmmsi 45 | 46 | :param mmsi: str MMSI as decoded from AIS data. 47 | :return: 48 | """ 49 | sar = False 50 | _mmsi = str(mmsi) 51 | if _mmsi[:3] == "111": 52 | sar = True 53 | elif _mmsi[:5] in ["30386", "33885"]: # US Coast Guard 54 | sar = True 55 | return sar 56 | 57 | def create_cot_event(message: dict): 58 | now = datetime.datetime.now(datetime.timezone.utc) 59 | stale = now + datetime.timedelta(minutes=10) 60 | 61 | print(message['Message']['PositionReport']) 62 | print(message) 63 | 64 | return CoT.Event( 65 | version="2.0", 66 | type="a-u-S-X-M", 67 | access="Undefined", 68 | uid="MMSI-{}".format(message['MetaData']['MMSI']), 69 | time=now, 70 | start=now, 71 | stale=stale, 72 | how="m-f", 73 | qos="2-i-c", 74 | point=CoT.Point(lat=float(message["Message"]["PositionReport"]["Latitude"]), lon=float(message["Message"]["PositionReport"]["Longitude"]), hae=9999999, ce=9999999, le=9999999), 75 | detail={"contact": {"callsign": message["MetaData"]["ShipName"]}}, 76 | ) 77 | 78 | async def connect_ais_stream(): 79 | async with websockets.connect("wss://stream.aisstream.io/v0/stream") as websocket: 80 | subscribe_message = { 81 | "APIKey": "4a98e66f38997bf8dc62226380434734886e4efb", 82 | "BoundingBoxes": [[[-90, -180], [90, 180]]], 83 | "FilteringMMSI": ["368207620", "367719770", "211476060"], 84 | "FilderingMessageTypes": ["PositionReport"] 85 | } 86 | subscribe_message_json = json.dumps(subscribe_message) 87 | await websocket.send(subscribe_message_json) 88 | 89 | async for message_json in websocket: 90 | message = json.loads(message_json) 91 | message_type = message["MessageType"] 92 | if message_type == "PositionReport": 93 | ais_message = message['Message']['PositionReport'] 94 | cot_event = create_cot_event(message) 95 | data = cot_event.xml() 96 | b = bytes(data, encoding="utf-8") 97 | 98 | with socket.create_connection((hostname, port)) as sock: 99 | with context.wrap_socket(sock, server_hostname=hostname) as ssock: 100 | ssock.sendall(b) 101 | data = ssock.recv(1024) 102 | await asyncio.sleep(1) 103 | 104 | 105 | if __name__ == "__main__": 106 | while True: 107 | try: 108 | asyncio.run(asyncio.run(connect_ais_stream())) 109 | except: 110 | continue -------------------------------------------------------------------------------- /examples/pycot-from-file.py: -------------------------------------------------------------------------------- 1 | import datetime 2 | import xml.etree.ElementTree as ElementTree 3 | 4 | import CoT 5 | 6 | with open("./tests/messages/MITRE-Message.xml", "r", encoding="utf-8") as file: 7 | event = CoT.Event(**CoT.xml.parse(file.read())) 8 | 9 | assert event.uid == "FBCB2.T-117" 10 | assert event.access == "Unclassified" 11 | 12 | assert event.time == datetime.datetime.strptime( 13 | "2002-10-05T18:00:23Z", "%Y-%m-%dT%H:%M:%S%z" 14 | ) 15 | assert event.start == datetime.datetime.strptime( 16 | "2002-10-05T18:00:23Z", "%Y-%m-%dT%H:%M:%S%z" 17 | ) 18 | assert event.time == datetime.datetime.strptime( 19 | "2002-10-05T18:00:23Z", "%Y-%m-%dT%H:%M:%S%z" 20 | ) 21 | 22 | assert event.type == "a-h-G-E-V-A-T" 23 | assert event.type.description == "TANK" 24 | assert event.type.full == "Gnd/Equip/Vehic/Armor/Tank" 25 | assert event.type.reservation == "hostile" 26 | -------------------------------------------------------------------------------- /examples/pycot-from-json-igs.py: -------------------------------------------------------------------------------- 1 | # Data Sourced from network.igs.org 2 | import json 3 | import CoT 4 | import datetime 5 | import socket 6 | 7 | def generate_cot_event(station): 8 | # Required fields 9 | uid = station.get("name", "UNKNOWN") 10 | lat, lon, hae = station.get("llh", [0, 0, 0]) 11 | 12 | now = datetime.datetime.now(datetime.timezone.utc) 13 | stale = now + datetime.timedelta(minutes=90) 14 | 15 | # Optional metadata 16 | contact = {"callsign": uid} 17 | remarks_parts = [ 18 | f"Receiver: {station.get('receiver_type')}", 19 | f"Antenna: {station.get('antenna_type')}", 20 | f"Firmware: {station.get('firmware')}", 21 | f"City: {station.get('city')}", 22 | f"Country: {station.get('country')}", 23 | f"Serial: {station.get('serial_number')}", 24 | ] 25 | remarks = "\n".join(filter(None, remarks_parts)) 26 | 27 | # Build CoT event 28 | event = CoT.Event( 29 | version="2.0", 30 | type="a-u-P-S", # Arbitrary MIL-STD-2525C type for unit 31 | uid=uid, 32 | time=now, 33 | start=now, 34 | stale=stale, 35 | how="m-g", # machine generated 36 | qos="2-i-c", 37 | access="Undefined", 38 | point=CoT.Point( 39 | lat=lat, 40 | lon=lon, 41 | hae=hae, 42 | ce=9999999, 43 | le=9999999, 44 | ), 45 | detail={ 46 | "contact": contact, 47 | "remarks": CoT.models.Remarks( 48 | text=remarks, 49 | ) 50 | } 51 | ) 52 | return event.xml() 53 | 54 | def main(): 55 | # Downloaded from network.igs.org 56 | with open("igs_stations.json", "r") as f: 57 | stations = json.load(f) 58 | 59 | for station in stations: 60 | cot_xml = generate_cot_event(station) 61 | print(cot_xml) 62 | TAK_IP = "0.0.0.0" 63 | TAK_PORT = 9090 64 | 65 | sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 66 | sock.connect((TAK_IP, TAK_PORT)) 67 | 68 | sock.sendall(bytes(cot_xml, encoding="utf-8")) 69 | 70 | if __name__ == "__main__": 71 | main() -------------------------------------------------------------------------------- /examples/pycot-from-pcap.py: -------------------------------------------------------------------------------- 1 | import CoT 2 | from scapy.all import * 3 | 4 | packets = rdpcap("sample.pcap") 5 | packets.summary() 6 | 7 | for packet in packets: 8 | xml = packet.load.decode() 9 | try: 10 | event = CoT.Event(**CoT.xml.parse(xml)) 11 | # do something with the event 12 | except: 13 | pass 14 | -------------------------------------------------------------------------------- /examples/pycot-from-sat-info.py: -------------------------------------------------------------------------------- 1 | import socket 2 | import time 3 | from datetime import datetime, timedelta, timezone 4 | 5 | import CoT 6 | from skyfield.api import Loader, load, wgs84 7 | 8 | stations_url = "http://celestrak.com/NORAD/elements/gps-ops.txt" # will locally download gps-ops.txt 9 | satellites = load.tle_file(stations_url) 10 | 11 | # LOAD OFFLINE FILE 12 | # satellites = load.tle_file('gps-ops.txt') 13 | 14 | TAK_IP = "localhost" 15 | TAK_PORT = 1234 16 | 17 | # UDP Connection 18 | sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) 19 | 20 | # TCP Connection 21 | # sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 22 | # sock.connect((TAK_IP, TAK_PORT)) 23 | 24 | ts = load.timescale() 25 | 26 | while True: 27 | now = datetime.now(timezone.utc) 28 | stale = now + timedelta(minutes=2) 29 | 30 | t = ts.now() 31 | for sat in satellites: 32 | geocentric = sat.at(t) 33 | lat, lon = wgs84.latlon_of(geocentric) 34 | 35 | try: 36 | satCoT = CoT.Event( 37 | type="a-u-G-U-U-S-R-S", 38 | uid=sat.name, 39 | access="Unclassified", 40 | how="h-e", 41 | time=now, 42 | start=now, 43 | stale=stale, 44 | point=CoT.Point( 45 | lat=lat.degrees, 46 | lon=lon.degrees, 47 | hae=0, 48 | le=0, 49 | ce=0, 50 | ), 51 | detail={"contact": {"callsign": sat.name}}, 52 | ) 53 | # UDP Connection 54 | sock.sendto(bytes(satCoT.xml(), encoding="utf-8"), ((TAK_IP, TAK_PORT))) 55 | # TCP Connection 56 | # sock.sendall(bytes(satCoT.xml(), encoding="utf-8")) 57 | except: 58 | print("Bad satellite TLE data.") 59 | 60 | # Dont overload UDP / TCP Connections 61 | time.sleep(1) 62 | -------------------------------------------------------------------------------- /examples/pycot-from-scapy.py: -------------------------------------------------------------------------------- 1 | import CoT 2 | from scapy.all import * 3 | 4 | # local address, remove line if external 5 | INTERFACE = "\\Device\\NPF_Loopback" 6 | 7 | 8 | def PacketToCoT(packet): 9 | xml = packet.load.decode() 10 | try: 11 | event = CoT.Event(**CoT.xml.parse(xml)) 12 | # do something with the event 13 | except: 14 | pass 15 | 16 | 17 | SNIFFER = sniff( 18 | filter="port 4242", # BFP Filter TAK Port 4242 19 | prn=PacketToCoT, 20 | store=0, # dont store packets in SNIFFER 21 | iface=INTERFACE, # local address, remove line if external 22 | ) 23 | -------------------------------------------------------------------------------- /examples/pycot-from-string.py: -------------------------------------------------------------------------------- 1 | import datetime 2 | 3 | import CoT 4 | 5 | string = """ 6 | 15 | 16 | 17 | """ 18 | 19 | event = CoT.Event(**CoT.xml.parse(string)) 20 | 21 | print(event.xml()) 22 | 23 | assert event.uid == "FBCB2.T-117" 24 | assert event.access == "Unclassified" 25 | assert event.time == "2002-10-05T18:00:23.00Z" 26 | assert event.start == "2002-10-05T18:00:23.00Z" 27 | assert event.time == "2002-10-05T18:00:23.00Z" 28 | assert event.type == "a-h-G-E-V-A-T" 29 | -------------------------------------------------------------------------------- /examples/pycot-to-prometheus.py: -------------------------------------------------------------------------------- 1 | import json 2 | import time 3 | 4 | from prometheus_client import Gauge, start_http_server 5 | 6 | # Load your JSON data 7 | with open("your_data.json", "r") as file: 8 | data = json.load(file) 9 | 10 | # Define your metrics 11 | lat_metric = Gauge("latitude", "Latitude of the location", ["location"]) 12 | lon_metric = Gauge("longitude", "Longitude of the location", ["location"]) 13 | 14 | 15 | def process_data(): 16 | for location, coords in data.items(): 17 | lat_metric.labels(location=location).set(coords["lat"]) 18 | lon_metric.labels(location=location).set(coords["lon"]) 19 | 20 | 21 | if __name__ == "__main__": 22 | # Start up the server to expose the metrics. 23 | start_http_server(8000) 24 | # Update the metrics with your data 25 | while True: 26 | process_data() 27 | time.sleep(15) 28 | -------------------------------------------------------------------------------- /examples/pycot-to-tak-with-cert.py: -------------------------------------------------------------------------------- 1 | import socket 2 | import ssl 3 | from cryptography.hazmat.primitives.serialization import Encoding, PrivateFormat, NoEncryption 4 | from cryptography.hazmat.primitives.serialization.pkcs12 import load_key_and_certificates 5 | 6 | # Load the .p12 file 7 | p12_file_path = 'examples/admin.p12' 8 | p12_password = b'atakatak' 9 | 10 | with open(p12_file_path, 'rb') as f: 11 | p12_data = f.read() 12 | 13 | private_key, certificate, additional_certificates = load_key_and_certificates(p12_data, p12_password) 14 | 15 | # Save cert and key to temp files 16 | with open('client_cert.pem', 'wb') as cert_file: 17 | cert_file.write(certificate.public_bytes(Encoding.PEM)) 18 | 19 | with open('client_key.pem', 'wb') as key_file: 20 | key_file.write(private_key.private_bytes(Encoding.PEM, PrivateFormat.TraditionalOpenSSL, NoEncryption())) 21 | 22 | # Insecure context 23 | context = ssl._create_unverified_context() 24 | context.load_cert_chain(certfile='client_cert.pem', keyfile='client_key.pem') 25 | 26 | # Connect to server 27 | hostname = 'x.x.x.x' 28 | port = 8089 29 | 30 | import datetime 31 | import CoT 32 | 33 | now = datetime.datetime.now(datetime.timezone.utc) 34 | stale = now + datetime.timedelta(minutes=2) 35 | 36 | # Generate new CoT event 37 | py_cot = CoT.Event( 38 | version="2.0", 39 | type="a-u-G-U-U-S-R-S", 40 | access="Undefined", 41 | uid="Debug.Python", 42 | time=now, 43 | start=now, 44 | stale=stale, 45 | how="h-g-i-g-o", 46 | qos="2-i-c", 47 | point=CoT.Point(lat=2, lon=2, hae=9999999, ce=9999999, le=9999999), 48 | detail={"contact": {"callsign": "Debug.Python"}}, 49 | ) 50 | 51 | data = py_cot.xml() 52 | b = bytes(data, encoding="utf-8") 53 | 54 | with socket.create_connection((hostname, port)) as sock: 55 | with context.wrap_socket(sock, server_hostname=hostname) as ssock: 56 | ssock.sendall(b) 57 | data = ssock.recv(1024) -------------------------------------------------------------------------------- /examples/pycot-to-tak.py: -------------------------------------------------------------------------------- 1 | import datetime 2 | import socket 3 | 4 | import CoT 5 | 6 | now = datetime.datetime.now(datetime.timezone.utc) 7 | stale = now + datetime.timedelta(minutes=2) 8 | 9 | # Generate new CoT event 10 | py_cot = CoT.Event( 11 | version="2.0", 12 | type="a-u-G-U-U-S-R-S", 13 | access="Undefined", 14 | uid="Debug.Python", 15 | time=now, 16 | start=now, 17 | stale=stale, 18 | how="h-g-i-g-o", 19 | qos="2-i-c", 20 | point=CoT.Point(lat=2, lon=2, hae=9999999, ce=9999999, le=9999999), 21 | detail={"contact": {"callsign": "Debug.Python"}}, 22 | ) 23 | 24 | TAK_IP = "x.x.x.x" 25 | TAK_PORT = 8089 26 | 27 | sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 28 | sock.connect((TAK_IP, TAK_PORT)) 29 | 30 | sock.sendall(bytes(py_cot.xml(), encoding="utf-8")) 31 | -------------------------------------------------------------------------------- /extensions/mitre/__init__.py: -------------------------------------------------------------------------------- 1 | from datetime import datetime 2 | from typing import Optional 3 | 4 | from pydantic import ConfigDict, EmailStr, Field, HttpUrl 5 | 6 | import CoT 7 | from CoT.utils import CustomModel 8 | 9 | 10 | class MITRERemarks(CustomModel): 11 | source: Optional[str] = None 12 | time: Optional[datetime] = None 13 | to: Optional[str] = None 14 | keywords: Optional[str] = Field(None, pattern=r"[\w\- ]+(,[\w\- ]+)*") 15 | version: Optional[float] = None 16 | text: Optional[str] = None 17 | 18 | 19 | class MITREFlowTags(CustomModel): 20 | version: float = Field(None, description="Schema version.") 21 | model_config = ConfigDict(arbitrary_types_allowed=True, extra="allow") 22 | 23 | 24 | class MITREUid(CustomModel): 25 | version: Optional[float] = Field( 26 | None, ge=0, description="The version of the UID schema" 27 | ) 28 | model_config = ConfigDict(arbitrary_types_allowed=True, extra="allow") 29 | 30 | 31 | class MITREAttitude(CustomModel): 32 | roll: float = Field( 33 | ..., 34 | ge=-180, 35 | le=180, 36 | description="Roll of entity in degrees. Positive indicates listing to the right.", 37 | ) 38 | pitch: float = Field( 39 | ..., 40 | ge=-180, 41 | le=180, 42 | description="Pitch of entity in degrees. Positive indicates nose point up.", 43 | ) 44 | yaw: Optional[float] = Field( 45 | None, 46 | ge=-180, 47 | le=180, 48 | description="Yaw of entity in degrees. Positive indicates turned to the right.", 49 | ) 50 | eRoll: Optional[float] = Field( 51 | None, 52 | ge=0, 53 | description="1-sigma error of roll with respect to a zero mean normal Gaussian distribution.", 54 | ) 55 | ePitch: Optional[float] = Field( 56 | None, 57 | description="1-sigma error of pitch with respect to a zero mean normal Gaussian distribution.", 58 | ) 59 | eYaw: Optional[float] = Field( 60 | None, 61 | description="1-sigma error of yaw with respect to a zero mean normal Gaussian distribution.", 62 | ) 63 | 64 | 65 | class MITRESpin(CustomModel): 66 | roll: float = Field( 67 | ..., 68 | description="Degrees per second with positive indicating to the pilot's right", 69 | ) 70 | pitch: float = Field( 71 | ..., description="Degrees per second with positive indicating nose up." 72 | ) 73 | yaw: Optional[float] = Field( 74 | None, description="Degrees per second with positive indicating right." 75 | ) 76 | eRoll: Optional[float] = Field( 77 | None, 78 | ge=0, 79 | description="1-sigma error of roll with respect to a zero mean normal Gaussian distribution.", 80 | ) 81 | ePitch: Optional[float] = Field( 82 | None, 83 | ge=0, 84 | description="1-sigma error of pitch with respect to a zero mean normal Gaussian distribution.", 85 | ) 86 | eYaw: Optional[float] = Field( 87 | None, 88 | ge=0, 89 | description="1-sigma error of yaw with respect to a zero mean normal Gaussian distribution.", 90 | ) 91 | 92 | 93 | class MTIRESpatial(CustomModel): 94 | attitude: MITREAttitude 95 | spin: MITRESpin 96 | version: Optional[float] = Field( 97 | None, 98 | description="Version tag for this sub schema. Necessary to ensure upward compatibility with future revisions.", 99 | ) 100 | 101 | 102 | class MITRELink(CustomModel): 103 | relation: str = Field( 104 | ..., description="The type of relationship this link describes." 105 | ) 106 | uid: str = Field(..., description="The unique identifier of the related object.") 107 | type: str = Field(..., description="The CoT type of the referenced object.") 108 | url: Optional[HttpUrl] = Field( 109 | None, description="URL to retrieve the linked object." 110 | ) 111 | remarks: Optional[str] = Field( 112 | None, description="Additional comments about the link." 113 | ) 114 | mime: Optional[str] = Field( 115 | None, description="Internet Media type of the referenced object." 116 | ) 117 | version: Optional[float] = Field(None, description="Version tag for compatibility.") 118 | model_config = ConfigDict(arbitrary_types_allowed=True, extra="allow") 119 | 120 | 121 | class MITRETrack(CustomModel): 122 | course: float = Field( 123 | ..., 124 | ge=0, 125 | le=360, 126 | description="Direction of motion with respect to true north in degrees", 127 | ) 128 | speed: float = Field( 129 | ..., ge=0, description="Magnitude of motion measured in meters per second" 130 | ) 131 | slope: Optional[float] = Field( 132 | None, 133 | ge=-90, 134 | le=90, 135 | description="Vertical component of motion vector in degrees", 136 | ) 137 | eCourse: Optional[float] = Field( 138 | None, 139 | description="1-sigma error on a Gaussian distribution associated with the course attribute", 140 | ) 141 | eSpeed: Optional[float] = Field( 142 | None, 143 | description="1-sigma error on a Gaussian distribution associated with the speed attribute", 144 | ) 145 | eSlope: Optional[float] = Field( 146 | None, 147 | description="1-sigma error on a Gaussian distribution associated with the slope attribute", 148 | ) 149 | version: Optional[float] = Field(None, description="Schema version") 150 | 151 | 152 | class MITRERequest(CustomModel): 153 | notify: HttpUrl = Field( 154 | ..., description="Network endpoint for status notifications." 155 | ) 156 | wilcoby: Optional[datetime] = Field( 157 | None, description="Deadline for WILCO/CANTCO acknowledgement." 158 | ) 159 | priority: Optional[float] = Field( 160 | None, ge=0.0, le=1.0, description="Request's relative priority." 161 | ) 162 | version: Optional[float] = Field( 163 | None, description="Version tag for this sub schema." 164 | ) 165 | to: Optional[str] = Field( 166 | None, description="CoT UID of the specific entity addressed." 167 | ) 168 | authority: Optional[str] = Field( 169 | None, description="CoT UID of the entity authorizing the request." 170 | ) 171 | streamto: Optional[str] = Field( 172 | None, description="Additional streaming directions." 173 | ) 174 | 175 | 176 | class MITREDetail(CustomModel): 177 | remarks: Optional[MITRERemarks] 178 | flowTags: Optional[MITREFlowTags] = Field(alias="_flow-tags_") 179 | spatial: Optional[MITRESpin] 180 | uid: Optional[MITREUid] 181 | track: Optional[MITRETrack] 182 | request: Optional[MITRERequest] 183 | 184 | 185 | class MITREContact(CustomModel): 186 | callsign: Optional[str] = None 187 | freq: Optional[float] = None 188 | email: Optional[EmailStr] = None 189 | dsn: Optional[str] = None 190 | phone: Optional[str] = Field(None, pattern=r"^\+?[1-9]\d{1,14}$") 191 | modulation: Optional[str] = None 192 | hostname: Optional[str] = None 193 | version: Optional[float] = None 194 | 195 | 196 | class Event(CoT.Event): 197 | detail: Optional[MITREDetail] 198 | -------------------------------------------------------------------------------- /extensions/mitre/setup.py: -------------------------------------------------------------------------------- 1 | from setuptools import setup 2 | 3 | setup( 4 | name="PyCoT-MITRE", 5 | version="0.1", 6 | description="PyCoT MITRE Extensions", 7 | author="William Crum", 8 | author_email="will@wcrum.dev", 9 | packages=["pycot_ext_mitre"], 10 | package_dir={"pycot_ext_mitre": "."}, 11 | ) 12 | -------------------------------------------------------------------------------- /extensions/mitre/xsd/CoT Contact Schema (PUBLIC RELEASE).xsd: -------------------------------------------------------------------------------- 1 | 2 | 17 | 18 | 19 | 20 | 21 | This is a Cursor On Target sub-schema representing communications parameters for contacting a friendly element for human-to-human communcations. The objective of this schema is to carry the essential information needed to contact this entity by a variety of means. None of the modes of contact (e.g., e-mail, phone, etc) is required. 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | The unit's voice call sign 30 | 31 | 32 | 33 | 34 | The frequency (in MHz) on which the unit may be contacted via voice. 35 | 36 | 37 | 38 | 39 | e-mail address for this element (if applicable) 40 | 41 | 42 | 43 | 44 | DSN number for this element (if applicable) 45 | 46 | 47 | 48 | 49 | Phone number for this element (if applicable) 50 | 51 | 52 | 53 | 54 | Amplifies the radio frequency information provided. Contains the modulation type for the communication. (Coding tbd, should cover complex modulations such as SINCGARS hopping, csma, etc...) am|fm 55 | 56 | 57 | 58 | 59 | DNS-resolvable host name 60 | 61 | 62 | 63 | 64 | Version tag for this sub schema. Neccessary to ensure upward compatibility with future revisions. 65 | 66 | 67 | 68 | 69 | 70 | -------------------------------------------------------------------------------- /extensions/mitre/xsd/CoT Flow-Tags Schema (PUBLIC RELEASE).xsd: -------------------------------------------------------------------------------- 1 | 2 | 12 | 15 | 16 | 17 | This is a Cursor On Target detail sub-schema that holds "fingerprints" of the system that have processed a particular CoT event. This information aids in the routine of CoT messages along a particular processing chain. Each system that touches a particular CoT event is expected to add its own attribute to this entity. The attribute name should reflect the particular system name, and the value should be the time stamp when the information was sent out from that system. Some illustrative _flow-tags_ attributes are adocs, fbcb2, and tadilj, but the attribute list is not a closed set. 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | A system-specific flowtag identifier associated with the encapsulating CoT object. The attribute value should be an xs:dateTime value. 27 | 28 | 29 | 30 | 31 | -------------------------------------------------------------------------------- /extensions/mitre/xsd/CoT Link Schema (PUBLIC RELEASE).xsd: -------------------------------------------------------------------------------- 1 | 2 | 21 | 22 | 23 | 24 | 25 | This is a Cursor On Target sub-schema for linking to either another CoT event or an arbitrary Internet resource. The objective of this schema is to provide an abstract way to express a relationship between a CoT object and other object. This allows, for example, a sensor point of interest to be linked back to its source, or a PPLI from a wingman to be associated with his flight lead. Linkages are always unidirectional. One entity may have multiple links (i.e., it may be related to multipls other entities). For processing simplicity, it is required that the relationship graphs will directed and acyclic (no cycles). The link, itself, names the relationship (using a hierarchy similiar to the CoT type), the UID of the related object (whether CoT or not), possibly provides a URL for retrieving that object. 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | The type of relationship (e.g, subject, object, indirect object) that this link describes. This is a hierarchy much like the event type field. 34 | 35 | 36 | 37 | 38 | This is the CoT UID of the related object. If the linked object is not a CoT event, a CoT UID that represents that object is used. 39 | 40 | 41 | 42 | 43 | The CoT type of the referenced object. This is included because it is generally the key item needed in a tasking. 44 | 45 | 46 | 47 | 48 | If present, this is a URL through which the linked object can be retrieved. If the URL is missing, then the object should be a periodic message (e.g., blue force track) that can be read from a CoT stream. 49 | 50 | 51 | 52 | 53 | Remarks associated with this link. 54 | 55 | 56 | 57 | 58 | Internet Media type of the referenced object. If the link is to a CoT event, the mime attribute is optional and its type may be application/xml or text/xml as described in RFC 3023, "XML Media Types", or the unregistered type, application/cot+xml. If the link is to an arbitrary resource, the mime attribute is required and and appropriate Internet media type must be specified. Registered media types are managed by the IANA and are listed at http://www.iana.org/assignments/media-types/. 59 | 60 | 61 | 62 | 63 | Version tag for this sub schema. Neccessary to ensure upward compatibility with future revisions. 64 | 65 | 66 | 67 | 68 | 69 | -------------------------------------------------------------------------------- /extensions/mitre/xsd/CoT Remarks Schema (PUBLIC RELEASE).xsd: -------------------------------------------------------------------------------- 1 | 2 | 18 | 19 | 22 | 23 | 24 | This is a Cursor On Target sub-schema for a generic remarks (aka "FreeText"). While the use of free text is strongly discouraged (it hampers machine-to-machine communication) it is a pragmatic necessity. This entity attempts to encapsulate freetext in a way that simplifies subsequent machine processing. The content of this entity is presumed to be a human-readable chunk of textual data. The attributes merely aid in the machine handling of the data. 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | String identifying the source of this remark. (Field encoding is currently unspecified.) 33 | 34 | 35 | 36 | 37 | Time this remark was added to the CoT object 38 | 39 | 40 | 41 | 42 | Intended recipeint(s) of this remark information. Tentative field coding as follows: The to attribute may contain the UID of the entity to whom the message is addressed. (Implementors should expect that future versions of this sub schema will allow a comma separated list of UIDs.) Absense of an explict addressee means the message is broadcast. 43 | 44 | 45 | 46 | 47 | Used to track a conversation thread. The format is a comma-separated list of freetext keywords. 48 | 49 | ex. keywords="debriefing" - Describes a conversation about debriefing 50 | ex. keywords="mission-A" - Describes a conversation about mission-A 51 | ex. keywords="tasking_B, subject_C" - Describes a conversation about tasking_B and subject_C 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | Version tag for this sub schema. Neccessary to ensure upward compatibility with future revisions. 64 | 65 | 66 | 67 | 68 | 69 | -------------------------------------------------------------------------------- /extensions/mitre/xsd/CoT Request Schema (PUBLIC RELEASE).xsd: -------------------------------------------------------------------------------- 1 | 2 | 3 | 20 | 21 | 22 | 23 | 24 | This is a Cursor On Target sub-schema for a generic request. This schema contains information common to all requests, specifically where responses should be sent, the overall priority of the request, if immediate willco/cantco acknowledgement is needed, etc. Detail infomration for specific request types are carried in sub-schemas nested within this one. 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | Network endpoint to which status notifications should be delivered. (A network endpoint is represented as an URL, e.g., tcp://hostname:port, udp://hostname:port. The previous format, host:port, e.g., 192.168.0.1:71556, is deprecated, but implementers should be aware that this format may be in use. 33 | 34 | 35 | 36 | 37 | An optional field that requests the receiving system to provide a positive or negative akcnowledgement (WILCO/CANTCO) by a specific time. This is used to ensure that deadline driven requests are made known to the operator. 38 | 39 | 40 | 41 | 42 | This optional field indicates this request's relative priority with respect to other requests. (At present, no specific coding scheme is in mandated, but a floating point value between 0.0(low) and 1.0(high) is in current (limited) use.) 43 | 44 | 45 | 46 | 47 | Version tag for this sub schema. Neccessary to ensure upward compatibility with future revisions. 48 | 49 | 50 | 51 | 52 | When present, this field contains the CoT UID of the specific entity who is being addressed. It is assumed that all CoT entities that can provide a service are reported as friendly atoms. 53 | 54 | 55 | 56 | 57 | This is a 'signature block' which holds the CoT uid of the entity which has uathorized the request. The authorizing entity is not necessarily the originator of the request and might not be associated with the 'notify' field. Authority is intended to provide services (such as a striker) a mechanism to verify that the request has been approved. 58 | 59 | 60 | 61 | 62 | 63 | 64 | -------------------------------------------------------------------------------- /extensions/mitre/xsd/CoT Spatial Schema (PUBLIC RELEASE).xsd: -------------------------------------------------------------------------------- 1 | 2 | 22 | 23 | 24 | 25 | 26 | This is a Cursor On Target sub-schema for spatial information of physical entity. It is intended to appear in the detail section of the Cursor On Target schema. It has elements to represent attitude and associated first derivatives (spin). The intention behind the spatial element is to convey the attitude of a body moving through space with respect to its "nominal" flight attitude. 27 | 28 | 29 | 30 | 31 | 32 | Attitude represents the attitude of the entity described by the Cursor On Target base schema. 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | Roll of entity in degrees. Positive indicates listing to the right. 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | Pitch of entity in degrees. Positive indicates nose point up. 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | Yaw of entity in degrees. Positive indicates turned to the right. 63 | 64 | Yaw is defined here as is the difference between the craft's 65 | pointing direction and it's movement direction (its heading and 66 | coruse) (heading - course). Thinking of this in terms of 67 | "oversteer" and "understeer" in a car provides an example. 68 | If your car is traveling normally, going in the direction 69 | it's pointed, you have zero yaw. If you're skidding sideways, 70 | you'd then have a "yaw" of 90 degrees, and if that skid is to 71 | the right (the passenger side is going to hit first) then your 72 | "yaw" is -90 degrees (since you're car is pointed 90 degrees 73 | to the left of the direction you're moving.) 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 1-sigma error of roll with respect to a zero mean normal Gaussian distribution. 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 1-sigma error of pitch with respect to a zero mean normal Gaussian distribution. 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 1-sigma error of yaw with respect to a zero mean normal Gaussian distribution. 106 | 107 | 108 | 109 | 110 | 111 | 112 | 113 | 114 | 115 | 116 | 117 | Spin represents the first derivative of attributes found in attitude. 118 | 119 | 120 | 121 | 122 | 123 | 124 | 125 | Degrees per second with positive indicating to the pilots right 126 | 127 | 128 | 129 | 130 | 131 | 132 | 133 | Degrees per second with positive indicating nose up. 134 | 135 | 136 | 137 | 138 | 139 | 140 | 141 | Degrees per second with positive indicating right. 142 | 143 | 144 | 145 | 146 | 147 | 148 | 149 | 1-sigma error of roll with respect to a zero mean normal Gaussian distribution. 150 | 151 | 152 | 153 | 154 | 155 | 156 | 157 | 158 | 159 | 1-sigma error of pitch with respect to a zero mean normal Gaussian distribution. 160 | 161 | 162 | 163 | 164 | 165 | 166 | 167 | 168 | 169 | 1-sigma error of yaw with respect to a zero mean normal Gaussian distribution. 170 | 171 | 172 | 173 | 174 | 175 | 176 | 177 | 178 | 179 | 180 | 181 | 182 | Version tag for this sub schema. Neccessary to ensure upward compatibility with future revisions. 183 | 184 | 185 | 186 | 187 | 188 | -------------------------------------------------------------------------------- /extensions/mitre/xsd/CoT Track Schema (PUBLIC RELEASE).xsd: -------------------------------------------------------------------------------- 1 | 2 | 17 | 20 | 21 | 22 | This is a Cursor On Target detail sub-schema for track information. The root element and associated attributes of this schema are intended to appear in the detail element of the Cursor On Target schema. 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | Direction of motion with respect to true north. Measured in degrees. 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | Magnitude of motion measured in meters per second 42 | 43 | The “speed” attribute in the track entity represents the magnitude of 44 | the object’s velocity in three space. That is, an object is falling 45 | vertically toward the Earth at a velocity of 100m/s it should have a 46 | reported “speed” of 100m/s even though it’s effective “ground speed” is 47 | zero. Furthermore, the reported speed reflect that objects changing 48 | position in three space, not it’s motion through the medium, hence, an 49 | object flying at 100m/s directly into a 100m/s head wind would have a 50 | reported “speed” of zero despite the fact that it’s indicated airspeed 51 | in 100m/s. 52 | 53 | We observe that many systems (incorrectly) report only the horizontal 54 | components of their velocity. While not strictly correct, the resultant 55 | velocity errors tend to be small for terrestrial and surface systems. 56 | While airborne systems have the potential for much larger vertical 57 | components, vertical velocities generally remain relatively small for 58 | lift-based air vehicles in typical flight profiles. Aggressively 59 | maneuvering aircraft and ballistic vehicles may have dominant vertical 60 | velocities and should accurately report the 3D vector. We expect that 61 | the systems that (incorrectly) report only their horizontal velocity 62 | will not populate the “slope” attribute the of the track entity. 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | Vertical component of motion vector. Measured in degrees. Negative indicates downward motion. 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 1-sigma error on a Gaussian distribution associated with the course attribute 85 | 86 | 87 | 88 | 89 | 1-sigma error on a Gaussian distribution associated with the speed attribute 90 | 91 | 92 | 93 | 94 | 1-sigma error on a Gaussian distribution associated with the slope attribute 95 | 96 | 97 | 98 | 99 | 100 | -------------------------------------------------------------------------------- /extensions/mitre/xsd/CoT Uid Schema (PUBLIC RELEASE).xsd: -------------------------------------------------------------------------------- 1 | 2 | 3 | 18 | 19 | 20 | 21 | This is a Cursor On Target detail sub-schema that holds the unique ID assigned by each system that processed this event. Most systems (including CoT) have their own method for assigning system-wide unique identifiers for a particular object. In general, it is not possible for a single UID to be used for all systems. This 'uid' entity provides a common place where each systems can record its particular UID for each CoT event. Like the _flow-tags_ element, each system is responsible for adding its own attribute to this entity. The name of the attribute should represent the system, and the value of the attribute should be the id that system assigned to this CoT object. 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | The system-specific identifier (a.k.a UID, or track number) associated with the entity described by the encapsulating CoT object. 31 | 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /requirements.txt: -------------------------------------------------------------------------------- 1 | annotated-types==0.6.0 2 | certifi==2024.2.2 3 | jplephem==2.21 4 | numpy==1.26.4 5 | pydantic==2.6.3 6 | pydantic_core==2.16.3 7 | sgp4==2.23 8 | skyfield==1.48 9 | typing_extensions==4.10.0 10 | xmltodict==0.13.0 11 | -------------------------------------------------------------------------------- /setup.py: -------------------------------------------------------------------------------- 1 | from setuptools import setup 2 | 3 | __title__ = 'pycot' 4 | __version__ = '3.0.0' 5 | __author__ = 'William Crum' 6 | __license__ = 'Apache 2.0 License' 7 | 8 | # read the contents of your README file 9 | from pathlib import Path 10 | this_directory = Path(__file__).parent 11 | long_description = (this_directory / "README.md").read_text() 12 | 13 | setup( 14 | name="PyCoT", 15 | version="3.0.1", 16 | description="Python Cursor On Target Object-Relational Mapper", 17 | author="William Crum", 18 | author_email="will@wcrum.dev", 19 | url=f'https://github.com/ampledata/{__title__}', 20 | packages=["CoT", "CoT.models", "CoT.xml"], 21 | install_requires=[ 22 | "pydantic>=1.10.2", 23 | "xmltodict>=0.13.0", 24 | ], 25 | extras_require={ 26 | "mitre": ["PyCoT-MITRE"], 27 | "ais": ["pyais"] 28 | }, 29 | long_description=long_description, 30 | long_description_content_type='text/markdown' 31 | ) 32 | -------------------------------------------------------------------------------- /tests/geolife_small.gpkg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wcrum/py-cot/ed58867b41347c5974d1468c3312717cccf3311c/tests/geolife_small.gpkg -------------------------------------------------------------------------------- /tests/messages/MITRE-Message.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | -------------------------------------------------------------------------------- /tests/messages/README.md: -------------------------------------------------------------------------------- 1 | Reference [https://git.tak.gov/standards/takcot/-/tree/master/examples](https://git.tak.gov/standards/takcot/-/tree/master/examples) -------------------------------------------------------------------------------- /tests/test_cot_xml_interopability.py: -------------------------------------------------------------------------------- 1 | import json 2 | 3 | import CoT 4 | 5 | xml_cot = """ 6 | 15 | 16 | 17 | """ 18 | 19 | py_cot = CoT.Event( 20 | version="2.0", 21 | type="a-h-G-E-V-A-T", 22 | access="Unclassified", 23 | uid="FBCB2.T-117", 24 | time="2002-10-05T18:00:23.00Z", 25 | start="2002-10-05T18:00:23.00Z", 26 | stale="2002-10-05T18:00:23.00Z", 27 | how="m-i", 28 | point=CoT.models.Point(lat=26.4321, lon=-82.0554, hae=0, ce=32, le=221.0), 29 | ) 30 | 31 | json_cot = """{ 32 | "event": { 33 | "version": 2.0, 34 | "type": "a-h-G-E-V-A-T", 35 | "access": "Unclassified", 36 | "uid": "FBCB2.T-117", 37 | "time": "2002-10-05T18:00:23.00Z", 38 | "start": "2002-10-05T18:00:23.00Z", 39 | "stale": "2002-10-05T18:00:23.00Z", 40 | "how": "m-i", 41 | "point": { 42 | "lat": 26.4321, 43 | "lon": -82.0554, 44 | "hae": 0.0, 45 | "ce": 32.0, 46 | "le": 221.0 47 | } 48 | } 49 | }""" 50 | 51 | 52 | def test_json_to_xml_check(): 53 | # Checking if two strings are the same is a terrible 54 | # way of checking if the XML data is the same 55 | # to test if the XML == PyCoT XML 56 | # I am first creating an element in PyCoT 57 | # Turning it into XML, loading it back as if it was 58 | # Just XML and then comparing that to the loaded XML 59 | # At the end both values should be the same 60 | 61 | t1 = CoT.Event(**CoT.xml.parse(py_cot.xml())) 62 | 63 | t2 = CoT.Event(**CoT.xml.parse(xml_cot)) 64 | 65 | t3 = CoT.Event(**json.loads(json_cot)["event"]) 66 | 67 | assert t1.model_dump_json() == t2.model_dump_json() == t3.model_dump_json() 68 | -------------------------------------------------------------------------------- /tests/test_messages.py: -------------------------------------------------------------------------------- 1 | import glob 2 | import os 3 | 4 | import pytest 5 | 6 | import CoT 7 | 8 | working_directory = os.path.dirname(os.path.abspath(__file__)) 9 | 10 | 11 | @pytest.mark.parametrize("filename", glob.glob(working_directory + "/messages/*.cot")) 12 | def test_cot_file(filename): 13 | print(os.path.dirname(os.path.abspath(__file__))) 14 | with open(filename, "r", encoding="utf-8") as file: 15 | xml_dict = CoT.xml.parse(file.read()) 16 | xml_event = CoT.Event(**xml_dict) 17 | 18 | pycot_xml = xml_event.xml() 19 | pycot_event = CoT.Event(**CoT.xml.parse(pycot_xml)) 20 | 21 | # Ensure that the set of the json is empty 22 | # Make sure both combined are not unique 23 | assert not set(pycot_event.model_dump_json()) ^ set(xml_event.model_dump_json()) 24 | --------------------------------------------------------------------------------