rs2322tcp/internal/gui/assignment.go
2026-08-11 12:51:17 +02:00

167 lines
5 KiB
Go

/*
* ============================================================================
* Projekt.....: rs2322tcp
* Datei.......: internal/gui/assignment.go
* Copyright (C) 2026 Dieter Lang
*
* SPDX-License-Identifier: GPL-3.0-or-later
*
* Beschreibung:
* GUI-unabhängige Aufbereitung der Zuordnung zwischen lokalen virtuellen
* seriellen Schnittstellen und den vom rs2322tcp-Server angebotenen Geräten.
*
* Die Datei enthält bewusst keine Fyne-Abhängigkeiten.
*
* Die lokale Client-Konfiguration beschreibt ausschließlich die tatsächlich
* gewünschten Verbindungen. Physisch vorhandene /dev/ttyUSB-Schnittstellen
* außerhalb des von rs2322tcp verwalteten virtuellen Bereichs werden hier
* nicht betrachtet.
*
* Ein Server-Gerät kann daher in drei Zuständen erscheinen:
*
* 1. lokal zugeordnet und aktuell vom Server angeboten
* -> verfügbar / verbunden
*
* 2. lokal zugeordnet, aber momentan nicht vom Server angeboten
* -> nicht verfügbar
*
* 3. vom Server angeboten, aber keiner lokalen Schnittstelle zugeordnet
* -> noch nicht verwendet
*
* Nicht verwendete Server-Geräte werden nicht Bestandteil der
* Client-Konfiguration.
* ============================================================================
*/
package gui
import (
"git.lang-dieter.de/rs2322tcp/internal/config"
"git.lang-dieter.de/rs2322tcp/internal/transport"
)
///////////////////////////////////////////////////////////////////////////////
// Device assignment
///////////////////////////////////////////////////////////////////////////////
// DeviceAssignment beschreibt eine bereits in der Client-Konfiguration
// vorhandene Zuordnung zwischen einer lokalen virtuellen Schnittstelle
// und einem entfernten Gerät.
//
// Available gibt an, ob das konfigurierte Remote-Gerät momentan in der
// vom Server gelieferten Geräteliste vorhanden ist.
//
// Available == false bedeutet nicht, dass die Konfiguration ungültig ist.
// Das Gerät kann lediglich momentan nicht vom Server angeboten werden.
type DeviceAssignment struct {
LocalPort string
RemoteDevice string
Available bool
}
///////////////////////////////////////////////////////////////////////////////
// Build assignments
///////////////////////////////////////////////////////////////////////////////
// BuildAssignments erzeugt die Zuordnungsansicht aus der bestehenden
// Client-Konfiguration und der aktuell vom Server gelieferten Geräteliste.
//
// Es werden ausschließlich die in der Client-Konfiguration vorhandenen
// lokalen virtuellen Ports berücksichtigt.
//
// Physisch vorhandene serielle Schnittstellen des lokalen Rechners werden
// hier nicht gesucht und nicht bewertet.
func BuildAssignments(
cfg *config.ClientConfig,
devices []transport.RemoteDeviceInfo,
) []DeviceAssignment {
if cfg == nil {
return nil
}
assignments := make([]DeviceAssignment, 0, len(cfg.VirtualPorts))
for _, virtualPort := range cfg.VirtualPorts {
assignments = append(assignments, DeviceAssignment{
LocalPort: virtualPort.Port,
RemoteDevice: virtualPort.RemoteDevice,
Available: remoteDeviceExists(
virtualPort.RemoteDevice,
devices,
),
})
}
return assignments
}
///////////////////////////////////////////////////////////////////////////////
// Unassigned devices
///////////////////////////////////////////////////////////////////////////////
// UnassignedDevices liefert die vom Server angebotenen Geräte, die aktuell
// keiner lokalen virtuellen Schnittstelle zugeordnet sind.
//
// Diese Geräte werden bewusst nicht in die Client-Konfiguration übernommen.
// Erst wenn der Anwender im GUI eine Zuordnung vornimmt, entsteht daraus
// ein Eintrag in ClientConfig.VirtualPorts.
func UnassignedDevices(
cfg *config.ClientConfig,
devices []transport.RemoteDeviceInfo,
) []transport.RemoteDeviceInfo {
assigned := assignedRemoteDevices(cfg)
unassigned := make([]transport.RemoteDeviceInfo, 0)
for _, device := range devices {
if assigned[device.ID] {
continue
}
unassigned = append(unassigned, device)
}
return unassigned
}
///////////////////////////////////////////////////////////////////////////////
// Internal helpers
///////////////////////////////////////////////////////////////////////////////
// assignedRemoteDevices erzeugt eine Menge der Remote-Geräte, die bereits
// einer lokalen virtuellen Schnittstelle zugeordnet sind.
//
// Die Remote-Device-ID ist der stabile Schlüssel der Zuordnung.
func assignedRemoteDevices(
cfg *config.ClientConfig,
) map[string]bool {
assigned := make(map[string]bool)
if cfg == nil {
return assigned
}
for _, virtualPort := range cfg.VirtualPorts {
if virtualPort.RemoteDevice == "" {
continue
}
assigned[virtualPort.RemoteDevice] = true
}
return assigned
}
// remoteDeviceExists prüft, ob ein Remote-Gerät mit der angegebenen ID in
// der aktuellen Geräteliste des Servers vorhanden ist.
func remoteDeviceExists(
id string,
devices []transport.RemoteDeviceInfo,
) bool {
for _, device := range devices {
if device.ID == id {
return true
}
}
return false
}