@atmosx/event-product-parser 3.0.44 → 3.0.47

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (68) hide show
  1. package/README.md +77 -31
  2. package/SUPPORTED_EVENTS.md +369 -0
  3. package/dist/cjs/index.cjs +681 -403
  4. package/dist/esm/index.mjs +659 -382
  5. package/dist/index.d.mts +54 -25
  6. package/dist/index.d.ts +54 -25
  7. package/package.json +1 -1
  8. package/src/@building/building.attachments.ts +83 -0
  9. package/src/@building/building.enhance.ts +7 -3
  10. package/src/@building/building.office.ts +2 -2
  11. package/src/@building/building.properties.ts +12 -11
  12. package/src/@building/building.signature.ts +11 -11
  13. package/src/@building/building.tags.ts +2 -2
  14. package/src/@building/building.tracking.ts +3 -3
  15. package/src/@building/building.validate.ts +2 -2
  16. package/src/@core/core.createEvent.ts +83 -0
  17. package/src/@dictionaries/{dictionaries.eventActions.ts → dictionaries.actions.ts} +1 -1
  18. package/src/@dictionaries/{dictionaries.eventAwipAbreviations.ts → dictionaries.awips.ts} +1 -1
  19. package/src/@dictionaries/{dictionaries.eventCancelMessages.ts → dictionaries.cancellation.ts} +2 -1
  20. package/src/@dictionaries/{dictionaries.eventCauses.ts → dictionaries.causes.ts} +1 -1
  21. package/src/@dictionaries/{dictionaries.statusCorrelationText.ts → dictionaries.correlations.ts} +1 -1
  22. package/src/@dictionaries/{dictionaries.betterEventNames.ts → dictionaries.enhanced.ts} +13 -2
  23. package/src/@dictionaries/{dictionaries.eventTypes.ts → dictionaries.events.ts} +1 -1
  24. package/src/@dictionaries/{dictionaries.regExp.ts → dictionaries.expressions.ts} +2 -1
  25. package/src/@dictionaries/{dictionaries.hailStrings.ts → dictionaries.hail.ts} +4 -1
  26. package/src/@dictionaries/{dictionaries.officeICAOs.ts → dictionaries.icao.ts} +1 -1
  27. package/src/@dictionaries/{dictionaries.eventsMatchText.ts → dictionaries.matches.ts} +1 -1
  28. package/src/@dictionaries/{dictionaries.eventProducts.ts → dictionaries.products.ts} +1 -1
  29. package/src/@dictionaries/{dictionaries.eventRecords.ts → dictionaries.records.ts} +1 -1
  30. package/src/@dictionaries/{dictionaries.eventSeverity.ts → dictionaries.severity.ts} +1 -1
  31. package/src/@dictionaries/{dictionaries.shapefileLinks.ts → dictionaries.shapefiles.ts} +1 -1
  32. package/src/@dictionaries/dictionaries.states.ts +72 -0
  33. package/src/@dictionaries/{dictionaries.eventStatus.ts → dictionaries.status.ts} +1 -1
  34. package/src/@dictionaries/{dictionaries.eventTags.ts → dictionaries.tags.ts} +1 -1
  35. package/src/@dictionaries/{dictionaries.testSignatures.ts → dictionaries.testing.ts} +3 -2
  36. package/src/@events/events.api.ts +18 -15
  37. package/src/@events/events.text.ts +2 -2
  38. package/src/@events/events.ugc.ts +2 -2
  39. package/src/@manager/manager.mkEvent.ts +3 -3
  40. package/src/@manager/manager.rmEvent.ts +3 -2
  41. package/src/@manager/manager.updateListener.ts +163 -0
  42. package/src/@modules/@database/database.broadcastify.ts +67 -0
  43. package/src/@modules/@database/database.init.ts +14 -1
  44. package/src/@modules/@database/database.shapefiles.ts +3 -6
  45. package/src/@modules/@eas/eas.getCleanDescription.ts +2 -0
  46. package/src/@modules/@eas/eas.getTTS.ts +19 -8
  47. package/src/@modules/@eas/eas.setEasTone.ts +15 -10
  48. package/src/@modules/@stanza/stanza.getAwipsType.ts +2 -2
  49. package/src/@modules/@stanza/stanza.validate.ts +3 -3
  50. package/src/@modules/@utilities/utilities.createHttp.ts +56 -47
  51. package/src/@modules/@utilities/utilities.setCronSchedule.ts +5 -2
  52. package/src/@modules/@xmpp/xmpp.xReconnect.ts +1 -1
  53. package/src/@parsers/@hvtec/hvtec.extract.ts +8 -8
  54. package/src/@parsers/@pvtec/pvtec.extract.ts +12 -12
  55. package/src/@parsers/@text/text.getDescriptionFromProduct.ts +2 -2
  56. package/src/@parsers/@text/text.getEmbed.ts +58 -0
  57. package/src/@parsers/@ugc/ugc.header.ts +3 -3
  58. package/src/@types/type.event.ts +3 -3
  59. package/src/@types/{type.webhook.ts → type.listener.ts} +11 -7
  60. package/src/@types/type.properties.ts +10 -9
  61. package/src/@types/type.settings.ts +13 -6
  62. package/src/bootstrap.ts +13 -6
  63. package/src/index.ts +2 -1
  64. package/test.js +30 -22
  65. package/src/@building/building.outlooks.ts +0 -36
  66. package/src/@manager/manager.createWebhook.ts +0 -129
  67. package/src/@manager/manager.updateWebhooks.ts +0 -49
  68. package/src/@modules/@utilities/utilities.isImageReady.ts +0 -27
@@ -10491,6 +10491,7 @@ var index_exports = {};
10491
10491
  __export(index_exports, {
10492
10492
  Manager: () => Manager,
10493
10493
  clearEvents: () => clearEvents,
10494
+ createEvent: () => createEvent2,
10494
10495
  default: () => index_default,
10495
10496
  getCleanedEvent: () => getCleanedEvent,
10496
10497
  getEventGeometry: () => getEventGeometry,
@@ -10510,7 +10511,7 @@ module.exports = __toCommonJS(index_exports);
10510
10511
  var import_path = __toESM(require("path"));
10511
10512
  var import_node_events = require("events");
10512
10513
  var bootstrap = {
10513
- version: `3.0.44`,
10514
+ version: `3.0.47`,
10514
10515
  isReady: true,
10515
10516
  ratelimits: {},
10516
10517
  session_xmpp: null,
@@ -10566,7 +10567,12 @@ var bootstrap = {
10566
10567
  CallbackInterval: 15,
10567
10568
  EventsEndpoint: `https://api.weather.gov/alerts/active`
10568
10569
  },
10569
- WebhookSettings: [],
10570
+ BroadcastifySettings: {
10571
+ BroadcastifyAttachments: true,
10572
+ BroadcastifyDatabase: `https://scriptkitty.cafe/ftp/@atmosphericx/assets/broadcastify.json`,
10573
+ BroadcastifyTags: [`Ham`, `Air`, `Fire`, `Public Safety`, `Weather`, `EMS`, `Police`, `Rail`]
10574
+ },
10575
+ ListenerSettings: [],
10570
10576
  GlobalSettings: {
10571
10577
  EventManagement: true,
10572
10578
  BetterEventNames: true,
@@ -10586,10 +10592,12 @@ var bootstrap = {
10586
10592
  NodeLocationFiltering: false,
10587
10593
  IgnoreTestProducts: true
10588
10594
  },
10589
- EASSettings: {
10590
- ArchiveTTL: 60,
10591
- ArchiveDirectory: null,
10592
- IntroWavFile: null
10595
+ ArchiveSettings: {
10596
+ TTL: 60,
10597
+ EventDirectory: null,
10598
+ TextDirectory: null,
10599
+ EasDirectory: null,
10600
+ EasToneout: null
10593
10601
  }
10594
10602
  }
10595
10603
  }
@@ -13603,8 +13611,9 @@ var xError = () => {
13603
13611
  }));
13604
13612
  };
13605
13613
 
13606
- // src/@dictionaries/dictionaries.regExp.ts
13607
- var regExp = {
13614
+ // src/@dictionaries/dictionaries.expressions.ts
13615
+ var dict_expressions = {
13616
+ location: new RegExp(/^([A-Za-z.\-' ]+),\s*([A-Z]{2})$/),
13608
13617
  pvtec: new RegExp(`[OTEX].(NEW|CON|EXT|EXA|EXB|UPG|CAN|EXP|COR|ROU).[A-Z]{4}.[A-Z]{2}.[WAYSFON].[0-9]{4}.[0-9]{6}T[0-9]{4}Z-[0-9]{6}T[0-9]{4}Z`, "g"),
13609
13618
  hvtec: new RegExp(`[a-zA-Z0-9]{4}.[A-Z0-9].[A-Z]{2}.[0-9]{6}T[0-9]{4}Z.[0-9]{6}T[0-9]{4}Z.[0-9]{6}T[0-9]{4}Z.[A-Z]{2}`, "imu"),
13610
13619
  wmo: new RegExp(`[A-Z0-9]{6}\\s[A-Z]{4}\\s\\d{6}`, "imu"),
@@ -13614,8 +13623,8 @@ var regExp = {
13614
13623
  dateline: new RegExp(`\\d{3,4}\\s*(AM|PM)?\\s*[A-Z]{2,4}\\s+[A-Z]{3,}\\s+[A-Z]{3,}\\s+\\d{1,2}\\s+\\d{4}`, "gim")
13615
13624
  };
13616
13625
 
13617
- // src/@dictionaries/dictionaries.eventAwipAbreviations.ts
13618
- var eventAwipAbreviations = {
13626
+ // src/@dictionaries/dictionaries.awips.ts
13627
+ var dict_awips = {
13619
13628
  ABV: `rawinsonde-data-above-100-millibars`,
13620
13629
  ADA: `alarm-alert-administrative-message`,
13621
13630
  ADM: `alert-administrative-message`,
@@ -13970,7 +13979,7 @@ var getAwipsType = (options) => {
13970
13979
  prefix: null
13971
13980
  };
13972
13981
  }
13973
- for (const [prefix, type] of Object.entries(eventAwipAbreviations)) {
13982
+ for (const [prefix, type] of Object.entries(dict_awips)) {
13974
13983
  if (attributes.awipsid.startsWith(prefix)) {
13975
13984
  return { type, prefix };
13976
13985
  }
@@ -13988,8 +13997,8 @@ var validate = (options) => {
13988
13997
  if (attributes.awipsid && attributes.awipsid.length > 1) {
13989
13998
  const isCapEvent = message.includes(`<?xml`);
13990
13999
  const isCapAreaDescription = message.includes(`<areaDesc>`);
13991
- const isVTEC = message.match(regExp.pvtec) != null;
13992
- const isUGC = message.match(regExp.ugc1) != null;
14000
+ const isVTEC = message.match(dict_expressions.pvtec) != null;
14001
+ const isUGC = message.match(dict_expressions.ugc1) != null;
13993
14002
  const getType = getAwipsType({ attributes });
13994
14003
  if (getType.type != null) {
13995
14004
  return {
@@ -14013,7 +14022,7 @@ var validate = (options) => {
14013
14022
  // src/@parsers/@text/text.getDescriptionFromProduct.ts
14014
14023
  var getDescriptionFromProduct = (options) => {
14015
14024
  let message = options.message;
14016
- const dates = Array.from(message.matchAll(regExp.dateline));
14025
+ const dates = Array.from(message.matchAll(dict_expressions.dateline));
14017
14026
  if (dates.length) {
14018
14027
  const lastMatch = dates[dates.length - 1][0];
14019
14028
  const sIndx = message.lastIndexOf(lastMatch);
@@ -14079,8 +14088,8 @@ var getTextFromProduct = (options) => {
14079
14088
  return null;
14080
14089
  };
14081
14090
 
14082
- // src/@dictionaries/dictionaries.officeICAOs.ts
14083
- var officeICAOs = {
14091
+ // src/@dictionaries/dictionaries.icao.ts
14092
+ var dict_icao = {
14084
14093
  "KLUB": "Lubbock, TX",
14085
14094
  "KLCH": "Lake Charles, LA",
14086
14095
  "TSTL": "St. Louis, MO",
@@ -14325,12 +14334,12 @@ var officeICAOs = {
14325
14334
  var getEventOffice = (options) => {
14326
14335
  var _a, _b, _c, _d, _e, _f, _g;
14327
14336
  const office = options.pVtec != null ? (_b = (_a = options.pVtec) == null ? void 0 : _a.tracking) == null ? void 0 : _b.split(`.`)[0] : (_e = (_c = options.attributes) == null ? void 0 : _c.cccc) != null ? _e : options.organization != null ? Array.isArray(options.organization) ? (_d = options.organization) == null ? void 0 : _d[0] : options.organization : null;
14328
- const name = (_g = (_f = officeICAOs) == null ? void 0 : _f[office]) != null ? _g : null;
14337
+ const name = (_g = (_f = dict_icao) == null ? void 0 : _f[office]) != null ? _g : null;
14329
14338
  return { office, name };
14330
14339
  };
14331
14340
 
14332
- // src/@dictionaries/dictionaries.eventTags.ts
14333
- var eventTags = {
14341
+ // src/@dictionaries/dictionaries.tags.ts
14342
+ var dict_tags = {
14334
14343
  "FROSTBITE AND HYPOTHERMIA ARE LIKELY": "Frostbite and Hypothermia Likely",
14335
14344
  "LICKELY BECOME SLICK AND HAZARDOUS": "Slick and Hazardous Roads",
14336
14345
  "SLIPPERY ROAD CONDITIONS": "Slippery Roads",
@@ -14407,60 +14416,61 @@ var eventTags = {
14407
14416
 
14408
14417
  // src/@building/building.tags.ts
14409
14418
  var getEventTags = (message) => {
14410
- return Object.entries(eventTags).filter(([key]) => message == null ? void 0 : message.toLowerCase().includes(key.toLowerCase())).map(([, value]) => value);
14419
+ return Object.entries(dict_tags).filter(([key]) => message == null ? void 0 : message.toLowerCase().includes(key.toLowerCase())).map(([, value]) => value);
14411
14420
  };
14412
14421
 
14413
14422
  // src/@building/building.properties.ts
14414
14423
  var properties = (options) => {
14415
- var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _A, _B, _C, _D, _E, _F, _G, _H, _I, _J, _K, _L;
14416
- const organization = (_b = (_a = options.message.match(regExp.wmo)) == null ? void 0 : _a[0]) != null ? _b : null;
14424
+ var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _A, _B, _C, _D, _E, _F, _G, _H, _I, _J, _K, _L, _M, _N, _O, _P, _Q, _R, _S, _T, _U, _V, _W, _X;
14425
+ const organization = (_b = (_a = options.message.match(dict_expressions.wmo)) == null ? void 0 : _a[0]) != null ? _b : null;
14417
14426
  const polygons = getPolygonFromProduct(options.message);
14418
14427
  const properties2 = {
14419
14428
  locations: (_e = (_d = (_c = options == null ? void 0 : options.ugc) == null ? void 0 : _c.locations) == null ? void 0 : _d.join(`; `)) != null ? _e : null,
14420
- description: getDescriptionFromProduct({ message: options.message, handle: (_g = (_f = options == null ? void 0 : options.pVtec) == null ? void 0 : _f.vtec) != null ? _g : null }),
14429
+ locations_array: (_g = (_f = options == null ? void 0 : options.ugc) == null ? void 0 : _f.locations) != null ? _g : [],
14430
+ description: getDescriptionFromProduct({ message: options.message, handle: (_i = (_h = options == null ? void 0 : options.pVtec) == null ? void 0 : _h.vtec) != null ? _i : null }),
14421
14431
  attributes: options.attributes,
14422
14432
  geocode: {
14423
14433
  office: getEventOffice({ attributes: options.attributes, organization, pVtec: options.pVtec }),
14424
14434
  organization,
14425
- ugc: (_i = (_h = options == null ? void 0 : options.ugc) == null ? void 0 : _h.zones) != null ? _i : [],
14435
+ ugc: (_k = (_j = options == null ? void 0 : options.ugc) == null ? void 0 : _j.zones) != null ? _k : [],
14426
14436
  polygon: polygons.length > 0 ? Buffer.from(JSON.stringify([polygons])).toString("base64") : null,
14427
14437
  polygon_generated: polygons.length > 0 ? true : false
14428
14438
  },
14429
14439
  parameters: {
14430
14440
  tags: getEventTags(options.message),
14431
- instructions: (_j = getTextFromProduct({ message: options.message, find: [`For your protection`, `do not`, `use extreme caution`], append: `...`, removal: [`.`] })) != null ? _j : null,
14432
- source: (_k = getTextFromProduct({ message: options.message, find: [`SOURCE...`], removal: [`.`] })) != null ? _k : null,
14433
- hazards: (_l = getTextFromProduct({ message: options.message, find: [`HAZARD...`], removal: [`.`] })) != null ? _l : null,
14434
- impacts: (_m = getTextFromProduct({ message: options.message, find: [`IMPACT...`], removal: [`.`] })) != null ? _m : null,
14435
- estimated_hail_size: (_n = getTextFromProduct({ message: options.message, find: [`MAX HAIL SIZE...`, `HAIL...`], removal: ["in"] })) != null ? _n : null,
14436
- estimated_wind_gusts: (_o = getTextFromProduct({ message: options.message, find: [`MAX WIND GUST...`, `WIND...`] })) != null ? _o : null,
14437
- damage_threat: (_p = getTextFromProduct({ message: options.message, find: [`DAMAGE THREAT...`], removal: [] })) != null ? _p : null,
14438
- tornado_threat: (_q = getTextFromProduct({ message: options.message, find: [`TORNADO...`, `WATERSPOUT...`] })) != null ? _q : null,
14439
- flood_threat: (_r = getTextFromProduct({ message: options.message, find: [`FLASH FLOOD...`] })) != null ? _r : null,
14440
- wind_threat: (_s = getTextFromProduct({ message: options.message, find: [`WIND THREAT...`] })) != null ? _s : null,
14441
- hail_threat: (_t = getTextFromProduct({ message: options.message, find: [`HAIL THREAT...`], removal: [] })) != null ? _t : null
14441
+ instructions: (_l = getTextFromProduct({ message: options.message, find: [`For your protection`, `do not`, `use extreme caution`], append: `...`, removal: [`.`] })) != null ? _l : null,
14442
+ source: (_m = getTextFromProduct({ message: options.message, find: [`SOURCE...`], removal: [`.`] })) != null ? _m : null,
14443
+ hazards: (_n = getTextFromProduct({ message: options.message, find: [`HAZARD...`], removal: [`.`] })) != null ? _n : null,
14444
+ impacts: (_o = getTextFromProduct({ message: options.message, find: [`IMPACT...`], removal: [`.`] })) != null ? _o : null,
14445
+ estimated_hail_size: (_p = getTextFromProduct({ message: options.message, find: [`MAX HAIL SIZE...`, `HAIL...`], removal: ["in"] })) != null ? _p : null,
14446
+ estimated_wind_gusts: (_q = getTextFromProduct({ message: options.message, find: [`MAX WIND GUST...`, `WIND...`] })) != null ? _q : null,
14447
+ damage_threat: (_r = getTextFromProduct({ message: options.message, find: [`DAMAGE THREAT...`], removal: [] })) != null ? _r : null,
14448
+ tornado_threat: (_s = getTextFromProduct({ message: options.message, find: [`TORNADO...`, `WATERSPOUT...`] })) != null ? _s : null,
14449
+ flood_threat: (_t = getTextFromProduct({ message: options.message, find: [`FLASH FLOOD...`] })) != null ? _t : null,
14450
+ wind_threat: (_u = getTextFromProduct({ message: options.message, find: [`WIND THREAT...`] })) != null ? _u : null,
14451
+ hail_threat: (_v = getTextFromProduct({ message: options.message, find: [`HAIL THREAT...`], removal: [] })) != null ? _v : null
14442
14452
  },
14443
- spc_parameters: {
14444
- spc_number: (_u = getTextFromProduct({ message: options.message, find: [`Mesoscale Discussion `], removal: [`Mesoscale Discussion`, `Number`, `...`] })) != null ? _u : null,
14445
- spc_concerning: (_v = getTextFromProduct({ message: options.message, find: [`Concerning...`] })) != null ? _v : null,
14446
- spc_max_tornado: (_w = getTextFromProduct({ message: options.message, find: [`MOST PROBABLE PEAK TORNADO INTENSITY...`] })) != null ? _w : null,
14447
- spc_max_hail: (_x = getTextFromProduct({ message: options.message, find: [`MOST PROBABLE PEAK HAIL SIZE...`] })) != null ? _x : null,
14448
- spc_max_wind: (_y = getTextFromProduct({ message: options.message, find: [`MOST PROBABLE PEAK WIND GUST...`] })) != null ? _y : null,
14449
- spc_watch_issuance: (_z = getTextFromProduct({ message: options.message, find: [`Probability of Watch Issuance...`], removal: [`percent`] })) != null ? _z : null
14453
+ discussion_parameters: {
14454
+ discussion_number: (_y = (_x = (_w = getTextFromProduct({ message: options.message, find: [`Mesoscale Discussion `], removal: [`Mesoscale Discussion`, `Number`, `...`] })) == null ? void 0 : _w.toString()) == null ? void 0 : _x.padStart(4, "0")) != null ? _y : null,
14455
+ discussion_concerning: (_z = getTextFromProduct({ message: options.message, find: [`Concerning...`] })) != null ? _z : null,
14456
+ discussion_max_tornado: (_A = getTextFromProduct({ message: options.message, find: [`MOST PROBABLE PEAK TORNADO INTENSITY...`] })) != null ? _A : null,
14457
+ discussion_max_hail: (_B = getTextFromProduct({ message: options.message, find: [`MOST PROBABLE PEAK HAIL SIZE...`] })) != null ? _B : null,
14458
+ discussion_max_wind: (_C = getTextFromProduct({ message: options.message, find: [`MOST PROBABLE PEAK WIND GUST...`] })) != null ? _C : null,
14459
+ discussion_watch_issuance: (_D = getTextFromProduct({ message: options.message, find: [`Probability of Watch Issuance...`], removal: [`percent`] })) != null ? _D : null
14450
14460
  },
14451
14461
  watch_parameters: {
14452
- watch_number: (_C = (_B = (_A = getTextFromProduct({ message: options.message, find: [`ITIES FOR`, `UPDATE FOR`, `Watch Number `], removal: [`%`, `<`, `:`] })) == null ? void 0 : _A.replace(/(WT|WS|)/g, "")) == null ? void 0 : _B.trim()) != null ? _C : null,
14462
+ watch_number: ((_E = options == null ? void 0 : options.pVtec) == null ? void 0 : _E.is_watch) && ((_O = (_N = (_I = (_H = (_G = (_F = getTextFromProduct({ message: options.message, find: [`ITIES FOR`, `UPDATE FOR`, `Watch Number `], removal: [`%`, `<`, `:`] })) == null ? void 0 : _F.replace(/(WT|WS|)/g, "")) == null ? void 0 : _G.trim()) == null ? void 0 : _H.toString()) == null ? void 0 : _I.padStart(4, "0")) != null ? _N : (_M = (_L = (_K = (_J = options == null ? void 0 : options.pVtec) == null ? void 0 : _J.tracking) == null ? void 0 : _K.slice(-4)) == null ? void 0 : _L.toString()) == null ? void 0 : _M.padStart(4, "0")) != null ? _O : null),
14453
14463
  watch_type: options.message.includes(`TORNADO WATCH`) ? `Tornado` : (options == null ? void 0 : options.message.includes(`SEVERE`)) ? `Severe` : null,
14454
- additional_tornadoes_probability: (_D = getTextFromProduct({ message: options.message, find: [`PROB OF 2 OR MORE TORNADOES`], removal: [`%`, `<`, `:`] })) != null ? _D : null,
14455
- strong_tornadoes_probability: (_E = getTextFromProduct({ message: options.message, find: [`PROB OF 1 OR MORE STRONG /EF2-EF5/ TORNADOES`], removal: [`%`, `<`, `:`] })) != null ? _E : null,
14456
- severe_wind_probability: (_F = getTextFromProduct({ message: options.message, find: [`PROB OF 10 OR MORE SEVERE WIND EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _F : null,
14457
- severe_hail_probability: (_G = getTextFromProduct({ message: options.message, find: [`PROB OF 10 OR MORE SEVERE HAIL EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _G : null,
14458
- hail_2in_probability: (_H = getTextFromProduct({ message: options.message, find: [`PROB OF 1 OR MORE HAIL EVENTS >= 2 INCHES`], removal: [`%`, `<`, `:`] })) != null ? _H : null,
14459
- combined_hail_wind_probability: (_I = getTextFromProduct({ message: options.message, find: [`PROB OF 6 OR MORE COMBINED SEVERE HAIL/WIND EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _I : null,
14460
- max_hail_in: (_J = getTextFromProduct({ message: options.message, find: [`MAX HAIL /INCHES/`], removal: [`%`, `<`, `:`] })) != null ? _J : null,
14461
- max_wind_surface: (_K = getTextFromProduct({ message: options.message, find: [`MAX WIND GUSTS SURFACE /KNOTS/`], removal: [`%`, `<`, `:`] })) != null ? _K : null,
14462
- max_tops_x100feet: (_L = getTextFromProduct({ message: options.message, find: [`MAX TOPS /X 100 FEET/`], removal: [`%`, `<`, `:`] })) != null ? _L : null,
14463
- pds_watch: getTextFromProduct({ message: options.message, find: [`PARTICULARLY DANGEROUS SITUATION`], removal: [`%`, `<`, `:`] }) === `YES`
14464
+ additional_tornadoes_probability: (_P = getTextFromProduct({ message: options.message, find: [`PROB OF 2 OR MORE TORNADOES`], removal: [`%`, `<`, `:`] })) != null ? _P : null,
14465
+ strong_tornadoes_probability: (_Q = getTextFromProduct({ message: options.message, find: [`PROB OF 1 OR MORE STRONG /EF2-EF5/ TORNADOES`], removal: [`%`, `<`, `:`] })) != null ? _Q : null,
14466
+ severe_wind_probability: (_R = getTextFromProduct({ message: options.message, find: [`PROB OF 10 OR MORE SEVERE WIND EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _R : null,
14467
+ severe_hail_probability: (_S = getTextFromProduct({ message: options.message, find: [`PROB OF 10 OR MORE SEVERE HAIL EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _S : null,
14468
+ hail_2in_probability: (_T = getTextFromProduct({ message: options.message, find: [`PROB OF 1 OR MORE HAIL EVENTS >= 2 INCHES`], removal: [`%`, `<`, `:`] })) != null ? _T : null,
14469
+ combined_hail_wind_probability: (_U = getTextFromProduct({ message: options.message, find: [`PROB OF 6 OR MORE COMBINED SEVERE HAIL/WIND EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _U : null,
14470
+ max_hail_in: (_V = getTextFromProduct({ message: options.message, find: [`MAX HAIL /INCHES/`], removal: [`%`, `<`, `:`] })) != null ? _V : null,
14471
+ max_wind_surface: (_W = getTextFromProduct({ message: options.message, find: [`MAX WIND GUSTS SURFACE /KNOTS/`], removal: [`%`, `<`, `:`] })) != null ? _W : null,
14472
+ max_tops_x100feet: (_X = getTextFromProduct({ message: options.message, find: [`MAX TOPS /X 100 FEET/`], removal: [`%`, `<`, `:`] })) != null ? _X : null,
14473
+ pds_watch: getTextFromProduct({ message: options.message, find: [`PARTICULARLY DANGEROUS SITUATION`], removal: [`%`, `<`, `:`] }) === `YES` ? true : null
14464
14474
  }
14465
14475
  };
14466
14476
  if (isNaN(Number(properties2.watch_parameters.watch_number))) {
@@ -14478,8 +14488,8 @@ var getEventHeader = (options) => {
14478
14488
  return `ZCZC-ATMOSX-${options.getType.prefix}-${ugc2}-${(_b = vtec2 == null ? void 0 : vtec2.status) != null ? _b : `Issued`}-${(/* @__PURE__ */ new Date()).toISOString().replace(/[-:]/g, "").split(".")[0]}-${(_c = properties2.geocode.office.office) != null ? _c : `KWNS`}`;
14479
14489
  };
14480
14490
 
14481
- // src/@dictionaries/dictionaries.eventsMatchText.ts
14482
- var eventsMatchText = {
14491
+ // src/@dictionaries/dictionaries.matches.ts
14492
+ var dict_matches = {
14483
14493
  "Special Weather Statement": "Special Weather Statement",
14484
14494
  "Hurricane Warning": "Hurricane Warning",
14485
14495
  "Hurricane Force Wind Warning": "Hurricane Force Wind Warning",
@@ -14499,7 +14509,7 @@ var eventsMatchText = {
14499
14509
 
14500
14510
  // src/@building/building.tracking.ts
14501
14511
  var getEventTracking = (options) => {
14502
- var _a, _b, _c, _d, _e, _f, _g;
14512
+ var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j;
14503
14513
  const properties2 = options.properties;
14504
14514
  const attributes = options.attributes;
14505
14515
  const stanza = options.stanza;
@@ -14516,26 +14526,26 @@ var getEventTracking = (options) => {
14516
14526
  }
14517
14527
  if (options.type === `API`) {
14518
14528
  if (options.vtec) {
14519
- const vtecValue = Array.isArray(options.vtec) ? options.vtec[0] : options.vtec;
14529
+ const vtecValue = Array.isArray(options.vtec) ? options.vtec[0].vtec : (_c = options.vtec) == null ? void 0 : _c.vtec;
14520
14530
  const splitPVTEC = vtecValue.split(".");
14521
14531
  return `${splitPVTEC[2]}.${splitPVTEC[3]}.${splitPVTEC[4]}.${splitPVTEC[5]}`;
14522
14532
  }
14523
- const wmoMatch = (_d = (_c = options.organization) == null ? void 0 : _c.wmoidentifier) == null ? void 0 : _d.match(/([A-Z]{4}\d{2})\s+([A-Z]{4})/);
14524
- const station = (_e = wmoMatch == null ? void 0 : wmoMatch[2]) != null ? _e : "N/A";
14533
+ const wmoMatch = (_e = (_d = options.organization) == null ? void 0 : _d.wmoidentifier) == null ? void 0 : _e.match(/([A-Z]{4}\d{2})\s+([A-Z]{4})/);
14534
+ const station = (_f = wmoMatch == null ? void 0 : wmoMatch[2]) != null ? _f : "N/A";
14525
14535
  if (options.organization.featureId) {
14526
14536
  const idMatch = options.organization.featureId.match(/([a-f0-9]+)\.(\d+)\.(\d+)$/);
14527
- return `${station}.${(_f = idMatch == null ? void 0 : idMatch[1]) != null ? _f : "N/A"}`;
14537
+ return `${station}.${(_h = (_g = idMatch == null ? void 0 : idMatch[0]) == null ? void 0 : _g.replace(/\./g, "")) != null ? _h : "N/A"}`;
14528
14538
  }
14529
- const id2 = (_g = wmoMatch == null ? void 0 : wmoMatch[1]) != null ? _g : "N/A";
14530
- return `${station}.${id2}`;
14539
+ const id2 = (_i = wmoMatch == null ? void 0 : wmoMatch[1]) != null ? _i : "N/A";
14540
+ return `${station}.${(_j = id2 == null ? void 0 : id2.replace(/\./g, "")) != null ? _j : "N/A"}`;
14531
14541
  }
14532
14542
  };
14533
14543
 
14534
14544
  // src/@building/building.validate.ts
14535
14545
  var import_crypto = require("crypto");
14536
14546
 
14537
- // src/@dictionaries/dictionaries.betterEventNames.ts
14538
- var betterEventNames = {
14547
+ // src/@dictionaries/dictionaries.enhanced.ts
14548
+ var dict_enhanced = {
14539
14549
  "Tornado Warning": {
14540
14550
  "Tornado Emergency": {
14541
14551
  description: "tornado emergency"
@@ -14553,6 +14563,11 @@ var betterEventNames = {
14553
14563
  },
14554
14564
  "Radar Indicated Tornado Warning": {}
14555
14565
  },
14566
+ "Fire Weather Warning": {
14567
+ "PDS Fire Weather Warning": {
14568
+ description: "particularly dangerous situation"
14569
+ }
14570
+ },
14556
14571
  "Blizzard Warning": {
14557
14572
  "PDS Blizzard Warning": {
14558
14573
  description: "particularly dangerous situation"
@@ -14570,7 +14585,12 @@ var betterEventNames = {
14570
14585
  },
14571
14586
  "Tornado Watch": {
14572
14587
  "PDS Tornado Watch": {
14573
- description: "particularly dangerous situation"
14588
+ pdswatch: true
14589
+ }
14590
+ },
14591
+ "Severe Thunderstorm Watch": {
14592
+ "PDS Severe Thunderstorm Watch": {
14593
+ pdswatch: true
14574
14594
  }
14575
14595
  },
14576
14596
  "Flash Flood Warning": {
@@ -14611,16 +14631,17 @@ var betterEventNames = {
14611
14631
 
14612
14632
  // src/@building/building.enhance.ts
14613
14633
  var getEventEnhancedName = (event) => {
14614
- var _a, _b, _c, _d, _e, _f, _g;
14634
+ var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j;
14615
14635
  const configurations = bootstrap.settings;
14616
14636
  let name = (_a = event == null ? void 0 : event.properties) == null ? void 0 : _a.event;
14617
14637
  if (!((_b = configurations == null ? void 0 : configurations.GlobalSettings) == null ? void 0 : _b.BetterEventNames)) {
14618
14638
  return name;
14619
14639
  }
14620
14640
  const damage = (_d = (_c = event == null ? void 0 : event.properties) == null ? void 0 : _c.parameters) == null ? void 0 : _d.damage_threat;
14621
- const tornado = (_e = event == null ? void 0 : event.properties) == null ? void 0 : _e.parameters.tornado_threat;
14622
- const description = (_g = (_f = event == null ? void 0 : event.properties) == null ? void 0 : _f.description) == null ? void 0 : _g.toLowerCase();
14623
- for (const [eventKey, eventConfig] of Object.entries(betterEventNames)) {
14641
+ const tornado = (_f = (_e = event == null ? void 0 : event.properties) == null ? void 0 : _e.parameters) == null ? void 0 : _f.tornado_threat;
14642
+ const pdswatch = (_h = (_g = event == null ? void 0 : event.properties) == null ? void 0 : _g.watch_parameters) == null ? void 0 : _h.pds_watch;
14643
+ const description = (_j = (_i = event == null ? void 0 : event.properties) == null ? void 0 : _i.description) == null ? void 0 : _j.toLowerCase();
14644
+ for (const [eventKey, eventConfig] of Object.entries(dict_enhanced)) {
14624
14645
  if (eventKey !== name) continue;
14625
14646
  for (const [paramKey, paramValue] of Object.entries(eventConfig)) {
14626
14647
  let matches = true;
@@ -14633,6 +14654,9 @@ var getEventEnhancedName = (event) => {
14633
14654
  if (paramValue == null ? void 0 : paramValue.tornado) {
14634
14655
  if (paramValue.tornado !== tornado) matches = false;
14635
14656
  }
14657
+ if (paramValue == null ? void 0 : paramValue.pdswatch) {
14658
+ if (paramValue.pdswatch !== pdswatch) matches = false;
14659
+ }
14636
14660
  if (matches) {
14637
14661
  name = paramKey;
14638
14662
  break;
@@ -14642,8 +14666,8 @@ var getEventEnhancedName = (event) => {
14642
14666
  return name;
14643
14667
  };
14644
14668
 
14645
- // src/@dictionaries/dictionaries.statusCorrelationText.ts
14646
- var statusCorrelationText = [
14669
+ // src/@dictionaries/dictionaries.correlations.ts
14670
+ var dict_correlations = [
14647
14671
  { type: "Statement", name: "Statement", isCancel: false, isUpdate: false, isIssued: true, isStatement: true },
14648
14672
  { type: "Update", name: "Updated", isCancel: false, isUpdate: true, isIssued: false, isStatement: false },
14649
14673
  { type: "Cancel", name: "Cancelled", isCancel: true, isUpdate: false, isIssued: false, isStatement: false },
@@ -14658,11 +14682,12 @@ var statusCorrelationText = [
14658
14682
  { type: "Routine", name: "Routine", isCancel: false, isUpdate: true, isIssued: false, isStatement: false }
14659
14683
  ];
14660
14684
 
14661
- // src/@dictionaries/dictionaries.eventCancelMessages.ts
14662
- var eventCancelMessages = [
14685
+ // src/@dictionaries/dictionaries.cancellation.ts
14686
+ var dict_cancellation = [
14663
14687
  "has been cancelled",
14664
14688
  "subsided sufficiently for the advisory to be cancelled",
14665
14689
  "has been cancelled",
14690
+ "no tsunami threat from a nearby earthquake",
14666
14691
  "will be allowed to expire",
14667
14692
  "has diminished",
14668
14693
  "and no longer",
@@ -14671,24 +14696,28 @@ var eventCancelMessages = [
14671
14696
  "has weakened below severe"
14672
14697
  ];
14673
14698
 
14674
- // src/@dictionaries/dictionaries.testSignatures.ts
14675
- var testSignatures = [
14699
+ // src/@dictionaries/dictionaries.testing.ts
14700
+ var dict_testing = [
14676
14701
  `This is a test message`,
14677
14702
  `Monitoring message only.`,
14678
- `THIS_MESSAGE_IS_FOR_TEST_PURPOSES_ONLY`
14703
+ `THIS_MESSAGE_IS_FOR_TEST_PURPOSES_ONLY`,
14704
+ "TEST MESSAGE"
14679
14705
  ];
14680
14706
 
14681
- // src/@dictionaries/dictionaries.eventProducts.ts
14682
- var eventProducts = {
14707
+ // src/@dictionaries/dictionaries.products.ts
14708
+ var dict_products = {
14683
14709
  "O": "Operational Product",
14684
14710
  "T": "Test Product",
14685
14711
  "E": "Experimental Product",
14686
14712
  "X": "Experimental Product (Non-Operational)"
14687
14713
  };
14688
14714
 
14689
- // src/@dictionaries/dictionaries.hailStrings.ts
14690
- var hailStrings = {
14715
+ // src/@dictionaries/dictionaries.hail.ts
14716
+ var dict_hail = {
14717
+ ".25": "Pea",
14718
+ ".50": "Penny",
14691
14719
  ".75": "Penny",
14720
+ "Up to .75": "Penny",
14692
14721
  ".88": "Nickel",
14693
14722
  "0.75": "Penny",
14694
14723
  "0.88": "Nickel",
@@ -14704,25 +14733,25 @@ var hailStrings = {
14704
14733
 
14705
14734
  // src/@building/building.signature.ts
14706
14735
  var getEventSignature = (event) => {
14707
- var _a, _b, _c, _d, _e, _f;
14736
+ var _a, _b, _c, _d, _e, _f, _g, _h;
14708
14737
  const properties2 = event == null ? void 0 : event.properties;
14709
14738
  const vtec2 = (_b = (_a = event == null ? void 0 : event.properties) == null ? void 0 : _a.metadata) == null ? void 0 : _b.vtec;
14710
- const status = statusCorrelationText.find((c) => c.type === (properties2 == null ? void 0 : properties2.status));
14711
- const csig = eventCancelMessages.find((sig) => properties2.description.toLowerCase().includes(sig.toLowerCase()));
14739
+ const status = dict_correlations.find((c) => c.type === (properties2 == null ? void 0 : properties2.status));
14740
+ const csig = dict_cancellation.find((sig) => properties2.description.toLowerCase().includes(sig.toLowerCase()));
14712
14741
  properties2.status_metadata = __spreadProps(__spreadValues({}, properties2.status_metadata), { is_issued: true, is_test: false });
14713
- if (properties2.parameters.estimated_hail_size) {
14714
- properties2.parameters.estimated_hail_size += ` (${(_c = hailStrings[properties2.parameters.estimated_hail_size]) != null ? _c : "--"})`;
14742
+ if ((_c = properties2 == null ? void 0 : properties2.parameters) == null ? void 0 : _c.estimated_hail_size) {
14743
+ properties2.parameters.estimated_hail_size += ` (${(_e = dict_hail[(_d = properties2 == null ? void 0 : properties2.parameters) == null ? void 0 : _d.estimated_hail_size]) != null ? _e : "--"})`;
14715
14744
  }
14716
14745
  if (status) {
14717
- properties2.status = (_d = status.name) != null ? _d : properties2.status;
14746
+ properties2.status = (_f = status.name) != null ? _f : properties2.status;
14718
14747
  properties2.status_metadata = __spreadProps(__spreadValues({}, properties2.status_metadata), { is_updated: !!status.isUpdate, is_issued: !!status.isIssued, is_expired: !!status.isCancel, is_statement: !!status.isStatement });
14719
14748
  }
14720
14749
  if (csig) {
14721
14750
  properties2.status_metadata = __spreadProps(__spreadValues({}, properties2.status_metadata), { is_expired: true });
14722
14751
  }
14723
- const getProduct = (_f = (_e = vtec2 == null ? void 0 : vtec2.vtec) == null ? void 0 : _e.split(`.`)[0]) == null ? void 0 : _f.replace(`/`, ``);
14724
- const isTestProduct = eventProducts[getProduct] == `Test Product`;
14725
- if (isTestProduct || testSignatures.some((sig) => {
14752
+ const getProduct = (_h = (_g = vtec2 == null ? void 0 : vtec2.vtec) == null ? void 0 : _g.split(`.`)[0]) == null ? void 0 : _h.replace(`/`, ``);
14753
+ const isTestProduct = dict_products[getProduct] == `Test Product`;
14754
+ if (isTestProduct || dict_testing.some((sig) => {
14726
14755
  var _a2, _b2, _c2, _d2;
14727
14756
  return (_d2 = (_a2 = properties2.description) == null ? void 0 : _a2.toLowerCase().includes(sig.toLowerCase())) != null ? _d2 : (_c2 = (_b2 = properties2 == null ? void 0 : properties2.parameters) == null ? void 0 : _b2.instructions) == null ? void 0 : _c2.toLowerCase().includes(sig.toLowerCase());
14728
14757
  })) {
@@ -14749,74 +14778,6 @@ var setHash = (event, entry) => {
14749
14778
  }
14750
14779
  };
14751
14780
 
14752
- // src/@modules/@utilities/utilities.createHttp.ts
14753
- var import_request = __toESM(require("request"));
14754
- var createHttp = (options) => __async(null, null, function* () {
14755
- return new Promise((resolve6, reject) => {
14756
- var _a, _b, _c, _d, _e;
14757
- const requestOptions = {
14758
- url: (_a = options.url) != null ? _a : `https://api.weather.gov/alerts/active`,
14759
- headers: (_b = options.headers) != null ? _b : {
14760
- "User-Agent": "AtmosphericX",
14761
- "Accept": "application/geo+json, text/plain, */*; q=0.9",
14762
- "Accept-Language": "en-US,en;q=0.9"
14763
- },
14764
- method: (_c = options.method) != null ? _c : `GET`,
14765
- timeout: (_d = options.timeout) != null ? _d : 1e4,
14766
- proxy: (_e = options.proxy) != null ? _e : null,
14767
- maxRedirects: 1
14768
- };
14769
- if (options.formData) {
14770
- requestOptions["formData"] = options.formData;
14771
- } else if (options.body) {
14772
- requestOptions["body"] = options.body;
14773
- }
14774
- (0, import_request.default)(requestOptions, (error, response2, body) => {
14775
- var _a2, _b2, _c2, _d2, _e2;
14776
- if (error) {
14777
- return resolve6({
14778
- error: true,
14779
- options: requestOptions,
14780
- status: -1,
14781
- message: (_a2 = error.message) != null ? _a2 : `Unknown Error`
14782
- });
14783
- }
14784
- if (response2.statusCode < 200 || response2.statusCode >= 300) {
14785
- return resolve6({
14786
- error: true,
14787
- options: requestOptions,
14788
- status: (_b2 = response2.statusCode) != null ? _b2 : -1,
14789
- message: `HTTP Status Code ${(_c2 = response2.statusCode) != null ? _c2 : `Unknown Status Code`} (${body})`
14790
- });
14791
- }
14792
- if (body == void 0 || body == null) {
14793
- return resolve6({
14794
- error: true,
14795
- options: requestOptions,
14796
- status: (_d2 = response2.statusCode) != null ? _d2 : -1,
14797
- message: `Empty Response Body`
14798
- });
14799
- }
14800
- resolve6({
14801
- error: false,
14802
- options: requestOptions,
14803
- status: (_e2 = response2.statusCode) != null ? _e2 : -1,
14804
- message: body
14805
- });
14806
- });
14807
- });
14808
- });
14809
-
14810
- // src/@modules/@utilities/utilities.isImageReady.ts
14811
- var isImageReady = (url) => __async(null, null, function* () {
14812
- try {
14813
- const res = yield fetch(url, { method: "HEAD" });
14814
- return res.ok;
14815
- } catch (e) {
14816
- return false;
14817
- }
14818
- });
14819
-
14820
14781
  // src/@modules/@eas/eas.getWavPCM16.ts
14821
14782
  var getWavPCM16 = (buffer) => {
14822
14783
  if (buffer.toString("ascii", 0, 4) !== "RIFF" || buffer.toString("ascii", 8, 12) !== "WAVE") {
@@ -15061,17 +15022,34 @@ var getPCM16 = (samples, sampleRate) => {
15061
15022
 
15062
15023
  // src/@modules/@eas/eas.getTTS.ts
15063
15024
  var import_os = require("os");
15025
+ var import_fs = require("fs");
15064
15026
  var import_child_process = require("child_process");
15065
15027
  var getTTS = (text2, outputPath) => __async(null, null, function* () {
15066
15028
  const vPlatform = (0, import_os.platform)();
15067
15029
  switch (vPlatform) {
15068
15030
  case "win32": {
15069
- const command = `Add-Type -AssemblyName System.Speech;$speak = New-Object System.Speech.Synthesis.SpeechSynthesizer;$speak.SetOutputToWaveFile('${outputPath}');$speak.Speak('${text2}');$speak.Dispose();`;
15070
- (0, import_child_process.execSync)(`powershell -Command "${command}"`, { stdio: "ignore" });
15031
+ try {
15032
+ const txtPath = outputPath + ".txt";
15033
+ (0, import_fs.writeFileSync)(txtPath, text2, "utf8");
15034
+ const command = [
15035
+ "Add-Type -AssemblyName System.Speech;",
15036
+ `$speak = New-Object System.Speech.Synthesis.SpeechSynthesizer;`,
15037
+ `$text = Get-Content -Raw -LiteralPath '${txtPath}';`,
15038
+ `$speak.SetOutputToWaveFile('${outputPath}');`,
15039
+ `$speak.Speak($text);`,
15040
+ `$speak.Dispose();`
15041
+ ].join(" ");
15042
+ (0, import_child_process.execSync)(`powershell -Command "${command}"`, { stdio: "inherit" });
15043
+ } catch (error) {
15044
+ console.error("Error occurred while generating TTS:", error);
15045
+ }
15071
15046
  break;
15072
15047
  }
15073
15048
  case "linux":
15074
- (0, import_child_process.execSync)(`espeak -w "${outputPath}" "${text2.replace(/"/g, '\\"')}"`);
15049
+ try {
15050
+ (0, import_child_process.execSync)(`espeak -w "${outputPath}" "${text2.replace(/"/g, '\\"')}"`);
15051
+ } catch (e) {
15052
+ }
15075
15053
  break;
15076
15054
  default:
15077
15055
  break;
@@ -15147,20 +15125,22 @@ var getCleanDescription = (message) => {
15147
15125
  for (const { regex, replacement } of patches) {
15148
15126
  message = message.replace(regex, replacement);
15149
15127
  }
15150
- return message.replace(/\b(\d{1,2}):(\d{2})\s*(AM|PM)\b/gi, (_, h, m, ap) => fmt(+h, +m, ap.toUpperCase())).replace(/\b(\d{1,2})\s+(\d{2})\s+(AM|PM)\b/gi, (_, h, m, ap) => fmt(+h, +m, ap.toUpperCase())).replace(/\b(\d{2})(\d{2})\s+(AM|PM)\b/gi, (_, hh, mm, ap) => fmt(+hh, +mm, ap.toUpperCase())).replace(/\*+/g, " ").replace(/-/g, " ").replace(/\n/g, " ").trim();
15128
+ return message.replace(/'/g, "''").replace(/\b(\d{1,2}):(\d{2})\s*(AM|PM)\b/gi, (_, h, m, ap) => fmt(+h, +m, ap.toUpperCase())).replace(/\b(\d{1,2})\s+(\d{2})\s+(AM|PM)\b/gi, (_, h, m, ap) => fmt(+h, +m, ap.toUpperCase())).replace(/\b(\d{2})(\d{2})\s+(AM|PM)\b/gi, (_, hh, mm, ap) => fmt(+hh, +mm, ap.toUpperCase())).replace(/\b(\d{1,2})\s+(AM|PM)\b/gi, (_, h, ap) => fmt(+h, 0, ap.toUpperCase())).replace(/\*+/g, " ").replace(/-/g, " ").replace(/\n/g, " ").trim();
15151
15129
  };
15152
15130
 
15153
15131
  // src/@modules/@eas/eas.setEasTone.ts
15154
15132
  var import_path2 = require("path");
15155
- var import_fs = require("fs");
15133
+ var import_fs2 = require("fs");
15156
15134
  var import_child_process2 = require("child_process");
15157
15135
  var import_os2 = require("os");
15158
15136
  var setEasTone = (options) => __async(null, null, function* () {
15137
+ var _a;
15159
15138
  const settings = bootstrap.settings;
15160
- const directory = settings.GlobalSettings.EASSettings.ArchiveDirectory;
15161
- const prefix = settings.GlobalSettings.EASSettings.IntroWavFile;
15139
+ const directory = settings.GlobalSettings.ArchiveSettings.EasDirectory;
15140
+ const prefix = settings.GlobalSettings.ArchiveSettings.EasToneout;
15162
15141
  let message = options.message;
15163
15142
  let header = options.header;
15143
+ let title = (_a = options.title) != null ? _a : `${Math.random().toString(36).substring(2, 15)}-${header.replace(/[^a-zA-Z0-9]/g, "")}`;
15164
15144
  if (!message || !header) {
15165
15145
  setWarning({
15166
15146
  title: `EAS`,
@@ -15171,17 +15151,17 @@ var setEasTone = (options) => __async(null, null, function* () {
15171
15151
  let buffTTS;
15172
15152
  let buffRadio;
15173
15153
  let buffFull = [];
15174
- if (!(0, import_fs.existsSync)(directory)) {
15175
- (0, import_fs.mkdirSync)(directory, { recursive: true });
15154
+ if (!(0, import_fs2.existsSync)(directory)) {
15155
+ (0, import_fs2.mkdirSync)(directory, { recursive: true });
15176
15156
  }
15177
- if (!(0, import_fs.existsSync)((0, import_path2.join)(directory, `/temp`))) {
15178
- (0, import_fs.mkdirSync)((0, import_path2.join)(directory, `/temp`), { recursive: true });
15157
+ if (!(0, import_fs2.existsSync)((0, import_path2.join)(directory, `/tts`))) {
15158
+ (0, import_fs2.mkdirSync)((0, import_path2.join)(directory, `/tts`), { recursive: true });
15179
15159
  }
15180
- if (!(0, import_fs.existsSync)((0, import_path2.join)(directory, `/output`))) {
15181
- (0, import_fs.mkdirSync)((0, import_path2.join)(directory, `/output`), { recursive: true });
15160
+ if (!(0, import_fs2.existsSync)((0, import_path2.join)(directory, `/encoded`))) {
15161
+ (0, import_fs2.mkdirSync)((0, import_path2.join)(directory, `/encoded`), { recursive: true });
15182
15162
  }
15183
- const tmpTTS = (0, import_path2.join)(directory, `/temp/${Math.random().toString(36).substring(2, 15)}-${header.replace(/[^a-zA-Z0-9]/g, "")}.wav`);
15184
- const outTTS = (0, import_path2.join)(directory, `/output/${Math.random().toString(36).substring(2, 15)}-${header.replace(/[^a-zA-Z0-9]/g, "")}.wav`);
15163
+ const tmpTTS = (0, import_path2.join)(directory, `/tts/${title}.wav`);
15164
+ const outTTS = (0, import_path2.join)(directory, `/encoded/${title}.wav`);
15185
15165
  const vPlatform = (0, import_os2.platform)();
15186
15166
  if (vPlatform === "darwin") {
15187
15167
  setWarning({
@@ -15193,25 +15173,28 @@ var setEasTone = (options) => __async(null, null, function* () {
15193
15173
  yield new Promise((resolve6, reject) => {
15194
15174
  const tMsg = getCleanDescription(message);
15195
15175
  getTTS(tMsg, tmpTTS).then(() => {
15196
- buffTTS = (0, import_fs.readFileSync)(tmpTTS);
15197
15176
  resolve6();
15198
15177
  });
15199
15178
  });
15179
+ if (!(0, import_fs2.existsSync)(tmpTTS)) {
15180
+ return null;
15181
+ }
15182
+ buffTTS = (0, import_fs2.readFileSync)(tmpTTS);
15200
15183
  const vWav = getWavPCM16(buffTTS);
15201
15184
  const vSamples = getSampledPCM16(vWav.samples, vWav.sampleRate, 8e3);
15202
15185
  const vRadio = setRadioEffect(vSamples, 8e3);
15203
- if ((0, import_fs.existsSync)(prefix)) {
15204
- let tBuffer = (0, import_fs.readFileSync)(prefix);
15186
+ if ((0, import_fs2.existsSync)(prefix)) {
15187
+ let tBuffer = (0, import_fs2.readFileSync)(prefix);
15205
15188
  let tWav = getWavPCM16(tBuffer);
15206
15189
  if (tWav == null) {
15207
15190
  try {
15208
- const converted = (0, import_path2.join)(directory, `/temp/${Math.random().toString(36).substring(2, 15)}.converted.wav`);
15191
+ const converted = (0, import_path2.join)(directory, `/tts/${title}.converted.wav`);
15209
15192
  (0, import_child_process2.execSync)(`ffmpeg -y -i "${prefix}" -ar 8000 -ac 1 -sample_fmt s16 "${converted}"`, { stdio: "ignore" });
15210
- if ((0, import_fs.existsSync)(converted)) {
15211
- tBuffer = (0, import_fs.readFileSync)(converted);
15193
+ if ((0, import_fs2.existsSync)(converted)) {
15194
+ tBuffer = (0, import_fs2.readFileSync)(converted);
15212
15195
  tWav = getWavPCM16(tBuffer);
15213
15196
  try {
15214
- (0, import_fs.unlinkSync)(converted);
15197
+ (0, import_fs2.unlinkSync)(converted);
15215
15198
  } catch (e) {
15216
15199
  }
15217
15200
  }
@@ -15243,138 +15226,241 @@ var setEasTone = (options) => __async(null, null, function* () {
15243
15226
  const aSamples = getMergedPCM16(buffFull);
15244
15227
  const aFinal = setNoise(aSamples, 2e-3);
15245
15228
  const aBuffer = getPCM16(Array.from(aFinal).map((v) => ({ value: v })), 8e3);
15246
- (0, import_fs.writeFileSync)(outTTS, aBuffer);
15229
+ (0, import_fs2.writeFileSync)(outTTS, aBuffer);
15247
15230
  try {
15248
- (0, import_fs.unlinkSync)(tmpTTS);
15231
+ (0, import_fs2.unlinkSync)(tmpTTS);
15249
15232
  } catch (e) {
15250
15233
  }
15251
15234
  return outTTS;
15252
15235
  });
15253
15236
 
15254
- // src/@manager/manager.createWebhook.ts
15255
- var import_fs2 = require("fs");
15256
- var import_form_data = __toESM(require_form_data());
15257
- var createWebhook = (options) => __async(null, null, function* () {
15258
- var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l;
15259
- const event = options.event.properties;
15260
- const settings = options.webhook;
15237
+ // src/@parsers/@text/text.getEmbed.ts
15238
+ var getEmebed = (event) => {
15239
+ var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _A, _B, _C, _D, _E, _F, _G, _H, _I, _J, _K, _L, _M, _N, _O, _P, _Q, _R, _S, _T, _U, _V, _W, _X, _Y, _Z, __, _$, _aa, _ba, _ca, _da, _ea, _fa, _ga, _ha, _ia, _ja, _ka, _la, _ma, _na, _oa, _pa, _qa, _ra, _sa, _ta, _ua, _va, _wa, _xa, _ya, _za, _Aa, _Ba, _Ca, _Da, _Ea, _Fa, _Ga, _Ha, _Ia, _Ja, _Ka, _La, _Ma, _Na;
15261
15240
  const line = (label, value, condition = true) => condition && value ? `${label} ${value}` : null;
15262
- const isLimited = setTimeoutAction({ identifier: options.webhook.webhook, interval: options.webhook.rate, max: options.webhook.rate, addTime: true });
15263
- if (!isLimited.limited) {
15264
- const isStatement = event.status_metadata.is_statement;
15265
- const isExpired = event.status_metadata.is_expired;
15266
- let body = [
15267
- line(`**Locations:**`, (_a = event == null ? void 0 : event.locations) == null ? void 0 : _a.slice(0, 100)),
15268
- line(`**Issued:**`, `<t:${Math.floor(new Date(event.issued).getTime() / 1e3)}:R>`),
15269
- line(`**Expires:**`, `<t:${Math.floor(new Date(event.expires).getTime() / 1e3)}:R>`, !isExpired && !isStatement),
15270
- line(`**Damage Threat:**`, event.parameters.damage_threat, !isExpired),
15271
- line(`**Flood Threat:**`, event.parameters.flood_threat, !isExpired),
15272
- line(`**Tornado Threat:**`, event.parameters.tornado_threat, !isExpired),
15273
- line(`**Estimated Wind Gusts:**`, `${event.parameters.estimated_wind_gusts} ${event.parameters.wind_threat ? ` (${event.parameters.wind_threat})` : ""}`, !isExpired && event.parameters.estimated_wind_gusts != null),
15274
- line(`**Estimated Hail Size:**`, `${event.parameters.estimated_hail_size} ${event.parameters.hail_threat ? ` (${event.parameters.hail_threat})` : ""}`, !isExpired && event.parameters.estimated_hail_size != null),
15275
- line(`**Discussion:**`, event.spc_parameters.spc_number, !isExpired),
15276
- line(`**Concern:**`, event.spc_parameters.spc_concerning, !isExpired),
15277
- line(`**SPC Max Tornado Threat:**`, event.spc_parameters.spc_max_tornado, !isExpired),
15278
- line(`**SPC Max Hail Threat:**`, event.spc_parameters.spc_max_hail, !isExpired),
15279
- line(`**SPC Max Wind Threat:**`, event.spc_parameters.spc_max_wind, !isExpired),
15280
- line(`**SPC Watch Issuance Probability:**`, event.spc_parameters.spc_watch_issuance ? `${event.spc_parameters.spc_watch_issuance}%` : null, !isExpired),
15281
- line(`**Watch Number:**`, event.watch_parameters.watch_number, !isExpired),
15282
- line(`**Strong Tornadoes Probability:**`, event.watch_parameters.strong_tornadoes_probability ? `${event.watch_parameters.strong_tornadoes_probability}%` : null, !isExpired),
15283
- line(`**Additional Tornadoes Probability:**`, event.watch_parameters.additional_tornadoes_probability ? `${event.watch_parameters.additional_tornadoes_probability}%` : null, !isExpired),
15284
- line(`**Combined Hail/Wind Probability:**`, event.watch_parameters.combined_hail_wind_probability ? `${event.watch_parameters.combined_hail_wind_probability}%` : null, !isExpired),
15285
- line(`**Severe Hail Probability:**`, event.watch_parameters.severe_hail_probability ? `${event.watch_parameters.severe_hail_probability}%` : null, !isExpired),
15286
- line(`**Hail >2in Probability:**`, event.watch_parameters.hail_2in_probability ? `${event.watch_parameters.hail_2in_probability}%` : null, !isExpired),
15287
- line(`**Max Hail Inches:**`, event.watch_parameters.max_hail_in, !isExpired),
15288
- line(`**Severe Wind Probability:**`, event.watch_parameters.severe_wind_probability ? `${event.watch_parameters.severe_wind_probability}%` : null, !isExpired),
15289
- line(`**Max Surface Wind:**`, event.watch_parameters.max_wind_surface, !isExpired),
15290
- line(`**Max Tops (x100 feet):**`, event.watch_parameters.max_tops_x100feet, !isExpired),
15291
- line(`**Tags:**`, ((_b = event.parameters.tags) == null ? void 0 : _b.length) > 0 ? event.parameters.tags.join(", ") : null, !isExpired),
15292
- line(`**Sender:**`, ((_d = (_c = event.geocode) == null ? void 0 : _c.office) == null ? void 0 : _d.name) ? `${event.geocode.office.name} (${event.geocode.office.office})` : (_f = (_e = event.geocode) == null ? void 0 : _e.office) == null ? void 0 : _f.office),
15293
- line(`**Tracking:**`, (_g = event.metadata) == null ? void 0 : _g.tracking),
15294
- line(`**Logs:**`, ((_h = event.metadata.history) == null ? void 0 : _h.length) > 0 ? event.metadata.history.length : null),
15295
- line(``, event.description ? "```\n" + event.description.split("\n").map((l) => l.trim()).filter(Boolean).join("\n") + "\n```" : null, !isExpired)
15296
- ].filter(Boolean).join("\n");
15297
- if (body.length > 1900) {
15298
- body = body.substring(0, 1900) + "\n\n[Message truncated due to length]";
15299
- const blocks = ((_i = body.match(/```/g)) != null ? _i : []).length;
15300
- if (blocks % 2 !== 0) body += "```";
15301
- }
15302
- if (event.description.length < 25) {
15303
- return;
15304
- }
15305
- const form = new import_form_data.default();
15306
- const img = (_j = event.metadata.attachments) == null ? void 0 : _j[0];
15307
- const embed = {
15308
- title: `${event.event} (${event.status})`,
15309
- description: body,
15310
- color: 16711680,
15311
- timestamp: (/* @__PURE__ */ new Date()).toISOString(),
15312
- image: {},
15313
- footer: { text: settings.title }
15314
- };
15315
- if (img) {
15316
- for (let i = 0; i < 5; i++) {
15317
- const ok = yield isImageReady(img);
15318
- if (ok) break;
15319
- yield new Promise((r) => setTimeout(r, 5e3));
15320
- }
15321
- const finalCheck = yield isImageReady(img);
15322
- if (finalCheck) {
15323
- embed.image = { url: img };
15324
- }
15325
- }
15326
- form.append("payload_json", JSON.stringify({
15327
- username: (_k = settings.title) != null ? _k : "AtmosphericX",
15328
- content: (_l = settings.message) != null ? _l : "",
15329
- embeds: [embed]
15330
- }));
15331
- if (settings.upload) {
15332
- form.append("fUpload", Buffer.from(`${event.metadata.raw}
15241
+ const isStatement = event.properties.status_metadata.is_statement;
15242
+ const isExpired = event.properties.status_metadata.is_expired;
15243
+ return [
15244
+ line(`**Locations:**`, (_b = (_a = event == null ? void 0 : event.properties) == null ? void 0 : _a.locations) == null ? void 0 : _b.slice(0, 100)),
15245
+ line(`**Issued:**`, `<t:${Math.floor(new Date(event.properties.issued).getTime() / 1e3)}:R>`, !isExpired),
15246
+ line(`**Expires:**`, `<t:${Math.floor(new Date(event.properties.expires).getTime() / 1e3)}:R>`, !isStatement),
15247
+ line(`**Damage Threat:**`, (_d = (_c = event == null ? void 0 : event.properties) == null ? void 0 : _c.parameters) == null ? void 0 : _d.damage_threat, !isExpired),
15248
+ line(`**Flood Threat:**`, (_f = (_e = event == null ? void 0 : event.properties) == null ? void 0 : _e.parameters) == null ? void 0 : _f.flood_threat, !isExpired),
15249
+ line(`**Tornado Threat:**`, (_h = (_g = event == null ? void 0 : event.properties) == null ? void 0 : _g.parameters) == null ? void 0 : _h.tornado_threat, !isExpired),
15250
+ line(`**Estimated Wind Gusts:**`, `${(_j = (_i = event == null ? void 0 : event.properties) == null ? void 0 : _i.parameters) == null ? void 0 : _j.estimated_wind_gusts} ${((_l = (_k = event == null ? void 0 : event.properties) == null ? void 0 : _k.parameters) == null ? void 0 : _l.wind_threat) ? ` (${(_n = (_m = event == null ? void 0 : event.properties) == null ? void 0 : _m.parameters) == null ? void 0 : _n.wind_threat})` : ""}`, !isExpired && ((_p = (_o = event == null ? void 0 : event.properties) == null ? void 0 : _o.parameters) == null ? void 0 : _p.estimated_wind_gusts) != null),
15251
+ line(`**Estimated Hail Size:**`, `${(_r = (_q = event == null ? void 0 : event.properties) == null ? void 0 : _q.parameters) == null ? void 0 : _r.estimated_hail_size} ${((_t = (_s = event == null ? void 0 : event.properties) == null ? void 0 : _s.parameters) == null ? void 0 : _t.hail_threat) ? ` (${(_v = (_u = event == null ? void 0 : event.properties) == null ? void 0 : _u.parameters) == null ? void 0 : _v.hail_threat})` : ""}`, !isExpired && ((_x = (_w = event == null ? void 0 : event.properties) == null ? void 0 : _w.parameters) == null ? void 0 : _x.estimated_hail_size) != null),
15252
+ line(`**Discussion:**`, (_z = (_y = event == null ? void 0 : event.properties) == null ? void 0 : _y.discussion_parameters) == null ? void 0 : _z.discussion_number, !isExpired),
15253
+ line(`**Concern:**`, (_B = (_A = event == null ? void 0 : event.properties) == null ? void 0 : _A.discussion_parameters) == null ? void 0 : _B.discussion_concerning, !isExpired),
15254
+ line(`**SPC Max Tornado Threat:**`, (_D = (_C = event == null ? void 0 : event.properties) == null ? void 0 : _C.discussion_parameters) == null ? void 0 : _D.discussion_max_tornado, !isExpired),
15255
+ line(`**SPC Max Hail Threat:**`, (_F = (_E = event == null ? void 0 : event.properties) == null ? void 0 : _E.discussion_parameters) == null ? void 0 : _F.discussion_max_hail, !isExpired),
15256
+ line(`**SPC Max Wind Threat:**`, (_H = (_G = event == null ? void 0 : event.properties) == null ? void 0 : _G.discussion_parameters) == null ? void 0 : _H.discussion_max_wind, !isExpired),
15257
+ line(`**SPC Watch Issuance Probability:**`, ((_J = (_I = event == null ? void 0 : event.properties) == null ? void 0 : _I.discussion_parameters) == null ? void 0 : _J.discussion_watch_issuance) ? `${(_L = (_K = event == null ? void 0 : event.properties) == null ? void 0 : _K.discussion_parameters) == null ? void 0 : _L.discussion_watch_issuance}%` : null, !isExpired),
15258
+ line(`**Watch Number:**`, (_N = (_M = event == null ? void 0 : event.properties) == null ? void 0 : _M.watch_parameters) == null ? void 0 : _N.watch_number, !isExpired),
15259
+ line(`**Strong Tornadoes Probability:**`, ((_P = (_O = event == null ? void 0 : event.properties) == null ? void 0 : _O.watch_parameters) == null ? void 0 : _P.strong_tornadoes_probability) ? `${(_R = (_Q = event == null ? void 0 : event.properties) == null ? void 0 : _Q.watch_parameters) == null ? void 0 : _R.strong_tornadoes_probability}%` : null, !isExpired),
15260
+ line(`**Additional Tornadoes Probability:**`, ((_T = (_S = event == null ? void 0 : event.properties) == null ? void 0 : _S.watch_parameters) == null ? void 0 : _T.additional_tornadoes_probability) ? `${(_V = (_U = event == null ? void 0 : event.properties) == null ? void 0 : _U.watch_parameters) == null ? void 0 : _V.additional_tornadoes_probability}%` : null, !isExpired),
15261
+ line(`**Combined Hail/Wind Probability:**`, ((_X = (_W = event == null ? void 0 : event.properties) == null ? void 0 : _W.watch_parameters) == null ? void 0 : _X.combined_hail_wind_probability) ? `${(_Z = (_Y = event == null ? void 0 : event.properties) == null ? void 0 : _Y.watch_parameters) == null ? void 0 : _Z.combined_hail_wind_probability}%` : null, !isExpired),
15262
+ line(`**Severe Hail Probability:**`, ((_$ = (__ = event == null ? void 0 : event.properties) == null ? void 0 : __.watch_parameters) == null ? void 0 : _$.severe_hail_probability) ? `${(_ba = (_aa = event == null ? void 0 : event.properties) == null ? void 0 : _aa.watch_parameters) == null ? void 0 : _ba.severe_hail_probability}%` : null, !isExpired),
15263
+ line(`**Hail >2in Probability:**`, ((_da = (_ca = event == null ? void 0 : event.properties) == null ? void 0 : _ca.watch_parameters) == null ? void 0 : _da.hail_2in_probability) ? `${(_fa = (_ea = event == null ? void 0 : event.properties) == null ? void 0 : _ea.watch_parameters) == null ? void 0 : _fa.hail_2in_probability}%` : null, !isExpired),
15264
+ line(`**Max Hail Inches:**`, (_ha = (_ga = event == null ? void 0 : event.properties) == null ? void 0 : _ga.watch_parameters) == null ? void 0 : _ha.max_hail_in, !isExpired),
15265
+ line(`**Severe Wind Probability:**`, ((_ja = (_ia = event == null ? void 0 : event.properties) == null ? void 0 : _ia.watch_parameters) == null ? void 0 : _ja.severe_wind_probability) ? `${(_la = (_ka = event == null ? void 0 : event.properties) == null ? void 0 : _ka.watch_parameters) == null ? void 0 : _la.severe_wind_probability}%` : null, !isExpired),
15266
+ line(`**Max Surface Wind:**`, (_na = (_ma = event == null ? void 0 : event.properties) == null ? void 0 : _ma.watch_parameters) == null ? void 0 : _na.max_wind_surface, !isExpired),
15267
+ line(`**Max Tops (x100 feet):**`, (_pa = (_oa = event == null ? void 0 : event.properties) == null ? void 0 : _oa.watch_parameters) == null ? void 0 : _pa.max_tops_x100feet, !isExpired),
15268
+ line(`**Tags:**`, ((_sa = (_ra = (_qa = event == null ? void 0 : event.properties) == null ? void 0 : _qa.parameters) == null ? void 0 : _ra.tags) == null ? void 0 : _sa.length) > 0 ? (_ua = (_ta = event == null ? void 0 : event.properties) == null ? void 0 : _ta.parameters) == null ? void 0 : _ua.tags.join(", ") : null, !isExpired),
15269
+ line(`**Sender:**`, ((_xa = (_wa = (_va = event == null ? void 0 : event.properties) == null ? void 0 : _va.geocode) == null ? void 0 : _wa.office) == null ? void 0 : _xa.name) ? `${(_Aa = (_za = (_ya = event == null ? void 0 : event.properties) == null ? void 0 : _ya.geocode) == null ? void 0 : _za.office) == null ? void 0 : _Aa.name} (${(_Da = (_Ca = (_Ba = event == null ? void 0 : event.properties) == null ? void 0 : _Ba.geocode) == null ? void 0 : _Ca.office) == null ? void 0 : _Da.office})` : (_Ga = (_Fa = (_Ea = event == null ? void 0 : event.properties) == null ? void 0 : _Ea.geocode) == null ? void 0 : _Fa.office) == null ? void 0 : _Ga.office),
15270
+ line(`**Tracking:**`, (_Ia = (_Ha = event == null ? void 0 : event.properties) == null ? void 0 : _Ha.metadata) == null ? void 0 : _Ia.tracking),
15271
+ line(`**Logs:**`, ((_La = (_Ka = (_Ja = event == null ? void 0 : event.properties) == null ? void 0 : _Ja.metadata) == null ? void 0 : _Ka.history) == null ? void 0 : _La.length) > 0 ? (_Na = (_Ma = event == null ? void 0 : event.properties) == null ? void 0 : _Ma.metadata) == null ? void 0 : _Na.history.length : null)
15272
+ ].filter(Boolean).join("\n");
15273
+ };
15333
15274
 
15334
- ${JSON.stringify(getCleanedEvent(event), null, 2)}`), { filename: `${event.event}_${event.status}_${event.metadata.tracking}.txt`, contentType: "application/text" });
15335
- }
15336
- if (settings.eas) {
15337
- const audio = yield setEasTone({
15338
- message: event.description,
15339
- header: event.metadata.header
15340
- });
15341
- const file = (0, import_fs2.readFileSync)(audio);
15342
- if (audio) {
15343
- form.append("fEas", Buffer.from(file), { filename: `${event.event}_${event.status}_${event.metadata.tracking}_eas.mp3`, contentType: "audio/mpeg" });
15275
+ // src/@modules/@utilities/utilities.createHttp.ts
15276
+ var import_request = __toESM(require("request"));
15277
+ var createHttp = (options) => __async(null, null, function* () {
15278
+ return new Promise((resolve6, reject) => {
15279
+ var _a, _b, _c, _d, _e, _f;
15280
+ try {
15281
+ const requestOptions = {
15282
+ url: (_a = options.url) != null ? _a : `https://api.weather.gov/alerts/active`,
15283
+ headers: (_b = options.headers) != null ? _b : {
15284
+ "User-Agent": "AtmosphericX",
15285
+ "Accept": "application/geo+json, text/plain, */*; q=0.9",
15286
+ "Accept-Language": "en-US,en;q=0.9"
15287
+ },
15288
+ method: (_c = options.method) != null ? _c : `GET`,
15289
+ timeout: (_d = options.timeout) != null ? _d : 1e4,
15290
+ proxy: (_e = options.proxy) != null ? _e : null,
15291
+ maxRedirects: 1
15292
+ };
15293
+ if (options.formData) {
15294
+ requestOptions["formData"] = options.formData;
15295
+ } else if (options.body) {
15296
+ requestOptions["body"] = options.body;
15344
15297
  }
15298
+ (0, import_request.default)(requestOptions, (error, response2, body) => {
15299
+ var _a2, _b2, _c2, _d2, _e2;
15300
+ if (error) {
15301
+ return resolve6({
15302
+ error: true,
15303
+ options: requestOptions,
15304
+ status: -1,
15305
+ message: (_a2 = error.message) != null ? _a2 : `Unknown Error`
15306
+ });
15307
+ }
15308
+ if (response2.statusCode < 200 || response2.statusCode >= 300) {
15309
+ return resolve6({
15310
+ error: true,
15311
+ options: requestOptions,
15312
+ status: (_b2 = response2.statusCode) != null ? _b2 : -1,
15313
+ message: `HTTP Status Code ${(_c2 = response2.statusCode) != null ? _c2 : `Unknown Status Code`} (${body})`
15314
+ });
15315
+ }
15316
+ if (body == void 0 || body == null) {
15317
+ return resolve6({
15318
+ error: true,
15319
+ options: requestOptions,
15320
+ status: (_d2 = response2.statusCode) != null ? _d2 : -1,
15321
+ message: `Empty Response Body`
15322
+ });
15323
+ }
15324
+ resolve6({
15325
+ error: false,
15326
+ options: requestOptions,
15327
+ status: (_e2 = response2.statusCode) != null ? _e2 : -1,
15328
+ message: body
15329
+ });
15330
+ });
15331
+ } catch (error) {
15332
+ return resolve6({
15333
+ error: true,
15334
+ options: {},
15335
+ status: -1,
15336
+ message: (_f = error.message) != null ? _f : `Unknown Error`
15337
+ });
15345
15338
  }
15346
- yield createHttp({
15347
- url: settings.webhook,
15348
- timeout: 2e3,
15349
- method: `POST`,
15350
- headers: form.getHeaders(),
15351
- body: form
15352
- });
15353
- }
15339
+ });
15354
15340
  });
15355
15341
 
15356
- // src/@manager/manager.updateWebhooks.ts
15357
- var updateWebhooks = (event) => __async(null, null, function* () {
15342
+ // src/@manager/manager.updateListener.ts
15343
+ var import_fs3 = require("fs");
15344
+ var import_form_data = __toESM(require_form_data());
15345
+ var updateListener = (event) => __async(null, null, function* () {
15346
+ var _a, _b, _c, _d;
15358
15347
  const settings = bootstrap.settings;
15359
- const webhooks = settings.WebhookSettings;
15360
- const eventName = event.properties.event;
15361
- for (const socket of webhooks) {
15362
- const events = socket.events;
15363
- if (!events || events.length === 0) {
15364
- yield createWebhook({ webhook: socket, event });
15365
- continue;
15366
- }
15367
- const matched = events.some((pattern) => {
15348
+ const listeners2 = settings.ListenerSettings;
15349
+ const properties2 = event.properties;
15350
+ const metadata = {
15351
+ file: null,
15352
+ eas: null,
15353
+ name: properties2.event,
15354
+ status: properties2.status,
15355
+ description: properties2.description,
15356
+ tracking: properties2.metadata.tracking,
15357
+ header: properties2.metadata.header,
15358
+ raw: properties2.metadata.raw,
15359
+ expired: properties2.status_metadata.is_expired,
15360
+ attachments: properties2.metadata.attachments
15361
+ };
15362
+ for (const listener2 of listeners2) {
15363
+ const events = listener2 == null ? void 0 : listener2.events;
15364
+ const webhook = listener2 == null ? void 0 : listener2.webhook;
15365
+ const uploads = listener2 == null ? void 0 : listener2.uploads;
15366
+ const isMatched = events.some((pattern) => {
15368
15367
  if (!pattern) return false;
15369
- if (pattern === "*" || pattern === eventName) return true;
15368
+ if (pattern === "*" || pattern === metadata.name) return true;
15370
15369
  if (pattern.includes("*")) {
15371
15370
  const regex = "^" + pattern.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*/g, ".*") + "$";
15372
- return new RegExp(regex).test(eventName);
15371
+ return new RegExp(regex).test(metadata.name);
15373
15372
  }
15374
15373
  return false;
15375
15374
  });
15376
- if (matched) {
15377
- yield createWebhook({ webhook: socket, event });
15375
+ if ((events == null ? void 0 : events.length) == 0 || isMatched) {
15376
+ if (uploads == null ? void 0 : uploads.eas) {
15377
+ metadata.eas = yield setEasTone({
15378
+ title: `${metadata.name}_${metadata.status}_${metadata.tracking}`,
15379
+ message: metadata.description,
15380
+ header: metadata.header
15381
+ });
15382
+ }
15383
+ if (uploads == null ? void 0 : uploads.file) {
15384
+ const fDestination = settings.GlobalSettings.ArchiveSettings.TextDirectory;
15385
+ if (fDestination) {
15386
+ if (!(0, import_fs3.existsSync)(fDestination)) {
15387
+ (0, import_fs3.mkdirSync)(fDestination, { recursive: true });
15388
+ }
15389
+ if ((0, import_fs3.existsSync)(`${fDestination}/${metadata.name}_${metadata.status}_${metadata.tracking}.txt`)) {
15390
+ (0, import_fs3.appendFileSync)(`${fDestination}/${metadata.name}_${metadata.status}_${metadata.tracking}.txt`, metadata.raw);
15391
+ } else {
15392
+ (0, import_fs3.writeFileSync)(`${fDestination}/${metadata.name}_${metadata.status}_${metadata.tracking}.txt`, metadata.raw);
15393
+ }
15394
+ }
15395
+ metadata.file = metadata.raw;
15396
+ }
15397
+ if (uploads == null ? void 0 : uploads.event) {
15398
+ const eDestination = settings.GlobalSettings.ArchiveSettings.EventDirectory;
15399
+ if (eDestination) {
15400
+ if (!(0, import_fs3.existsSync)(eDestination)) {
15401
+ (0, import_fs3.mkdirSync)(eDestination, { recursive: true });
15402
+ }
15403
+ (0, import_fs3.writeFileSync)(`${eDestination}/${metadata.name}_${metadata.status}_${metadata.tracking}.json`, JSON.stringify(getCleanedEvent(event), null, 2));
15404
+ }
15405
+ }
15406
+ if (webhook.enabled && webhook.destination) {
15407
+ const ratelimit = setTimeoutAction({ identifier: webhook.destination, interval: webhook.ratelimit, max: webhook.ratelimit, addTime: true });
15408
+ const form = new import_form_data.default();
15409
+ const embed = {
15410
+ title: `${metadata.name} (${metadata.status})`,
15411
+ description: getEmebed(event),
15412
+ fields: [],
15413
+ color: 16711680,
15414
+ timestamp: (/* @__PURE__ */ new Date()).toISOString(),
15415
+ footer: { text: (_a = webhook.title) != null ? _a : `AtmosphericX` }
15416
+ };
15417
+ if (ratelimit.limited) {
15418
+ return;
15419
+ }
15420
+ if (metadata.description && !metadata.expired) {
15421
+ if (metadata.description.length > 900) {
15422
+ metadata.description = metadata.description.substring(0, 900) + "\n\n[Message truncated due to length]";
15423
+ }
15424
+ embed.fields.push({
15425
+ name: "Description",
15426
+ value: metadata.description ? "```\n" + metadata.description.split("\n").map((l) => l.trim()).filter(Boolean).join("\n") + "\n```" : ""
15427
+ });
15428
+ }
15429
+ if (((_b = metadata.attachments) == null ? void 0 : _b.length) > 0) {
15430
+ metadata.attachments = metadata.attachments.slice(0, 5);
15431
+ embed.fields.push({
15432
+ name: "Attachments",
15433
+ value: metadata.attachments.map((attachment) => `- [${attachment.name.length > 45 ? attachment.name.substring(0, 45) + "..." : attachment.name}](${attachment.link})`).join("\n")
15434
+ });
15435
+ }
15436
+ if (uploads == null ? void 0 : uploads.file) {
15437
+ form.append("fUpload", Buffer.from(metadata.file), {
15438
+ filename: `${properties2.event}_${properties2.status}_${properties2.metadata.tracking}.txt`,
15439
+ contentType: "application/text"
15440
+ });
15441
+ }
15442
+ if (uploads == null ? void 0 : uploads.eas) {
15443
+ if (metadata.eas) {
15444
+ const file = (0, import_fs3.readFileSync)(metadata.eas);
15445
+ form.append("fEas", Buffer.from(file), {
15446
+ filename: `${properties2.event}_${properties2.status}_${properties2.metadata.tracking}_eas.mp3`,
15447
+ contentType: "audio/mpeg"
15448
+ });
15449
+ }
15450
+ }
15451
+ form.append("payload_json", JSON.stringify({
15452
+ username: (_c = webhook.title) != null ? _c : "AtmosphericX",
15453
+ content: (_d = webhook.message) != null ? _d : "",
15454
+ embeds: [embed]
15455
+ }));
15456
+ yield createHttp({
15457
+ url: webhook.destination,
15458
+ timeout: 5e3,
15459
+ method: `POST`,
15460
+ headers: form.getHeaders(),
15461
+ body: form
15462
+ });
15463
+ }
15378
15464
  }
15379
15465
  }
15380
15466
  });
@@ -15593,10 +15679,10 @@ var mkEvent = (event) => __async(null, null, function* () {
15593
15679
  })
15594
15680
  })
15595
15681
  });
15596
- updateWebhooks(bootstrap.cache.events.features[getIndex]);
15682
+ updateListener(bootstrap.cache.events.features[getIndex]);
15597
15683
  } else {
15598
15684
  features.push(event);
15599
- updateWebhooks(event);
15685
+ updateListener(event);
15600
15686
  }
15601
15687
  }
15602
15688
  }
@@ -15611,6 +15697,7 @@ var rmEvent = (event) => {
15611
15697
  const cachedStatus = event.properties.status;
15612
15698
  event.properties.expires = (/* @__PURE__ */ new Date()).toISOString();
15613
15699
  event.properties.status = `Expired`;
15700
+ event.properties.status_metadata.is_expired = true;
15614
15701
  if (getEvent) {
15615
15702
  setEventEmit({
15616
15703
  event: `onEventStatus`,
@@ -15621,7 +15708,7 @@ var rmEvent = (event) => {
15621
15708
  message: `[Removed] ${event.properties.event} (${event.properties.status}) (${event.properties.metadata.tracking})`
15622
15709
  });
15623
15710
  setEventEmit({ event: `onExpiredProduct`, metadata: event });
15624
- if (cachedStatus != `Statement`) updateWebhooks(event);
15711
+ if (cachedStatus != `Statement`) updateListener(event);
15625
15712
  bootstrap.cache.events.features.splice(bootstrap.cache.events.features.indexOf(getEvent), 1);
15626
15713
  bootstrap.cache.hashes = bootstrap.cache.hashes.filter((hash) => hash.tracking !== event.properties.metadata.tracking);
15627
15714
  }
@@ -15646,21 +15733,105 @@ var getLatestIssuance = () => {
15646
15733
  return latest.toString().padStart(4, "0");
15647
15734
  };
15648
15735
 
15649
- // src/@building/building.outlooks.ts
15736
+ // src/@dictionaries/dictionaries.states.ts
15737
+ var dict_states = {
15738
+ "AL": "Alabama",
15739
+ "AK": "Alaska",
15740
+ "AZ": "Arizona",
15741
+ "AR": "Arkansas",
15742
+ "CA": "California",
15743
+ "CO": "Colorado",
15744
+ "CT": "Connecticut",
15745
+ "DE": "Delaware",
15746
+ "FL": "Florida",
15747
+ "GA": "Georgia",
15748
+ "HI": "Hawaii",
15749
+ "ID": "Idaho",
15750
+ "IL": "Illinois",
15751
+ "IN": "Indiana",
15752
+ "IA": "Iowa",
15753
+ "KS": "Kansas",
15754
+ "KY": "Kentucky",
15755
+ "LA": "Louisiana",
15756
+ "ME": "Maine",
15757
+ "MD": "Maryland",
15758
+ "MA": "Massachusetts",
15759
+ "MI": "Michigan",
15760
+ "MN": "Minnesota",
15761
+ "MS": "Mississippi",
15762
+ "MO": "Missouri",
15763
+ "MT": "Montana",
15764
+ "NE": "Nebraska",
15765
+ "NV": "Nevada",
15766
+ "NH": "New Hampshire",
15767
+ "NJ": "New Jersey",
15768
+ "NM": "New Mexico",
15769
+ "NY": "New York",
15770
+ "NC": "North Carolina",
15771
+ "ND": "North Dakota",
15772
+ "OH": "Ohio",
15773
+ "OK": "Oklahoma",
15774
+ "OR": "Oregon",
15775
+ "PA": "Pennsylvania",
15776
+ "RI": "Rhode Island",
15777
+ "SC": "South Carolina",
15778
+ "SD": "South Dakota",
15779
+ "TN": "Tennessee",
15780
+ "TX": "Texas",
15781
+ "UT": "Utah",
15782
+ "VT": "Vermont",
15783
+ "VA": "Virginia",
15784
+ "WA": "Washington",
15785
+ "WV": "West Virginia",
15786
+ "WI": "Wisconsin",
15787
+ "WY": "Wyoming",
15788
+ "DC": "District of Columbia"
15789
+ };
15790
+
15791
+ // src/@building/building.attachments.ts
15650
15792
  var getEventAttachments = (event) => {
15651
- var _a, _b;
15793
+ var _a, _b, _c, _d, _e, _f, _g;
15794
+ let attachments = [];
15652
15795
  const latestTime = getLatestIssuance();
15653
- const validEvents = [
15796
+ const spcNumber = (_b = (_a = event == null ? void 0 : event.properties) == null ? void 0 : _a.discussion_parameters) == null ? void 0 : _b.discussion_number;
15797
+ const watchNumber = (_d = (_c = event == null ? void 0 : event.properties) == null ? void 0 : _c.watch_parameters) == null ? void 0 : _d.watch_number;
15798
+ const locations = (_e = event == null ? void 0 : event.properties) == null ? void 0 : _e.locations_array;
15799
+ const events = [
15654
15800
  { target: "Day 1", attachment: `https://www.spc.noaa.gov/products/outlook/day1otlk_${latestTime}.png` },
15655
15801
  { target: "Day 2", attachment: `https://www.spc.noaa.gov/products/outlook/day2otlk.png` },
15656
15802
  { target: "Day 3", attachment: `https://www.spc.noaa.gov/products/outlook/day3otlk.png` },
15657
- { target: "Mesoscale Discussion", attachment: `https://www.spc.noaa.gov/products/md/mcd${(_b = (_a = event == null ? void 0 : event.properties) == null ? void 0 : _a.spc_parameters) == null ? void 0 : _b.spc_number}.png` }
15803
+ { target: "Mesoscale Discussion", attachment: `https://www.spc.noaa.gov/products/md/mcd${spcNumber}.png` },
15804
+ { target: "Tornado Watch", attachment: `https://www.spc.noaa.gov/products/watch/ww${watchNumber}_radar_big.gif` },
15805
+ { target: "PDS Tornado Watch", attachment: `https://www.spc.noaa.gov/products/watch/ww${watchNumber}_radar_big.gif` },
15806
+ { target: "Severe Thunderstorm Watch", attachment: `https://www.spc.noaa.gov/products/watch/ww${watchNumber}_radar_big.gif` },
15807
+ { target: "PDS Severe Thunderstorm Watch", attachment: `https://www.spc.noaa.gov/products/watch/ww${watchNumber}_radar_big.gif` }
15658
15808
  ];
15659
- const isValid = validEvents.find((outlook) => outlook.target == event.properties.event);
15660
- if (isValid) {
15661
- return (isValid == null ? void 0 : isValid.attachment) ? [isValid.attachment] : [];
15809
+ if (events.find((e) => e.target === event.properties.event)) {
15810
+ attachments.push({ name: `Image: Graphic`, link: events.find((e) => e.target === event.properties.event).attachment });
15811
+ }
15812
+ for (const location of locations) {
15813
+ if (dict_expressions.location.test(location)) {
15814
+ const lines = [`Northern`, `Southern`, `Eastern`, `Western`, `Inland`, `Costal`, `County`];
15815
+ const county = (_f = location == null ? void 0 : location.split(",")[0]) == null ? void 0 : _f.trim().replace(new RegExp(`^(${lines.join("|")}) `), "");
15816
+ const state = dict_states[(_g = location == null ? void 0 : location.split(",")[1]) == null ? void 0 : _g.trim()];
15817
+ const feeds = bootstrap.database.prepare(`SELECT * FROM broadcastify WHERE state = ? AND county = ?`).all(state, county).sort((a, b) => {
15818
+ const typeOrder = ["Other", "Public Safety"];
15819
+ const indexA = typeOrder.indexOf(a.type);
15820
+ const indexB = typeOrder.indexOf(b.type);
15821
+ return indexA - indexB;
15822
+ });
15823
+ const tags = bootstrap.settings.BroadcastifySettings.BroadcastifyTags;
15824
+ const filtered = feeds.filter((feed) => tags.includes(feed.type));
15825
+ if (filtered.length > 0) {
15826
+ filtered.map((filtered2) => {
15827
+ if (!attachments.some((a) => a.link === filtered2.link)) {
15828
+ attachments.push({ name: `${filtered2.type}: ${filtered2.feed}`, link: filtered2.link });
15829
+ }
15830
+ });
15831
+ }
15832
+ }
15662
15833
  }
15663
- return null;
15834
+ return attachments;
15664
15835
  };
15665
15836
 
15666
15837
  // src/@building/building.validate.ts
@@ -15704,7 +15875,7 @@ var validateEvents = (events) => __async(null, null, function* () {
15704
15875
  rmEvent(define2);
15705
15876
  return false;
15706
15877
  }
15707
- if ((_c = (_b = properties2.metadata) == null ? void 0 : _b.vtec) == null ? void 0 : _c.is_watch) {
15878
+ if (((_c = (_b = properties2.metadata) == null ? void 0 : _b.vtec) == null ? void 0 : _c.is_watch) && properties2.metadata.source != `events.api`) {
15708
15879
  const isSPC = (_e = (_d = properties2.metadata) == null ? void 0 : _d.vtec) == null ? void 0 : _e.prediction_center;
15709
15880
  setEventEmit({ event: isSPC ? `onStormPredictionWatch` : `onNonStormPredictionWatch`, metadata: define2 });
15710
15881
  if ((bools == null ? void 0 : bools.SPCWatchesOnly) && !isSPC) {
@@ -15792,7 +15963,7 @@ var text = (stanza) => __async(null, null, function* () {
15792
15963
  const header = getEventHeader({ properties: props, getType: stanza.getType });
15793
15964
  const issued = new Date(attributes.issue);
15794
15965
  const expires = new Date(issued.getTime() + 12 * 60 * 60 * 1e3);
15795
- let event = Object.keys(eventsMatchText).find((event2) => message.toLowerCase().includes(event2.toLowerCase()));
15966
+ let event = Object.keys(dict_matches).find((event2) => message.toLowerCase().includes(event2.toLowerCase()));
15796
15967
  let isStatement = false;
15797
15968
  if (!event) {
15798
15969
  event = stanza.getType.type.split(`-`).map((word) => word.charAt(0).toUpperCase() + word.slice(1).toLowerCase()).join(` `);
@@ -15835,9 +16006,9 @@ var text = (stanza) => __async(null, null, function* () {
15835
16006
 
15836
16007
  // src/@parsers/@ugc/ugc.header.ts
15837
16008
  var getUGCHeader = (message) => {
15838
- const start = message.search(regExp.ugc1);
16009
+ const start = message.search(dict_expressions.ugc1);
15839
16010
  const sub = message.substring(start);
15840
- const end = sub.search(regExp.ugc2);
16011
+ const end = sub.search(dict_expressions.ugc2);
15841
16012
  const fin = sub.substring(0, end).replace(/\s+/g, "").slice(0, -1);
15842
16013
  return fin != null ? fin : null;
15843
16014
  };
@@ -15929,7 +16100,7 @@ var ugc = (stanza) => __async(null, null, function* () {
15929
16100
  const issued = new Date(attributes.issue);
15930
16101
  const expires = new Date(ugc2.expires);
15931
16102
  const header = getEventHeader({ properties: props, getType: stanza.getType });
15932
- let event = Object.keys(eventsMatchText).find((event2) => message.toLowerCase().includes(event2.toLowerCase()));
16103
+ let event = Object.keys(dict_matches).find((event2) => message.toLowerCase().includes(event2.toLowerCase()));
15933
16104
  let isStatement = false;
15934
16105
  if (!event) {
15935
16106
  event = stanza.getType.type.split(`-`).map((word) => word.charAt(0).toUpperCase() + word.slice(1).toLowerCase()).join(` `);
@@ -15971,8 +16142,8 @@ var ugc = (stanza) => __async(null, null, function* () {
15971
16142
  validateEvents(processed);
15972
16143
  });
15973
16144
 
15974
- // src/@dictionaries/dictionaries.eventTypes.ts
15975
- var eventTypes = {
16145
+ // src/@dictionaries/dictionaries.events.ts
16146
+ var dict_events = {
15976
16147
  "AF": "Ashfall",
15977
16148
  "AS": "Air Stagnation",
15978
16149
  "BH": "Beach Hazard",
@@ -16036,8 +16207,8 @@ var eventTypes = {
16036
16207
  "ZY": "Freezing Spray"
16037
16208
  };
16038
16209
 
16039
- // src/@dictionaries/dictionaries.eventActions.ts
16040
- var eventActions = {
16210
+ // src/@dictionaries/dictionaries.actions.ts
16211
+ var dict_actions = {
16041
16212
  "W": "Warning",
16042
16213
  "F": "Forecast",
16043
16214
  "A": "Watch",
@@ -16047,8 +16218,8 @@ var eventActions = {
16047
16218
  "S": "Statement"
16048
16219
  };
16049
16220
 
16050
- // src/@dictionaries/dictionaries.eventStatus.ts
16051
- var eventStatus = {
16221
+ // src/@dictionaries/dictionaries.status.ts
16222
+ var dict_status = {
16052
16223
  "NEW": "Issued",
16053
16224
  "CON": "Updated",
16054
16225
  "EXT": "Extended",
@@ -16073,7 +16244,8 @@ var getExpiry2 = (dates) => {
16073
16244
  // src/@parsers/@pvtec/pvtec.extract.ts
16074
16245
  var pvExtract = (message) => {
16075
16246
  var _a, _b, _c, _d;
16076
- const getVTECs = (_a = message.match(regExp.pvtec)) != null ? _a : [];
16247
+ if (!message) return null;
16248
+ const getVTECs = (_a = message.match(dict_expressions.pvtec)) != null ? _a : [];
16077
16249
  const vtecs = [];
16078
16250
  for (const vtec2 of getVTECs) {
16079
16251
  const sub = vtec2.split(`.`);
@@ -16081,11 +16253,11 @@ var pvExtract = (message) => {
16081
16253
  const dates = (_b = sub[6]) == null ? void 0 : _b.split(`-`);
16082
16254
  vtecs.push({
16083
16255
  vtec: vtec2,
16084
- product: eventProducts[sub[0]],
16256
+ product: dict_products[sub[0]],
16085
16257
  tracking: `${sub[2]}.${sub[3]}.${sub[4]}.${sub[5]}`,
16086
- event: `${eventTypes[sub[3]]} ${eventActions[sub[4]]}`,
16087
- status: eventStatus[sub[1]],
16088
- organization: (_d = (_c = message.match(regExp.wmo)) == null ? void 0 : _c[0]) != null ? _d : null,
16258
+ event: `${dict_events[sub[3]]} ${dict_actions[sub[4]]}`,
16259
+ status: dict_status[sub[1]],
16260
+ organization: (_d = (_c = message.match(dict_expressions.wmo)) == null ? void 0 : _c[0]) != null ? _d : null,
16089
16261
  expires: getExpiry2(dates),
16090
16262
  is_watch: (sub[4] == `A` || sub[4] == `Y`) && (sub[3] == `TO` || sub[3] == `SV`),
16091
16263
  prediction_center: sub[2] == `KWNS` ? true : false
@@ -16094,8 +16266,8 @@ var pvExtract = (message) => {
16094
16266
  return vtecs.length > 0 ? vtecs : null;
16095
16267
  };
16096
16268
 
16097
- // src/@dictionaries/dictionaries.eventCauses.ts
16098
- var eventCauses = {
16269
+ // src/@dictionaries/dictionaries.causes.ts
16270
+ var dict_causes = {
16099
16271
  "SM": "Snow Melt",
16100
16272
  "RS": "Rain/Snow Melt",
16101
16273
  "ER": "Excessive Rain",
@@ -16113,16 +16285,16 @@ var eventCauses = {
16113
16285
  "OT": "Other Effects"
16114
16286
  };
16115
16287
 
16116
- // src/@dictionaries/dictionaries.eventRecords.ts
16117
- var eventRecords = {
16288
+ // src/@dictionaries/dictionaries.records.ts
16289
+ var dict_records = {
16118
16290
  "NO": "No Record Expected",
16119
16291
  "NR": "Near Record or possible record",
16120
16292
  "UU": "Unknown history of records",
16121
16293
  "OO": "Other"
16122
16294
  };
16123
16295
 
16124
- // src/@dictionaries/dictionaries.eventSeverity.ts
16125
- var eventSeverity = {
16296
+ // src/@dictionaries/dictionaries.severity.ts
16297
+ var dict_severity = {
16126
16298
  N: "Not Expected",
16127
16299
  0: "Areal Flood or FF Product",
16128
16300
  1: "Minor",
@@ -16134,16 +16306,16 @@ var eventSeverity = {
16134
16306
  // src/@parsers/@hvtec/hvtec.extract.ts
16135
16307
  var hvExtract = (message) => {
16136
16308
  var _a;
16137
- const getHVTECs = (_a = message.match(regExp.hvtec)) != null ? _a : [];
16309
+ const getHVTECs = (_a = message.match(dict_expressions.hvtec)) != null ? _a : [];
16138
16310
  const vtecs = [];
16139
16311
  for (const vtec2 of getHVTECs) {
16140
16312
  const sub = vtec2.split(`.`);
16141
16313
  if (sub.length < 7) continue;
16142
16314
  vtecs.push({
16143
16315
  hvtec: vtec2,
16144
- severity: eventSeverity[sub[1]],
16145
- cause: eventCauses[sub[2]],
16146
- record: eventRecords[sub[6]]
16316
+ severity: dict_severity[sub[1]],
16317
+ cause: dict_causes[sub[2]],
16318
+ record: dict_records[sub[6]]
16147
16319
  });
16148
16320
  }
16149
16321
  return vtecs.length > 0 ? vtecs : null;
@@ -16207,12 +16379,12 @@ var vtec = (stanza) => __async(null, null, function* () {
16207
16379
 
16208
16380
  // src/@events/events.api.ts
16209
16381
  var api = (stanza) => __async(null, null, function* () {
16210
- var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _A, _B, _C, _D, _E, _F, _G, _H, _I, _J, _K, _L, _M, _N, _O, _P, _Q, _R, _S, _T, _U, _V, _W, _X, _Y, _Z, __, _$, _aa, _ba, _ca, _da, _ea, _fa, _ga, _ha, _ia, _ja, _ka, _la, _ma, _na, _oa, _pa, _qa, _ra, _sa, _ta, _ua, _va, _wa, _xa, _ya, _za, _Aa, _Ba, _Ca, _Da, _Ea, _Fa, _Ga, _Ha, _Ia, _Ja, _Ka, _La, _Ma, _Na, _Oa, _Pa, _Qa, _Ra, _Sa, _Ta, _Ua, _Va, _Wa, _Xa, _Ya, _Za, __a, _$a, _ab, _bb, _cb, _db, _eb, _fb, _gb;
16382
+ var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _A, _B, _C, _D, _E, _F, _G, _H, _I, _J, _K, _L, _M, _N, _O, _P, _Q, _R, _S, _T, _U, _V, _W, _X, _Y, _Z, __, _$, _aa, _ba, _ca, _da, _ea, _fa, _ga, _ha, _ia, _ja, _ka, _la, _ma, _na, _oa, _pa, _qa, _ra, _sa, _ta, _ua, _va, _wa, _xa, _ya, _za, _Aa, _Ba, _Ca, _Da, _Ea, _Fa, _Ga, _Ha, _Ia, _Ja, _Ka, _La, _Ma, _Na, _Oa, _Pa, _Qa, _Ra, _Sa, _Ta, _Ua, _Va, _Wa, _Xa, _Ya, _Za, __a, _$a, _ab, _bb, _cb, _db, _eb, _fb, _gb, _hb, _ib, _jb, _kb, _lb, _mb, _nb, _ob, _pb, _qb, _rb, _sb, _tb, _ub;
16211
16383
  let processed = [];
16212
16384
  const messages = Object.values(JSON.parse(stanza.message).features);
16213
16385
  for (const feature of messages) {
16214
16386
  const tick = performance.now();
16215
- const pVtec = (_d = (_c = (_b = (_a = feature == null ? void 0 : feature.properties) == null ? void 0 : _a.parameters) == null ? void 0 : _b.VTEC) == null ? void 0 : _c[0]) != null ? _d : null;
16387
+ const pVtec = (_d = pvExtract((_c = (_b = (_a = feature == null ? void 0 : feature.properties) == null ? void 0 : _a.parameters) == null ? void 0 : _b.VTEC) == null ? void 0 : _c[0])) != null ? _d : null;
16216
16388
  processed.push({
16217
16389
  type: `Feature`,
16218
16390
  geometry: {
@@ -16226,67 +16398,68 @@ var api = (stanza) => __async(null, null, function* () {
16226
16398
  issued: ((_k = feature == null ? void 0 : feature.properties) == null ? void 0 : _k.sent) ? new Date((_l = feature == null ? void 0 : feature.properties) == null ? void 0 : _l.sent).toISOString() : null,
16227
16399
  expires: ((_m = feature == null ? void 0 : feature.properties) == null ? void 0 : _m.expires) ? new Date((_n = feature == null ? void 0 : feature.properties) == null ? void 0 : _n.expires).toISOString() : null,
16228
16400
  locations: (_p = (_o = feature == null ? void 0 : feature.properties) == null ? void 0 : _o.areaDesc) != null ? _p : null,
16229
- description: (_r = (_q = feature == null ? void 0 : feature.properties) == null ? void 0 : _q.description) != null ? _r : null,
16230
- attributes: (_t = (_s = feature == null ? void 0 : feature.properties) == null ? void 0 : _s.attributes) != null ? _t : {},
16401
+ locations_array: ((_q = feature == null ? void 0 : feature.properties) == null ? void 0 : _q.areaDesc) ? (_r = feature == null ? void 0 : feature.properties) == null ? void 0 : _r.areaDesc.split(";") : [],
16402
+ description: (_t = (_s = feature == null ? void 0 : feature.properties) == null ? void 0 : _s.description) != null ? _t : null,
16403
+ attributes: (_v = (_u = feature == null ? void 0 : feature.properties) == null ? void 0 : _u.attributes) != null ? _v : {},
16231
16404
  geocode: {
16232
16405
  office: {
16233
- office: pVtec ? pVtec.split(`.`)[2] : null,
16234
- name: (_u = officeICAOs[pVtec ? pVtec.split(`.`)[2] : null]) != null ? _u : null
16406
+ office: pVtec ? (_w = pVtec == null ? void 0 : pVtec[0]) == null ? void 0 : _w.tracking.split(`.`)[0] : null,
16407
+ name: (_y = dict_icao[pVtec ? (_x = pVtec == null ? void 0 : pVtec[0]) == null ? void 0 : _x.tracking.split(`.`)[0] : null]) != null ? _y : null
16235
16408
  },
16236
- organization: (_x = (_w = (_v = feature == null ? void 0 : feature.properties) == null ? void 0 : _v.parameters) == null ? void 0 : _w.WMOidentifier) == null ? void 0 : _x[0],
16237
- ugc: (_A = (_z = (_y = feature == null ? void 0 : feature.properties) == null ? void 0 : _y.geocode) == null ? void 0 : _z.UGC) != null ? _A : [],
16238
- polygon: ((_B = feature == null ? void 0 : feature.geometry) == null ? void 0 : _B.coordinates.length) > 0 ? Buffer.from(JSON.stringify([(_C = feature == null ? void 0 : feature.geometry) == null ? void 0 : _C.coordinates[0]])).toString("base64") : null,
16239
- polygon_generated: ((_D = feature == null ? void 0 : feature.geometry) == null ? void 0 : _D.coordinates.length) > 0 ? true : false
16409
+ organization: (_B = (_A = (_z = feature == null ? void 0 : feature.properties) == null ? void 0 : _z.parameters) == null ? void 0 : _A.WMOidentifier) == null ? void 0 : _B[0],
16410
+ ugc: (_E = (_D = (_C = feature == null ? void 0 : feature.properties) == null ? void 0 : _C.geocode) == null ? void 0 : _D.UGC) != null ? _E : [],
16411
+ polygon: ((_F = feature == null ? void 0 : feature.geometry) == null ? void 0 : _F.coordinates.length) > 0 ? Buffer.from(JSON.stringify([(_G = feature == null ? void 0 : feature.geometry) == null ? void 0 : _G.coordinates[0]])).toString("base64") : null,
16412
+ polygon_generated: ((_H = feature == null ? void 0 : feature.geometry) == null ? void 0 : _H.coordinates.length) > 0 ? true : false
16240
16413
  },
16241
16414
  parameters: {
16242
- tags: getEventTags((_E = feature == null ? void 0 : feature.properties) == null ? void 0 : _E.description),
16243
- instructions: (_G = (_F = feature == null ? void 0 : feature.properties) == null ? void 0 : _F.instruction) != null ? _G : null,
16244
- source: (_I = getTextFromProduct({ message: (_H = feature == null ? void 0 : feature.properties) == null ? void 0 : _H.description, find: [`SOURCE...`], removal: [`.`] })) != null ? _I : null,
16245
- hazards: (_K = getTextFromProduct({ message: (_J = feature == null ? void 0 : feature.properties) == null ? void 0 : _J.description, find: [`HAZARD...`], removal: [`.`] })) != null ? _K : null,
16246
- impacts: (_M = getTextFromProduct({ message: (_L = feature == null ? void 0 : feature.properties) == null ? void 0 : _L.description, find: [`IMPACT...`], removal: [`.`] })) != null ? _M : null,
16247
- estimated_hail_size: (_Q = (_P = (_O = (_N = feature == null ? void 0 : feature.properties) == null ? void 0 : _N.parameters) == null ? void 0 : _O.maxHailSize) == null ? void 0 : _P[0]) != null ? _Q : null,
16248
- estimated_wind_gusts: (_U = (_T = (_S = (_R = feature == null ? void 0 : feature.properties) == null ? void 0 : _R.parameters) == null ? void 0 : _S.maxWindGust) == null ? void 0 : _T[0]) != null ? _U : null,
16249
- damage_threat: (_Y = (_X = (_W = (_V = feature == null ? void 0 : feature.properties) == null ? void 0 : _V.parameters) == null ? void 0 : _W.thunderstormDamageThreat) == null ? void 0 : _X[0]) != null ? _Y : null,
16250
- tornado_threat: (_aa = (_$ = (__ = (_Z = feature == null ? void 0 : feature.properties) == null ? void 0 : _Z.parameters) == null ? void 0 : __.tornadoDetection) == null ? void 0 : _$[0]) != null ? _aa : null,
16251
- flood_threat: (_ea = (_da = (_ca = (_ba = feature == null ? void 0 : feature.properties) == null ? void 0 : _ba.parameters) == null ? void 0 : _ca.floodDetection) == null ? void 0 : _da[0]) != null ? _ea : null,
16252
- wind_threat: (_ia = (_ha = (_ga = (_fa = feature == null ? void 0 : feature.properties) == null ? void 0 : _fa.parameters) == null ? void 0 : _ga.windThreat) == null ? void 0 : _ha[0]) != null ? _ia : null,
16253
- hail_threat: (_ma = (_la = (_ka = (_ja = feature == null ? void 0 : feature.properties) == null ? void 0 : _ja.parameters) == null ? void 0 : _ka.hailThreat) == null ? void 0 : _la[0]) != null ? _ma : null
16415
+ tags: getEventTags((_I = feature == null ? void 0 : feature.properties) == null ? void 0 : _I.description),
16416
+ instructions: (_K = (_J = feature == null ? void 0 : feature.properties) == null ? void 0 : _J.instruction) != null ? _K : null,
16417
+ source: (_M = getTextFromProduct({ message: (_L = feature == null ? void 0 : feature.properties) == null ? void 0 : _L.description, find: [`SOURCE...`], removal: [`.`] })) != null ? _M : null,
16418
+ hazards: (_O = getTextFromProduct({ message: (_N = feature == null ? void 0 : feature.properties) == null ? void 0 : _N.description, find: [`HAZARD...`], removal: [`.`] })) != null ? _O : null,
16419
+ impacts: (_Q = getTextFromProduct({ message: (_P = feature == null ? void 0 : feature.properties) == null ? void 0 : _P.description, find: [`IMPACT...`], removal: [`.`] })) != null ? _Q : null,
16420
+ estimated_hail_size: (_U = (_T = (_S = (_R = feature == null ? void 0 : feature.properties) == null ? void 0 : _R.parameters) == null ? void 0 : _S.maxHailSize) == null ? void 0 : _T[0]) != null ? _U : null,
16421
+ estimated_wind_gusts: (_Y = (_X = (_W = (_V = feature == null ? void 0 : feature.properties) == null ? void 0 : _V.parameters) == null ? void 0 : _W.maxWindGust) == null ? void 0 : _X[0]) != null ? _Y : null,
16422
+ damage_threat: (_aa = (_$ = (__ = (_Z = feature == null ? void 0 : feature.properties) == null ? void 0 : _Z.parameters) == null ? void 0 : __.thunderstormDamageThreat) == null ? void 0 : _$[0]) != null ? _aa : null,
16423
+ tornado_threat: (_ea = (_da = (_ca = (_ba = feature == null ? void 0 : feature.properties) == null ? void 0 : _ba.parameters) == null ? void 0 : _ca.tornadoDetection) == null ? void 0 : _da[0]) != null ? _ea : null,
16424
+ flood_threat: (_ia = (_ha = (_ga = (_fa = feature == null ? void 0 : feature.properties) == null ? void 0 : _fa.parameters) == null ? void 0 : _ga.floodDetection) == null ? void 0 : _ha[0]) != null ? _ia : null,
16425
+ wind_threat: (_ma = (_la = (_ka = (_ja = feature == null ? void 0 : feature.properties) == null ? void 0 : _ja.parameters) == null ? void 0 : _ka.windThreat) == null ? void 0 : _la[0]) != null ? _ma : null,
16426
+ hail_threat: (_qa = (_pa = (_oa = (_na = feature == null ? void 0 : feature.properties) == null ? void 0 : _na.parameters) == null ? void 0 : _oa.hailThreat) == null ? void 0 : _pa[0]) != null ? _qa : null
16254
16427
  },
16255
- spc_parameters: {
16256
- spc_number: (_oa = getTextFromProduct({ message: (_na = feature == null ? void 0 : feature.properties) == null ? void 0 : _na.description, find: [`Mesoscale Discussion `], removal: [`Mesoscale Discussion`, `Number`, `...`] })) != null ? _oa : null,
16257
- spc_concerning: (_qa = getTextFromProduct({ message: (_pa = feature == null ? void 0 : feature.properties) == null ? void 0 : _pa.description, find: [`Concerning...`] })) != null ? _qa : null,
16258
- spc_max_tornado: (_sa = getTextFromProduct({ message: (_ra = feature == null ? void 0 : feature.properties) == null ? void 0 : _ra.description, find: [`MOST PROBABLE PEAK TORNADO INTENSITY...`] })) != null ? _sa : null,
16259
- spc_max_hail: (_ua = getTextFromProduct({ message: (_ta = feature == null ? void 0 : feature.properties) == null ? void 0 : _ta.description, find: [`MOST PROBABLE PEAK HAIL SIZE...`] })) != null ? _ua : null,
16260
- spc_max_wind: (_wa = getTextFromProduct({ message: (_va = feature == null ? void 0 : feature.properties) == null ? void 0 : _va.description, find: [`MOST PROBABLE PEAK WIND GUST...`] })) != null ? _wa : null,
16261
- spc_watch_issuance: (_ya = getTextFromProduct({ message: (_xa = feature == null ? void 0 : feature.properties) == null ? void 0 : _xa.description, find: [`Probability of Watch Issuance...`], removal: [`percent`] })) != null ? _ya : null
16428
+ discussion_parameters: {
16429
+ discussion_number: (_ua = (_ta = (_sa = getTextFromProduct({ message: (_ra = feature == null ? void 0 : feature.properties) == null ? void 0 : _ra.description, find: [`Mesoscale Discussion `], removal: [`Mesoscale Discussion`, `Number`, `...`] })) == null ? void 0 : _sa.toString()) == null ? void 0 : _ta.padStart(4, "0")) != null ? _ua : null,
16430
+ discussion_concerning: (_wa = getTextFromProduct({ message: (_va = feature == null ? void 0 : feature.properties) == null ? void 0 : _va.description, find: [`Concerning...`] })) != null ? _wa : null,
16431
+ discussion_max_tornado: (_ya = getTextFromProduct({ message: (_xa = feature == null ? void 0 : feature.properties) == null ? void 0 : _xa.description, find: [`MOST PROBABLE PEAK TORNADO INTENSITY...`] })) != null ? _ya : null,
16432
+ discussion_max_hail: (_Aa = getTextFromProduct({ message: (_za = feature == null ? void 0 : feature.properties) == null ? void 0 : _za.description, find: [`MOST PROBABLE PEAK HAIL SIZE...`] })) != null ? _Aa : null,
16433
+ discussion_max_wind: (_Ca = getTextFromProduct({ message: (_Ba = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ba.description, find: [`MOST PROBABLE PEAK WIND GUST...`] })) != null ? _Ca : null,
16434
+ discussion_watch_issuance: (_Ea = getTextFromProduct({ message: (_Da = feature == null ? void 0 : feature.properties) == null ? void 0 : _Da.description, find: [`Probability of Watch Issuance...`], removal: [`percent`] })) != null ? _Ea : null
16262
16435
  },
16263
16436
  watch_parameters: {
16264
- watch_number: (_Ca = (_Ba = (_Aa = getTextFromProduct({ message: (_za = feature == null ? void 0 : feature.properties) == null ? void 0 : _za.description, find: [`ITIES FOR`, `UPDATE FOR`, `Watch Number `], removal: [`%`, `<`, `:`] })) == null ? void 0 : _Aa.replace(/(WT|WS|)/g, "")) == null ? void 0 : _Ba.trim()) != null ? _Ca : null,
16265
- watch_type: ((_Da = feature == null ? void 0 : feature.properties) == null ? void 0 : _Da.description.includes(`TORNADO WATCH`)) ? `Tornado` : ((_Ea = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ea.description.includes(`SEVERE`)) ? `Severe` : null,
16266
- additional_tornadoes_probability: (_Ga = getTextFromProduct({ message: (_Fa = feature == null ? void 0 : feature.properties) == null ? void 0 : _Fa.description, find: [`PROB OF 2 OR MORE TORNADOES`], removal: [`%`, `<`, `:`] })) != null ? _Ga : null,
16267
- strong_tornadoes_probability: (_Ia = getTextFromProduct({ message: (_Ha = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ha.description, find: [`PROB OF 1 OR MORE STRONG /EF2-EF5/ TORNADOES`], removal: [`%`, `<`, `:`] })) != null ? _Ia : null,
16268
- severe_wind_probability: (_Ka = getTextFromProduct({ message: (_Ja = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ja.description, find: [`PROB OF 10 OR MORE SEVERE WIND EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _Ka : null,
16269
- severe_hail_probability: (_Ma = getTextFromProduct({ message: (_La = feature == null ? void 0 : feature.properties) == null ? void 0 : _La.description, find: [`PROB OF 10 OR MORE SEVERE HAIL EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _Ma : null,
16270
- hail_2in_probability: (_Oa = getTextFromProduct({ message: (_Na = feature == null ? void 0 : feature.properties) == null ? void 0 : _Na.description, find: [`PROB OF 1 OR MORE HAIL EVENTS >= 2 INCHES`], removal: [`%`, `<`, `:`] })) != null ? _Oa : null,
16271
- combined_hail_wind_probability: (_Qa = getTextFromProduct({ message: (_Pa = feature == null ? void 0 : feature.properties) == null ? void 0 : _Pa.description, find: [`PROB OF 6 OR MORE COMBINED SEVERE HAIL/WIND EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _Qa : null,
16272
- max_hail_in: (_Sa = getTextFromProduct({ message: (_Ra = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ra.description, find: [`MAX HAIL /INCHES/`], removal: [`%`, `<`, `:`] })) != null ? _Sa : null,
16273
- max_wind_surface: (_Ua = getTextFromProduct({ message: (_Ta = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ta.description, find: [`MAX WIND GUSTS SURFACE /KNOTS/`], removal: [`%`, `<`, `:`] })) != null ? _Ua : null,
16274
- max_tops_x100feet: (_Wa = getTextFromProduct({ message: (_Va = feature == null ? void 0 : feature.properties) == null ? void 0 : _Va.description, find: [`MAX TOPS /X 100 FEET/`], removal: [`%`, `<`, `:`] })) != null ? _Wa : null,
16275
- pds_watch: getTextFromProduct({ message: (_Xa = feature == null ? void 0 : feature.properties) == null ? void 0 : _Xa.description, find: [`PARTICULARLY DANGEROUS SITUATION`], removal: [`%`, `<`, `:`] }) === `YES`
16437
+ watch_number: ((_Fa = pVtec == null ? void 0 : pVtec[0]) == null ? void 0 : _Fa.is_watch) && ((_Qa = (_Pa = (_Ka = (_Ja = (_Ia = (_Ha = getTextFromProduct({ message: (_Ga = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ga.description, find: [`ITIES FOR`, `UPDATE FOR`, `Watch Number `], removal: [`%`, `<`, `:`] })) == null ? void 0 : _Ha.replace(/(WT|WS|)/g, "")) == null ? void 0 : _Ia.trim()) == null ? void 0 : _Ja.toString()) == null ? void 0 : _Ka.padStart(4, "0")) != null ? _Pa : (_Oa = (_Na = (_Ma = (_La = pVtec == null ? void 0 : pVtec[0]) == null ? void 0 : _La.tracking) == null ? void 0 : _Ma.slice(-4)) == null ? void 0 : _Na.toString()) == null ? void 0 : _Oa.padStart(4, "0")) != null ? _Qa : null),
16438
+ watch_type: ((_Ra = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ra.description.includes(`TORNADO WATCH`)) ? `Tornado` : ((_Sa = feature == null ? void 0 : feature.properties) == null ? void 0 : _Sa.description.includes(`SEVERE`)) ? `Severe` : null,
16439
+ additional_tornadoes_probability: (_Ua = getTextFromProduct({ message: (_Ta = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ta.description, find: [`PROB OF 2 OR MORE TORNADOES`], removal: [`%`, `<`, `:`] })) != null ? _Ua : null,
16440
+ strong_tornadoes_probability: (_Wa = getTextFromProduct({ message: (_Va = feature == null ? void 0 : feature.properties) == null ? void 0 : _Va.description, find: [`PROB OF 1 OR MORE STRONG /EF2-EF5/ TORNADOES`], removal: [`%`, `<`, `:`] })) != null ? _Wa : null,
16441
+ severe_wind_probability: (_Ya = getTextFromProduct({ message: (_Xa = feature == null ? void 0 : feature.properties) == null ? void 0 : _Xa.description, find: [`PROB OF 10 OR MORE SEVERE WIND EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _Ya : null,
16442
+ severe_hail_probability: (__a = getTextFromProduct({ message: (_Za = feature == null ? void 0 : feature.properties) == null ? void 0 : _Za.description, find: [`PROB OF 10 OR MORE SEVERE HAIL EVENTS`], removal: [`%`, `<`, `:`] })) != null ? __a : null,
16443
+ hail_2in_probability: (_ab = getTextFromProduct({ message: (_$a = feature == null ? void 0 : feature.properties) == null ? void 0 : _$a.description, find: [`PROB OF 1 OR MORE HAIL EVENTS >= 2 INCHES`], removal: [`%`, `<`, `:`] })) != null ? _ab : null,
16444
+ combined_hail_wind_probability: (_cb = getTextFromProduct({ message: (_bb = feature == null ? void 0 : feature.properties) == null ? void 0 : _bb.description, find: [`PROB OF 6 OR MORE COMBINED SEVERE HAIL/WIND EVENTS`], removal: [`%`, `<`, `:`] })) != null ? _cb : null,
16445
+ max_hail_in: (_eb = getTextFromProduct({ message: (_db = feature == null ? void 0 : feature.properties) == null ? void 0 : _db.description, find: [`MAX HAIL /INCHES/`], removal: [`%`, `<`, `:`] })) != null ? _eb : null,
16446
+ max_wind_surface: (_gb = getTextFromProduct({ message: (_fb = feature == null ? void 0 : feature.properties) == null ? void 0 : _fb.description, find: [`MAX WIND GUSTS SURFACE /KNOTS/`], removal: [`%`, `<`, `:`] })) != null ? _gb : null,
16447
+ max_tops_x100feet: (_ib = getTextFromProduct({ message: (_hb = feature == null ? void 0 : feature.properties) == null ? void 0 : _hb.description, find: [`MAX TOPS /X 100 FEET/`], removal: [`%`, `<`, `:`] })) != null ? _ib : null,
16448
+ pds_watch: getTextFromProduct({ message: (_jb = feature == null ? void 0 : feature.properties) == null ? void 0 : _jb.description, find: [`PARTICULARLY DANGEROUS SITUATION`], removal: [`%`, `<`, `:`] }) === `YES`
16276
16449
  },
16277
16450
  metadata: {
16278
16451
  ms: performance.now() - tick,
16279
16452
  source: `events.api`,
16280
- tracking: getEventTracking({ type: `API`, organization: { wmoidentifier: (__a = (_Za = (_Ya = feature == null ? void 0 : feature.properties) == null ? void 0 : _Ya.parameters) == null ? void 0 : _Za.WMOidentifier) == null ? void 0 : __a[0], featureId: feature == null ? void 0 : feature.id }, vtec: pVtec }),
16281
- header: `ZCZC-ATMOSX-${(_ab = (_$a = feature == null ? void 0 : feature.properties) == null ? void 0 : _$a.parameters) == null ? void 0 : _ab.WMOidentifier}`,
16282
- vtec: pVtec,
16453
+ tracking: getEventTracking({ type: `API`, organization: { wmoidentifier: (_mb = (_lb = (_kb = feature == null ? void 0 : feature.properties) == null ? void 0 : _kb.parameters) == null ? void 0 : _lb.WMOidentifier) == null ? void 0 : _mb[0], featureId: feature == null ? void 0 : feature.id }, vtec: pVtec == null ? void 0 : pVtec[0] }),
16454
+ header: `ZCZC-ATMOSX-${(_ob = (_nb = feature == null ? void 0 : feature.properties) == null ? void 0 : _nb.parameters) == null ? void 0 : _ob.WMOidentifier}`,
16455
+ vtec: pVtec == null ? void 0 : pVtec[0],
16283
16456
  hvtec: null,
16284
- raw: (_bb = feature == null ? void 0 : feature.properties) == null ? void 0 : _bb.description,
16457
+ raw: (_pb = feature == null ? void 0 : feature.properties) == null ? void 0 : _pb.description,
16285
16458
  history: [
16286
16459
  {
16287
- description: (_cb = feature == null ? void 0 : feature.properties) == null ? void 0 : _cb.description,
16288
- issued: ((_db = feature == null ? void 0 : feature.properties) == null ? void 0 : _db.sent) ? new Date((_eb = feature == null ? void 0 : feature.properties) == null ? void 0 : _eb.sent).toISOString() : null,
16289
- status: (_gb = (_fb = feature == null ? void 0 : feature.properties) == null ? void 0 : _fb.messageType) != null ? _gb : null
16460
+ description: (_qb = feature == null ? void 0 : feature.properties) == null ? void 0 : _qb.description,
16461
+ issued: ((_rb = feature == null ? void 0 : feature.properties) == null ? void 0 : _rb.sent) ? new Date((_sb = feature == null ? void 0 : feature.properties) == null ? void 0 : _sb.sent).toISOString() : null,
16462
+ status: (_ub = (_tb = feature == null ? void 0 : feature.properties) == null ? void 0 : _tb.messageType) != null ? _ub : null
16290
16463
  }
16291
16464
  ]
16292
16465
  }
@@ -16404,11 +16577,11 @@ var xDeploy = () => __async(null, null, function* () {
16404
16577
  });
16405
16578
 
16406
16579
  // src/@modules/@database/database.init.ts
16407
- var import_fs4 = __toESM(require("fs"));
16580
+ var import_fs5 = __toESM(require("fs"));
16408
16581
  var import_better_sqlite3 = __toESM(require("better-sqlite3"));
16409
16582
 
16410
16583
  // src/@modules/@database/database.shapefiles.ts
16411
- var import_fs3 = __toESM(require("fs"));
16584
+ var import_fs4 = __toESM(require("fs"));
16412
16585
  var import_path3 = require("path");
16413
16586
  var import_jszip = require("jszip");
16414
16587
  var import_shapefile = require("shapefile");
@@ -16422,8 +16595,8 @@ var setSleep = (options) => __async(null, null, function* () {
16422
16595
  });
16423
16596
  });
16424
16597
 
16425
- // src/@dictionaries/dictionaries.shapefileLinks.ts
16426
- var shapefileLinks = [
16598
+ // src/@dictionaries/dictionaries.shapefiles.ts
16599
+ var dict_shapefiles = [
16427
16600
  { name: "us_counties", id: "C", link: "https://www.weather.gov/source/gis/Shapefiles/County/c_16ap26.zip" },
16428
16601
  { name: "us_states_territories", id: "Z", link: "https://www.weather.gov/source/gis/Shapefiles/County/s_16ap26.zip" },
16429
16602
  { name: "fire_weather_zones", id: "Z", link: "https://www.weather.gov/source/gis/Shapefiles/WSOM/fz16ap26.zip" },
@@ -16443,20 +16616,19 @@ var importShapefiles = () => __async(null, null, function* () {
16443
16616
  const tShapefiles = bootstrap.database.prepare(`SELECT COUNT(*) AS count FROM shapefiles`).get().count;
16444
16617
  if (tShapefiles === 0) {
16445
16618
  yield setSleep({ timeout: 1e3 });
16446
- setWarning({ message: `Shapefiles are currently building, please DO NOT close your terminal. The shapefiles will not finish and will remain incomplete. If you do mess up, you will need to delete ${settings.Database} and restart the application.` });
16447
- for (const shapefile of shapefileLinks) {
16619
+ for (const shapefile of dict_shapefiles) {
16448
16620
  const response2 = yield fetch(shapefile.link);
16449
16621
  const arrayBuff = yield response2.arrayBuffer();
16450
16622
  const content = yield (0, import_jszip.loadAsync)(arrayBuff);
16451
16623
  const directory = (0, import_path3.resolve)(__dirname, `../../shapefiles`);
16452
- if (!import_fs3.default.existsSync(directory)) {
16453
- import_fs3.default.mkdirSync(directory, { recursive: true });
16624
+ if (!import_fs4.default.existsSync(directory)) {
16625
+ import_fs4.default.mkdirSync(directory, { recursive: true });
16454
16626
  }
16455
16627
  for (const file of Object.keys(content.files)) {
16456
16628
  if (file.endsWith(".shp") || file.endsWith(".dbf")) {
16457
16629
  const data = yield content.files[file].async(`nodebuffer`);
16458
16630
  const output = (0, import_path3.resolve)(directory, `${(_a = shapefile == null ? void 0 : shapefile.name) != null ? _a : ``}_${(_b = shapefile == null ? void 0 : shapefile.id) != null ? _b : ``}${(0, import_path3.extname)(file)}`);
16459
- import_fs3.default.writeFileSync(output, data);
16631
+ import_fs4.default.writeFileSync(output, data);
16460
16632
  }
16461
16633
  }
16462
16634
  const filepath = (0, import_path3.resolve)(__dirname, "../../shapefiles", shapefile.name + "_" + shapefile.id);
@@ -16464,7 +16636,7 @@ var importShapefiles = () => __async(null, null, function* () {
16464
16636
  filepath,
16465
16637
  filepath
16466
16638
  );
16467
- setWarning({ message: `Importing ${features.length} features from ${shapefile.name}_${shapefile.id}` });
16639
+ setWarning({ message: `Importing ${features.length} features from ${shapefile.name}_${shapefile.id} for Shapefiles` });
16468
16640
  const insert = bootstrap.database.prepare(`INSERT OR REPLACE INTO shapefiles (id, location, geometry) VALUES (?, ?, ?)`);
16469
16641
  const transaction = bootstrap.database.transaction((entries) => {
16470
16642
  var _a2, _b2, _c;
@@ -16487,13 +16659,11 @@ var importShapefiles = () => __async(null, null, function* () {
16487
16659
  insert.run(final2, location, JSON.stringify(geometry));
16488
16660
  }
16489
16661
  });
16490
- import_fs3.default.unlinkSync(`${filepath}.shp`);
16491
- import_fs3.default.unlinkSync(`${filepath}.dbf`);
16492
- setWarning({ message: `Cleaned up temporary files for ${shapefile.name}_${shapefile.id}` });
16662
+ import_fs4.default.unlinkSync(`${filepath}.shp`);
16663
+ import_fs4.default.unlinkSync(`${filepath}.dbf`);
16493
16664
  transaction(features);
16494
16665
  }
16495
- setWarning({ message: `Shapefiles have finished compiling, you can now continue and close this terminal` });
16496
- import_fs3.default.rm((0, import_path3.resolve)(__dirname, "../../shapefiles"), { recursive: true, force: true }, () => {
16666
+ import_fs4.default.rm((0, import_path3.resolve)(__dirname, "../../shapefiles"), { recursive: true, force: true }, () => {
16497
16667
  });
16498
16668
  }
16499
16669
  } catch (error) {
@@ -16501,18 +16671,68 @@ var importShapefiles = () => __async(null, null, function* () {
16501
16671
  }
16502
16672
  });
16503
16673
 
16674
+ // src/@modules/@database/database.broadcastify.ts
16675
+ var importBroadcastify = () => __async(null, null, function* () {
16676
+ const settings = bootstrap.settings;
16677
+ const isBroadcastifyImported = bootstrap.database.prepare(`SELECT name FROM sqlite_master WHERE type='table' AND name='broadcastify';`).get();
16678
+ if (!settings.BroadcastifySettings.BroadcastifyAttachments) {
16679
+ return;
16680
+ }
16681
+ if (isBroadcastifyImported) {
16682
+ return;
16683
+ }
16684
+ const broadcastify = yield createHttp({
16685
+ url: settings.BroadcastifySettings.BroadcastifyDatabase,
16686
+ timeout: 5e3
16687
+ });
16688
+ if (!broadcastify.error) {
16689
+ bootstrap.database.prepare(`CREATE TABLE broadcastify ( state TEXT, county TEXT, feed TEXT, type TEXT, link TEXT);`).run();
16690
+ const states = JSON.parse(broadcastify.message);
16691
+ const insert = bootstrap.database.prepare(`INSERT INTO broadcastify (state, county, feed, type, link) VALUES (?, ?, ?, ?, ?)`);
16692
+ const transaction = bootstrap.database.transaction((rows) => {
16693
+ for (const row of rows) {
16694
+ insert.run(row);
16695
+ }
16696
+ });
16697
+ const batch = [];
16698
+ for (const state of states) {
16699
+ setWarning({ message: `Importing ${state.counties.length} counties from ${state.state} for Broadcastify` });
16700
+ for (const county of state.counties) {
16701
+ const countyName = county.county;
16702
+ for (const feed of county.feeds) {
16703
+ batch.push([
16704
+ state.state,
16705
+ countyName,
16706
+ feed.name,
16707
+ feed.type,
16708
+ feed.link
16709
+ ]);
16710
+ }
16711
+ }
16712
+ }
16713
+ transaction(batch);
16714
+ }
16715
+ });
16716
+
16504
16717
  // src/@modules/@database/database.init.ts
16505
16718
  var initializeDatabase = () => __async(null, null, function* () {
16506
16719
  const settings = bootstrap.settings;
16507
16720
  try {
16508
- if (!import_fs4.default.existsSync(settings.Database)) {
16509
- import_fs4.default.writeFileSync(settings.Database, "");
16721
+ if (!import_fs5.default.existsSync(settings.Database)) {
16722
+ import_fs5.default.writeFileSync(settings.Database, "");
16510
16723
  setWarning({ message: `Creating new database at ${settings.Database}` });
16511
16724
  }
16512
16725
  bootstrap.database = new import_better_sqlite3.default(settings.Database);
16513
16726
  bootstrap.database.prepare(`CREATE TABLE IF NOT EXISTS stanzas ( id INTEGER PRIMARY KEY AUTOINCREMENT, type TEXT, issued TEXT, stanza TEXT )`).run();
16514
16727
  bootstrap.database.prepare(`CREATE TABLE IF NOT EXISTS shapefiles (id TEXT PRIMARY KEY, location TEXT, geometry TEXT)`).run();
16515
- yield importShapefiles();
16728
+ const isNeedingShapefiles = bootstrap.database.prepare(`SELECT name FROM sqlite_master WHERE type='table' AND name='shapefiles';`).get();
16729
+ const isNeedingBroadcastify = bootstrap.database.prepare(`SELECT name FROM sqlite_master WHERE type='table' AND name='broadcastify';`).get();
16730
+ if (!isNeedingShapefiles || !isNeedingBroadcastify) {
16731
+ setWarning({ message: `Required database tables are currently building, please ${bootstrap.ansi_colors.RED}DO NOT${bootstrap.ansi_colors.RESET} close your terminal. The building will not finish and will remain incomplete. If you do mess up, you will need to delete ${settings.Database} and restart the application.` });
16732
+ yield importBroadcastify();
16733
+ yield importShapefiles();
16734
+ setWarning({ message: `Building has completed, you can now continue or close the terminal` });
16735
+ }
16516
16736
  } catch (error) {
16517
16737
  setWarning({ message: `An error occurred while initializing the database: ${error.message}` });
16518
16738
  }
@@ -16573,7 +16793,8 @@ var xReconnect = (interval) => __async(null, null, function* () {
16573
16793
  },
16574
16794
  type: `reconnect`,
16575
16795
  error: true
16576
- }
16796
+ },
16797
+ message: `Attempting to reconnect to XMPP Service (Reconnect Attempt ${bootstrap.cache.tReconnects})`
16577
16798
  });
16578
16799
  yield bootstrap.session_xmpp.stop().catch(() => {
16579
16800
  });
@@ -16589,25 +16810,25 @@ var xReconnect = (interval) => __async(null, null, function* () {
16589
16810
  });
16590
16811
 
16591
16812
  // src/@modules/@utilities/utilities.setCronSchedule.ts
16592
- var import_fs5 = require("fs");
16813
+ var import_fs6 = require("fs");
16593
16814
  var import_path4 = require("path");
16594
16815
  var setCronSchedule = () => __async(null, null, function* () {
16595
16816
  const settings = bootstrap.settings;
16596
- const TTL = settings.GlobalSettings.EASSettings.ArchiveTTL;
16817
+ const TTL = settings.GlobalSettings.ArchiveSettings.TTL;
16597
16818
  const TTLCUT = Date.now() - TTL * 1e3;
16598
16819
  const walk = (dir) => {
16599
- if ((0, import_fs5.existsSync)(dir)) {
16600
- const entries = (0, import_fs5.readdirSync)(dir, { withFileTypes: true });
16820
+ if ((0, import_fs6.existsSync)(dir)) {
16821
+ const entries = (0, import_fs6.readdirSync)(dir, { withFileTypes: true });
16601
16822
  for (const entry of entries) {
16602
16823
  const fullPath = (0, import_path4.join)(dir, entry.name);
16603
16824
  if (entry.isDirectory()) {
16604
16825
  walk(fullPath);
16605
16826
  continue;
16606
16827
  }
16607
- const stats = (0, import_fs5.statSync)(fullPath);
16828
+ const stats = (0, import_fs6.statSync)(fullPath);
16608
16829
  if (stats.mtime.getTime() < TTLCUT) {
16609
16830
  try {
16610
- (0, import_fs5.unlinkSync)(fullPath);
16831
+ (0, import_fs6.unlinkSync)(fullPath);
16611
16832
  } catch (err) {
16612
16833
  console.error(`Failed to delete ${fullPath}:`, err);
16613
16834
  }
@@ -16615,7 +16836,9 @@ var setCronSchedule = () => __async(null, null, function* () {
16615
16836
  }
16616
16837
  }
16617
16838
  };
16618
- walk(settings.GlobalSettings.EASSettings.ArchiveDirectory);
16839
+ walk(settings.GlobalSettings.ArchiveSettings.TextDirectory);
16840
+ walk(settings.GlobalSettings.ArchiveSettings.EasDirectory);
16841
+ walk(settings.GlobalSettings.ArchiveSettings.EventDirectory);
16619
16842
  if (settings.EnableWireService) {
16620
16843
  if (settings.NOAAWeatherWireServiceSettings.ReconnectionSettings.Enabled) {
16621
16844
  void xReconnect(settings.NOAAWeatherWireServiceSettings.ReconnectionSettings.ReconnectionInterval);
@@ -16783,6 +17006,60 @@ var getNodes = () => {
16783
17006
  return bootstrap.cache.nodes;
16784
17007
  };
16785
17008
 
17009
+ // src/@core/core.createEvent.ts
17010
+ var createEvent2 = (options) => {
17011
+ var _a;
17012
+ const tick = performance.now();
17013
+ validateEvents([{
17014
+ type: `Feature`,
17015
+ geometry: {
17016
+ type: `Point`,
17017
+ coordinates: options.coordinates
17018
+ },
17019
+ properties: {
17020
+ event: options.event,
17021
+ parent: options.event,
17022
+ status: options.status,
17023
+ issued: options.issued.toISOString(),
17024
+ expires: options.expires.toISOString(),
17025
+ locations: options.locations,
17026
+ locations_array: options.locations ? options.locations.split(";") : [],
17027
+ description: options.description,
17028
+ geocode: {
17029
+ office: {
17030
+ office: `ATMX`,
17031
+ name: `AtmosphericX Manual Event`
17032
+ },
17033
+ organization: `AtmosphericX`,
17034
+ ugc: [],
17035
+ polygon: options.coordinates.length > 0 ? Buffer.from(JSON.stringify([options.coordinates[0]])).toString("base64") : null,
17036
+ polygon_generated: options.coordinates.length > 0 ? true : false
17037
+ },
17038
+ status_metadata: {
17039
+ is_issued: options.status == `Issued`,
17040
+ is_updated: options.status == `Updated`,
17041
+ is_expired: options.status == `Expired`,
17042
+ is_test: options.status == `Test`,
17043
+ is_statement: options.status == `Statement`
17044
+ },
17045
+ metadata: {
17046
+ ms: performance.now() - tick,
17047
+ source: `events.manual`,
17048
+ tracking: `ATMX-M-W-01`,
17049
+ header: `ZCZC-ATMOSX-ATMX-M-W-01`,
17050
+ raw: options.description,
17051
+ history: [
17052
+ {
17053
+ description: options.description,
17054
+ issued: options.issued.toISOString(),
17055
+ status: (_a = options.status) != null ? _a : null
17056
+ }
17057
+ ]
17058
+ }
17059
+ }
17060
+ }]);
17061
+ };
17062
+
16786
17063
  // src/@core/core.getRandomEvent.ts
16787
17064
  var getRandomEvent = () => {
16788
17065
  return bootstrap.cache.events.features[Math.floor(Math.random() * bootstrap.cache.events.features.length)];
@@ -16843,6 +17120,7 @@ var index_default = Manager;
16843
17120
  0 && (module.exports = {
16844
17121
  Manager,
16845
17122
  clearEvents,
17123
+ createEvent,
16846
17124
  getCleanedEvent,
16847
17125
  getEventGeometry,
16848
17126
  getEvents,