fix: resolve lint warnings/errors and apply formatting (#1024)

* fix: resolve lint warnings/errors and apply formatting

Fix 10 oxlint issues (2 errors, 8 warnings):
- Remove unused catch parameters in Security.tsx and ImportDialog.tsx
- Remove stray expression in Generator.tsx
- Add eslint-disable for debounced useCallback in FilterControl.tsx
- Remove unnecessary deps (resolveDB, store) in bindStoreToDevice.ts
- Prefix unused variant param in AppSidebar.tsx
- Memoize tabs arrays in DeviceConfig, RadioConfig, ModuleConfig
- Fix channels type in RadioConfig TabItem

Also applies oxfmt formatting across all files.

* updating lock file

* update protobuf package

* fix: regenerate pnpm-lock.yaml and exclude jsr protobufs from minimumReleaseAge

* prevented http card from always being polled

* updated pnpm config fiile

* updated actions

* removed biome config and lint system leftovers

* updating protobuf package
This commit is contained in:
Dan Ditomaso
2026-03-11 21:54:25 -04:00
committed by GitHub
parent a90df07ebe
commit c729d3b25e
256 changed files with 2164 additions and 4362 deletions
+41 -125
View File
@@ -44,8 +44,7 @@ export class MeshDevice {
constructor(transport: Transport, configId?: number) {
this.log = new Logger({
name: "iMeshDevice",
prettyLogTemplate:
"{{hh}}:{{MM}}:{{ss}}:{{ms}}\t{{logLevelName}}\t[{{name}}]\t",
prettyLogTemplate: "{{hh}}:{{MM}}:{{ss}}:{{ms}}\t{{logLevelName}}\t[{{name}}]\t",
});
this.transport = transport;
@@ -107,9 +106,7 @@ export class MeshDevice {
): Promise<number> {
this.log.debug(
Emitter[Emitter.SendText],
`📤 Sending message to ${destination ?? "broadcast"} on channel ${
channel?.toString() ?? 0
}`,
`📤 Sending message to ${destination ?? "broadcast"} on channel ${channel?.toString() ?? 0}`,
);
const enc = new TextEncoder();
@@ -137,9 +134,7 @@ export class MeshDevice {
): Promise<number> {
this.log.debug(
Emitter[Emitter.SendWaypoint],
`📤 Sending waypoint to ${destination} on channel ${
channel?.toString() ?? 0
}`,
`📤 Sending waypoint to ${destination} on channel ${channel?.toString() ?? 0}`,
);
waypointMessage.id = this.generateRandId();
@@ -210,19 +205,13 @@ export class MeshDevice {
meshPacket.rxTime = Math.trunc(Date.now() / 1000);
this.handleMeshPacket(meshPacket);
}
return await this.sendRaw(
toBinary(Protobuf.Mesh.ToRadioSchema, toRadioMessage),
meshPacket.id,
);
return await this.sendRaw(toBinary(Protobuf.Mesh.ToRadioSchema, toRadioMessage), meshPacket.id);
}
/**
* Sends raw packet over the radio
*/
public async sendRaw(
toRadio: Uint8Array,
id: number = this.generateRandId(),
): Promise<number> {
public async sendRaw(toRadio: Uint8Array, id: number = this.generateRandId()): Promise<number> {
if (toRadio.length > 512) {
throw new Error("Message longer than 512 bytes, it will not be sent!");
}
@@ -266,9 +255,7 @@ export class MeshDevice {
/**
* Writes module config to device
*/
public async setModuleConfig(
moduleConfig: Protobuf.ModuleConfig.ModuleConfig,
): Promise<number> {
public async setModuleConfig(moduleConfig: Protobuf.ModuleConfig.ModuleConfig): Promise<number> {
this.log.debug(Emitter[Emitter.SetModuleConfig], "⚙️ Setting module config");
const moduleConfigMessage = create(Protobuf.Admin.AdminMessageSchema, {
@@ -289,10 +276,7 @@ export class MeshDevice {
public async setCannedMessages(
cannedMessages: Protobuf.CannedMessages.CannedMessageModuleConfig,
): Promise<number> {
this.log.debug(
Emitter[Emitter.SetCannedMessages],
"⚙️ Setting CannedMessages",
);
this.log.debug(Emitter[Emitter.SetCannedMessages], "⚙️ Setting CannedMessages");
const cannedMessagesMessage = create(Protobuf.Admin.AdminMessageSchema, {
payloadVariant: {
@@ -332,10 +316,7 @@ export class MeshDevice {
* Sets devices ChannelSettings
*/
public async setChannel(channel: Protobuf.Channel.Channel): Promise<number> {
this.log.debug(
Emitter[Emitter.SetChannel],
`📻 Setting Channel: ${channel.index}`,
);
this.log.debug(Emitter[Emitter.SetChannel], `📻 Setting Channel: ${channel.index}`);
const setChannelMessage = create(Protobuf.Admin.AdminMessageSchema, {
payloadVariant: {
@@ -373,9 +354,7 @@ export class MeshDevice {
/**
* Sets static position of device
*/
public async setPosition(
positionMessage: Protobuf.Mesh.Position,
): Promise<number> {
public async setPosition(positionMessage: Protobuf.Mesh.Position): Promise<number> {
return await this.sendPacket(
toBinary(Protobuf.Mesh.PositionSchema, positionMessage),
Protobuf.Portnums.PortNum.POSITION_APP,
@@ -387,10 +366,7 @@ export class MeshDevice {
* Sets the fixed position of a device. Can be used to
* position GPS-less devices.
*/
public async setFixedPosition(
latitude: number,
longitude: number,
): Promise<number> {
public async setFixedPosition(latitude: number, longitude: number): Promise<number> {
const setPositionMessage = create(Protobuf.Admin.AdminMessageSchema, {
payloadVariant: {
case: "setFixedPosition",
@@ -434,10 +410,7 @@ export class MeshDevice {
* Gets specified channel information from the radio
*/
public async getChannel(index: number): Promise<number> {
this.log.debug(
Emitter[Emitter.GetChannel],
`📻 Requesting Channel: ${index}`,
);
this.log.debug(Emitter[Emitter.GetChannel], `📻 Requesting Channel: ${index}`);
const getChannelRequestMessage = create(Protobuf.Admin.AdminMessageSchema, {
payloadVariant: {
@@ -456,9 +429,7 @@ export class MeshDevice {
/**
* Gets devices config
*/
public async getConfig(
configType: Protobuf.Admin.AdminMessage_ConfigType,
): Promise<number> {
public async getConfig(configType: Protobuf.Admin.AdminMessage_ConfigType): Promise<number> {
this.log.debug(Emitter[Emitter.GetConfig], "⚙️ Requesting config");
const getRadioRequestMessage = create(Protobuf.Admin.AdminMessageSchema, {
@@ -481,10 +452,7 @@ export class MeshDevice {
public async getModuleConfig(
moduleConfigType: Protobuf.Admin.AdminMessage_ModuleConfigType,
): Promise<number> {
this.log.debug(
Emitter[Emitter.GetModuleConfig],
"⚙️ Requesting module config",
);
this.log.debug(Emitter[Emitter.GetModuleConfig], "⚙️ Requesting module config");
const getRadioRequestMessage = create(Protobuf.Admin.AdminMessageSchema, {
payloadVariant: {
@@ -522,26 +490,17 @@ export class MeshDevice {
* Gets devices metadata
*/
public async getMetadata(nodeNum: number): Promise<number> {
this.log.debug(
Emitter[Emitter.GetMetadata],
`🏷️ Requesting metadata from ${nodeNum}`,
);
this.log.debug(Emitter[Emitter.GetMetadata], `🏷️ Requesting metadata from ${nodeNum}`);
const getDeviceMetricsRequestMessage = create(
Protobuf.Admin.AdminMessageSchema,
{
payloadVariant: {
case: "getDeviceMetadataRequest",
value: true,
},
const getDeviceMetricsRequestMessage = create(Protobuf.Admin.AdminMessageSchema, {
payloadVariant: {
case: "getDeviceMetadataRequest",
value: true,
},
);
});
return await this.sendPacket(
toBinary(
Protobuf.Admin.AdminMessageSchema,
getDeviceMetricsRequestMessage,
),
toBinary(Protobuf.Admin.AdminMessageSchema, getDeviceMetricsRequestMessage),
Protobuf.Portnums.PortNum.ADMIN_APP,
nodeNum,
ChannelNumber.Admin,
@@ -552,10 +511,7 @@ export class MeshDevice {
* Clears specific channel with the designated index
*/
public async clearChannel(index: number): Promise<number> {
this.log.debug(
Emitter[Emitter.ClearChannel],
`📻 Clearing Channel ${index}`,
);
this.log.debug(Emitter[Emitter.ClearChannel], `📻 Clearing Channel ${index}`);
const channel = create(Protobuf.Channel.ChannelSchema, {
index,
@@ -634,10 +590,7 @@ export class MeshDevice {
* Removes a node from the internal NodeDB of the radio by node number
*/
public async removeNodeByNum(nodeNum: number): Promise<number> {
this.log.debug(
Emitter[Emitter.RemoveNodeByNum],
`📻 Removing Node ${nodeNum} from NodeDB`,
);
this.log.debug(Emitter[Emitter.RemoveNodeByNum], `📻 Removing Node ${nodeNum} from NodeDB`);
const removeNodeByNum = create(Protobuf.Admin.AdminMessageSchema, {
payloadVariant: {
@@ -762,10 +715,7 @@ export class MeshDevice {
* Triggers the device configure process
*/
public configure(): Promise<number> {
this.log.debug(
Emitter[Emitter.Configure],
"⚙️ Requesting device configuration",
);
this.log.debug(Emitter[Emitter.Configure], "⚙️ Requesting device configuration");
this.updateDeviceStatus(DeviceStatusEnum.DeviceConfiguring);
const toRadio = create(Protobuf.Mesh.ToRadioSchema, {
@@ -775,14 +725,12 @@ export class MeshDevice {
},
});
return this.sendRaw(toBinary(Protobuf.Mesh.ToRadioSchema, toRadio)).catch(
(e) => {
if (this.deviceStatus === DeviceStatusEnum.DeviceDisconnected) {
throw new Error("Device connection lost");
}
throw e;
},
);
return this.sendRaw(toBinary(Protobuf.Mesh.ToRadioSchema, toRadio)).catch((e) => {
if (this.deviceStatus === DeviceStatusEnum.DeviceDisconnected) {
throw new Error("Device connection lost");
}
throw e;
});
}
/**
@@ -810,10 +758,7 @@ export class MeshDevice {
}
this._heartbeatIntervalId = setInterval(() => {
this.heartbeat().catch((err) => {
this.log.error(
Emitter[Emitter.Ping],
`⚠️ Unable to send heartbeat: ${err.message}`,
);
this.log.error(Emitter[Emitter.Ping], `⚠️ Unable to send heartbeat: ${err.message}`);
});
}, interval);
}
@@ -950,10 +895,7 @@ export class MeshDevice {
case Protobuf.Portnums.PortNum.REMOTE_HARDWARE_APP: {
this.events.onRemoteHardwarePacket.dispatch({
...packetMetadata,
data: fromBinary(
Protobuf.RemoteHardware.HardwareMessageSchema,
dataPacket.payload,
),
data: fromBinary(Protobuf.RemoteHardware.HardwareMessageSchema, dataPacket.payload),
});
break;
}
@@ -975,10 +917,7 @@ export class MeshDevice {
}
case Protobuf.Portnums.PortNum.ROUTING_APP: {
routingPacket = fromBinary(
Protobuf.Mesh.RoutingSchema,
dataPacket.payload,
);
routingPacket = fromBinary(Protobuf.Mesh.RoutingSchema, dataPacket.payload);
this.events.onRoutingPacket.dispatch({
...packetMetadata,
@@ -986,9 +925,7 @@ export class MeshDevice {
});
switch (routingPacket.variant.case) {
case "errorReason": {
if (
routingPacket.variant.value === Protobuf.Mesh.Routing_Error.NONE
) {
if (routingPacket.variant.value === Protobuf.Mesh.Routing_Error.NONE) {
this.queue.processAck(dataPacket.requestId);
} else {
this.queue.processError({
@@ -1014,15 +951,10 @@ export class MeshDevice {
}
case Protobuf.Portnums.PortNum.ADMIN_APP: {
adminMessage = fromBinary(
Protobuf.Admin.AdminMessageSchema,
dataPacket.payload,
);
adminMessage = fromBinary(Protobuf.Admin.AdminMessageSchema, dataPacket.payload);
switch (adminMessage.payloadVariant.case) {
case "getChannelResponse": {
this.events.onChannelPacket.dispatch(
adminMessage.payloadVariant.value,
);
this.events.onChannelPacket.dispatch(adminMessage.payloadVariant.value);
break;
}
case "getOwnerResponse": {
@@ -1033,15 +965,11 @@ export class MeshDevice {
break;
}
case "getConfigResponse": {
this.events.onConfigPacket.dispatch(
adminMessage.payloadVariant.value,
);
this.events.onConfigPacket.dispatch(adminMessage.payloadVariant.value);
break;
}
case "getModuleConfigResponse": {
this.events.onModuleConfigPacket.dispatch(
adminMessage.payloadVariant.value,
);
this.events.onModuleConfigPacket.dispatch(adminMessage.payloadVariant.value);
break;
}
case "getDeviceMetadataResponse": {
@@ -1124,10 +1052,7 @@ export class MeshDevice {
case Protobuf.Portnums.PortNum.PAXCOUNTER_APP: {
this.events.onPaxcounterPacket.dispatch({
...packetMetadata,
data: fromBinary(
Protobuf.PaxCount.PaxcountSchema,
dataPacket.payload,
),
data: fromBinary(Protobuf.PaxCount.PaxcountSchema, dataPacket.payload),
});
break;
}
@@ -1159,10 +1084,7 @@ export class MeshDevice {
case Protobuf.Portnums.PortNum.TELEMETRY_APP: {
this.events.onTelemetryPacket.dispatch({
...packetMetadata,
data: fromBinary(
Protobuf.Telemetry.TelemetrySchema,
dataPacket.payload,
),
data: fromBinary(Protobuf.Telemetry.TelemetrySchema, dataPacket.payload),
});
break;
}
@@ -1186,10 +1108,7 @@ export class MeshDevice {
case Protobuf.Portnums.PortNum.TRACEROUTE_APP: {
this.events.onTraceRoutePacket.dispatch({
...packetMetadata,
data: fromBinary(
Protobuf.Mesh.RouteDiscoverySchema,
dataPacket.payload,
),
data: fromBinary(Protobuf.Mesh.RouteDiscoverySchema, dataPacket.payload),
});
break;
}
@@ -1197,10 +1116,7 @@ export class MeshDevice {
case Protobuf.Portnums.PortNum.NEIGHBORINFO_APP: {
this.events.onNeighborInfoPacket.dispatch({
...packetMetadata,
data: fromBinary(
Protobuf.Mesh.NeighborInfoSchema,
dataPacket.payload,
),
data: fromBinary(Protobuf.Mesh.NeighborInfoSchema, dataPacket.payload),
});
break;
}
+42 -65
View File
@@ -76,9 +76,8 @@ export class EventSystem {
*
* @event onAtakPacket
*/
public readonly onAtakPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onAtakPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Text packet has been
@@ -86,9 +85,8 @@ export class EventSystem {
*
* @event onMessagePacket
*/
public readonly onMessagePacket: SimpleEventDispatcher<
PacketMetadata<string>
> = new SimpleEventDispatcher<PacketMetadata<string>>();
public readonly onMessagePacket: SimpleEventDispatcher<PacketMetadata<string>> =
new SimpleEventDispatcher<PacketMetadata<string>>();
/**
* Fires when a new MeshPacket message containing a Remote Hardware packet has
@@ -98,9 +96,7 @@ export class EventSystem {
*/
public readonly onRemoteHardwarePacket: SimpleEventDispatcher<
PacketMetadata<Protobuf.RemoteHardware.HardwareMessage>
> = new SimpleEventDispatcher<
PacketMetadata<Protobuf.RemoteHardware.HardwareMessage>
>();
> = new SimpleEventDispatcher<PacketMetadata<Protobuf.RemoteHardware.HardwareMessage>>();
/**
* Fires when a new MeshPacket message containing a Position packet has been
@@ -108,9 +104,8 @@ export class EventSystem {
*
* @event onPositionPacket
*/
public readonly onPositionPacket: SimpleEventDispatcher<
PacketMetadata<Protobuf.Mesh.Position>
> = new SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.Position>>();
public readonly onPositionPacket: SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.Position>> =
new SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.Position>>();
/**
* Fires when a new MeshPacket message containing a User packet has been
@@ -118,9 +113,8 @@ export class EventSystem {
*
* @event onUserPacket
*/
public readonly onUserPacket: SimpleEventDispatcher<
PacketMetadata<Protobuf.Mesh.User>
> = new SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.User>>();
public readonly onUserPacket: SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.User>> =
new SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.User>>();
/**
* Fires when a new MeshPacket message containing a Routing packet has been
@@ -128,9 +122,8 @@ export class EventSystem {
*
* @event onRoutingPacket
*/
public readonly onRoutingPacket: SimpleEventDispatcher<
PacketMetadata<Protobuf.Mesh.Routing>
> = new SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.Routing>>();
public readonly onRoutingPacket: SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.Routing>> =
new SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.Routing>>();
/**
* Fires when the device receives a Metadata packet
@@ -146,9 +139,8 @@ export class EventSystem {
*
* @event onCannedMessageModulePacket
*/
public readonly onCannedMessageModulePacket: SimpleEventDispatcher<
PacketMetadata<string>
> = new SimpleEventDispatcher<PacketMetadata<string>>();
public readonly onCannedMessageModulePacket: SimpleEventDispatcher<PacketMetadata<string>> =
new SimpleEventDispatcher<PacketMetadata<string>>();
/**
* Fires when a new MeshPacket message containing a Waypoint packet has been
@@ -156,9 +148,8 @@ export class EventSystem {
*
* @event onWaypointPacket
*/
public readonly onWaypointPacket: SimpleEventDispatcher<
PacketMetadata<Protobuf.Mesh.Waypoint>
> = new SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.Waypoint>>();
public readonly onWaypointPacket: SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.Waypoint>> =
new SimpleEventDispatcher<PacketMetadata<Protobuf.Mesh.Waypoint>>();
/**
* Fires when a new MeshPacket message containing an Audio packet has been
@@ -166,9 +157,8 @@ export class EventSystem {
*
* @event onAudioPacket
*/
public readonly onAudioPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onAudioPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Detection Sensor packet has been
@@ -176,9 +166,8 @@ export class EventSystem {
*
* @event onDetectionSensorPacket
*/
public readonly onDetectionSensorPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onDetectionSensorPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Ping packet has been
@@ -186,9 +175,8 @@ export class EventSystem {
*
* @event onPingPacket
*/
public readonly onPingPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onPingPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a IP Tunnel packet has been
@@ -196,9 +184,8 @@ export class EventSystem {
*
* @event onIpTunnelPacket
*/
public readonly onIpTunnelPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onIpTunnelPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Paxcounter packet has been
@@ -216,9 +203,8 @@ export class EventSystem {
*
* @event onSerialPacket
*/
public readonly onSerialPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onSerialPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Store and Forward packet
@@ -226,9 +212,8 @@ export class EventSystem {
*
* @event onStoreForwardPacket
*/
public readonly onStoreForwardPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onStoreForwardPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Store and Forward packet
@@ -236,9 +221,8 @@ export class EventSystem {
*
* @event onRangeTestPacket
*/
public readonly onRangeTestPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onRangeTestPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Telemetry packet has been
@@ -256,9 +240,8 @@ export class EventSystem {
*
* @event onZPSPacket
*/
public readonly onZpsPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onZpsPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Simulator packet has been
@@ -266,9 +249,8 @@ export class EventSystem {
*
* @event onSimulatorPacket
*/
public readonly onSimulatorPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onSimulatorPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Trace Route packet has been
@@ -296,9 +278,8 @@ export class EventSystem {
*
* @event onAtakPluginPacket
*/
public readonly onAtakPluginPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onAtakPluginPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Map Report packet has been
@@ -306,9 +287,8 @@ export class EventSystem {
*
* @event onMapReportPacket
*/
public readonly onMapReportPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onMapReportPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a Private packet has been
@@ -316,9 +296,8 @@ export class EventSystem {
*
* @event onPrivatePacket
*/
public readonly onPrivatePacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onPrivatePacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing an ATAK Forwarder packet has been
@@ -326,9 +305,8 @@ export class EventSystem {
*
* @event onAtakForwarderPacket
*/
public readonly onAtakForwarderPacket: SimpleEventDispatcher<
PacketMetadata<Uint8Array>
> = new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
public readonly onAtakForwarderPacket: SimpleEventDispatcher<PacketMetadata<Uint8Array>> =
new SimpleEventDispatcher<PacketMetadata<Uint8Array>>();
/**
* Fires when a new MeshPacket message containing a ClientNotification packet has been
@@ -361,8 +339,7 @@ export class EventSystem {
*
* @event onMeshHeartbeat
*/
public readonly onMeshHeartbeat: SimpleEventDispatcher<Date> =
new SimpleEventDispatcher<Date>();
public readonly onMeshHeartbeat: SimpleEventDispatcher<Date> = new SimpleEventDispatcher<Date>();
/**
* Outputs any debug log data (currently serial connections only)
+4 -15
View File
@@ -54,9 +54,7 @@ export class Queue {
return;
}
console.warn(
`Packet ${item.id} of type ${decoded.payloadVariant.case} timed out`,
);
console.warn(`Packet ${item.id} of type ${decoded.payloadVariant.case} timed out`);
reject({
id: item.id,
@@ -82,11 +80,7 @@ export class Queue {
}
public processError(e: PacketError): void {
console.error(
`Error received for packet ${e.id}: ${
Protobuf.Mesh.Routing_Error[e.error]
}`,
);
console.error(`Error received for packet ${e.id}: ${Protobuf.Mesh.Routing_Error[e.error]}`);
this.errorNotifier.dispatch(e);
}
@@ -98,9 +92,7 @@ export class Queue {
return queueItem.promise;
}
public async processQueue(
outputStream: WritableStream<Uint8Array>,
): Promise<void> {
public async processQueue(outputStream: WritableStream<Uint8Array>): Promise<void> {
if (this.lock) {
return;
}
@@ -117,10 +109,7 @@ export class Queue {
await writer.write(item.data);
item.sent = true;
} catch (error) {
if (
error?.code === "ECONNRESET" ||
error?.code === "ERR_INVALID_STATE"
) {
if (error?.code === "ECONNRESET" || error?.code === "ERR_INVALID_STATE") {
writer.releaseLock();
this.lock = false;
throw error;
@@ -26,10 +26,7 @@ export const decodePacket = (device: MeshDevice) =>
case "packet": {
let decodedMessage: Protobuf.Mesh.FromRadio;
try {
decodedMessage = fromBinary(
Protobuf.Mesh.FromRadioSchema,
chunk.data,
);
decodedMessage = fromBinary(Protobuf.Mesh.FromRadioSchema, chunk.data);
} catch (e) {
device.log.error(
Types.Emitter[Types.Emitter.HandleFromRadio],
@@ -56,9 +53,7 @@ export const decodePacket = (device: MeshDevice) =>
}
case "myInfo": {
device.events.onMyNodeInfo.dispatch(
decodedMessage.payloadVariant.value,
);
device.events.onMyNodeInfo.dispatch(decodedMessage.payloadVariant.value);
device.log.info(
Types.Emitter[Types.Emitter.HandleFromRadio],
"📱 Received Node info for this device",
@@ -72,9 +67,7 @@ export const decodePacket = (device: MeshDevice) =>
`📱 Received Node Info packet for node: ${decodedMessage.payloadVariant.value.num}`,
);
device.events.onNodeInfoPacket.dispatch(
decodedMessage.payloadVariant.value,
);
device.events.onNodeInfoPacket.dispatch(decodedMessage.payloadVariant.value);
//TODO: HERE
if (decodedMessage.payloadVariant.value.position) {
@@ -117,9 +110,7 @@ export const decodePacket = (device: MeshDevice) =>
);
}
device.events.onConfigPacket.dispatch(
decodedMessage.payloadVariant.value,
);
device.events.onConfigPacket.dispatch(decodedMessage.payloadVariant.value);
break;
}
@@ -128,9 +119,7 @@ export const decodePacket = (device: MeshDevice) =>
Types.Emitter[Types.Emitter.HandleFromRadio],
"Received onLogRecord",
);
device.events.onLogRecord.dispatch(
decodedMessage.payloadVariant.value,
);
device.events.onLogRecord.dispatch(decodedMessage.payloadVariant.value);
break;
}
@@ -141,9 +130,7 @@ export const decodePacket = (device: MeshDevice) =>
);
// Emit the configCompleteId event for MeshService to handle two-stage flow
device.events.onConfigComplete.dispatch(
decodedMessage.payloadVariant.value,
);
device.events.onConfigComplete.dispatch(decodedMessage.payloadVariant.value);
// For backward compatibility: if configId matches, update device status
// MeshService will override this behavior for two-stage flow
@@ -152,9 +139,7 @@ export const decodePacket = (device: MeshDevice) =>
Types.Emitter[Types.Emitter.HandleFromRadio],
`⚙️ Config id matches device.configId: ${device.configId}`,
);
device.updateDeviceStatus(
Types.DeviceStatusEnum.DeviceConfigured,
);
device.updateDeviceStatus(Types.DeviceStatusEnum.DeviceConfigured);
}
break;
}
@@ -179,9 +164,7 @@ export const decodePacket = (device: MeshDevice) =>
);
}
device.events.onModuleConfigPacket.dispatch(
decodedMessage.payloadVariant.value,
);
device.events.onModuleConfigPacket.dispatch(decodedMessage.payloadVariant.value);
break;
}
@@ -191,9 +174,7 @@ export const decodePacket = (device: MeshDevice) =>
`🔐 Received Channel: ${decodedMessage.payloadVariant.value.index}`,
);
device.events.onChannelPacket.dispatch(
decodedMessage.payloadVariant.value,
);
device.events.onChannelPacket.dispatch(decodedMessage.payloadVariant.value);
break;
}
@@ -203,9 +184,7 @@ export const decodePacket = (device: MeshDevice) =>
`🚧 Received Queue Status: ${decodedMessage.payloadVariant.value}`,
);
device.events.onQueueStatus.dispatch(
decodedMessage.payloadVariant.value,
);
device.events.onQueueStatus.dispatch(decodedMessage.payloadVariant.value);
break;
}
@@ -216,9 +195,8 @@ export const decodePacket = (device: MeshDevice) =>
case "metadata": {
if (
Number.parseFloat(
decodedMessage.payloadVariant.value.firmwareVersion,
) < Constants.minFwVer
Number.parseFloat(decodedMessage.payloadVariant.value.firmwareVersion) <
Constants.minFwVer
) {
device.log.fatal(
Types.Emitter[Types.Emitter.HandleFromRadio],
+49 -57
View File
@@ -1,69 +1,61 @@
import type { DeviceOutput } from "../../types.ts";
export const fromDeviceStream: () => TransformStream<Uint8Array, DeviceOutput> =
(
// onReleaseEvent: SimpleEventDispatcher<boolean>,
) => {
let byteBuffer = new Uint8Array([]);
const textDecoder = new TextDecoder();
return new TransformStream<Uint8Array, DeviceOutput>({
transform(chunk: Uint8Array, controller): void {
// onReleaseEvent.subscribe(() => {
// controller.terminate();
// });
byteBuffer = new Uint8Array([...byteBuffer, ...chunk]);
let processingExhausted = false;
while (byteBuffer.length !== 0 && !processingExhausted) {
const framingIndex = byteBuffer.indexOf(0x94);
const framingByte2 = byteBuffer[framingIndex + 1];
if (framingByte2 === 0xc3) {
if (byteBuffer.subarray(0, framingIndex).length) {
controller.enqueue({
type: "debug",
data: textDecoder.decode(byteBuffer.subarray(0, framingIndex)),
});
byteBuffer = byteBuffer.subarray(framingIndex);
}
export const fromDeviceStream: () => TransformStream<Uint8Array, DeviceOutput> = (
// onReleaseEvent: SimpleEventDispatcher<boolean>,
) => {
let byteBuffer = new Uint8Array([]);
const textDecoder = new TextDecoder();
return new TransformStream<Uint8Array, DeviceOutput>({
transform(chunk: Uint8Array, controller): void {
// onReleaseEvent.subscribe(() => {
// controller.terminate();
// });
byteBuffer = new Uint8Array([...byteBuffer, ...chunk]);
let processingExhausted = false;
while (byteBuffer.length !== 0 && !processingExhausted) {
const framingIndex = byteBuffer.indexOf(0x94);
const framingByte2 = byteBuffer[framingIndex + 1];
if (framingByte2 === 0xc3) {
if (byteBuffer.subarray(0, framingIndex).length) {
controller.enqueue({
type: "debug",
data: textDecoder.decode(byteBuffer.subarray(0, framingIndex)),
});
byteBuffer = byteBuffer.subarray(framingIndex);
}
const msb = byteBuffer[2];
const lsb = byteBuffer[3];
const msb = byteBuffer[2];
const lsb = byteBuffer[3];
if (
msb !== undefined &&
lsb !== undefined &&
byteBuffer.length >= 4 + (msb << 8) + lsb
) {
const packet = byteBuffer.subarray(4, 4 + (msb << 8) + lsb);
if (msb !== undefined && lsb !== undefined && byteBuffer.length >= 4 + (msb << 8) + lsb) {
const packet = byteBuffer.subarray(4, 4 + (msb << 8) + lsb);
const malformedDetectorIndex = packet.indexOf(0x94);
if (
malformedDetectorIndex !== -1 &&
packet[malformedDetectorIndex + 1] === 0xc3
) {
console.warn(
`⚠️ Malformed packet found, discarding: ${byteBuffer
.subarray(0, malformedDetectorIndex - 1)
.toString()}`,
);
const malformedDetectorIndex = packet.indexOf(0x94);
if (malformedDetectorIndex !== -1 && packet[malformedDetectorIndex + 1] === 0xc3) {
console.warn(
`⚠️ Malformed packet found, discarding: ${byteBuffer
.subarray(0, malformedDetectorIndex - 1)
.toString()}`,
);
byteBuffer = byteBuffer.subarray(malformedDetectorIndex);
} else {
byteBuffer = byteBuffer.subarray(3 + (msb << 8) + lsb + 1);
controller.enqueue({
type: "packet",
data: packet,
});
}
byteBuffer = byteBuffer.subarray(malformedDetectorIndex);
} else {
/** Only partioal message in buffer, wait for the rest */
processingExhausted = true;
byteBuffer = byteBuffer.subarray(3 + (msb << 8) + lsb + 1);
controller.enqueue({
type: "packet",
data: packet,
});
}
} else {
/** Message not complete, only 1 byte in buffer */
/** Only partioal message in buffer, wait for the rest */
processingExhausted = true;
}
} else {
/** Message not complete, only 1 byte in buffer */
processingExhausted = true;
}
},
});
};
}
},
});
};
+9 -15
View File
@@ -1,18 +1,12 @@
/**
* Pads packets with appropriate framing information before writing to the output stream.
*/
export const toDeviceStream: () => TransformStream<Uint8Array, Uint8Array> =
() => {
return new TransformStream<Uint8Array, Uint8Array>({
transform(chunk: Uint8Array, controller): void {
const bufLen = chunk.length;
const header = new Uint8Array([
0x94,
0xc3,
(bufLen >> 8) & 0xff,
bufLen & 0xff,
]);
controller.enqueue(new Uint8Array([...header, ...chunk]));
},
});
};
export const toDeviceStream: () => TransformStream<Uint8Array, Uint8Array> = () => {
return new TransformStream<Uint8Array, Uint8Array>({
transform(chunk: Uint8Array, controller): void {
const bufLen = chunk.length;
const header = new Uint8Array([0x94, 0xc3, (bufLen >> 8) & 0xff, bufLen & 0xff]);
controller.enqueue(new Uint8Array([...header, ...chunk]));
},
});
};
+1 -5
View File
@@ -74,11 +74,7 @@ export class Xmodem {
this.rxBuffer[this.counter] = packet.buffer;
return this.sendCommand(Protobuf.Xmodem.XModem_Control.ACK);
}
return await this.sendCommand(
Protobuf.Xmodem.XModem_Control.NAK,
undefined,
packet.seq,
);
return await this.sendCommand(Protobuf.Xmodem.XModem_Control.NAK, undefined, packet.seq);
}
case Protobuf.Xmodem.XModem_Control.STX: {
break;