# Komplette Erklärung: ESB Certificate Manager Was passiert – **einzeln, von oben nach unten**. Zertifikat prüfen · Ziele laden · Sonic-API · Container-Neustart. Diese Datei ist zum Erklären (Präsentation, Kollegen, Übergabe). Technischer Fokus: aktueller Stand mit **MfApi-Neustart** und **lokaler Zertifikatserkennung**. --- # Teil A – Was die Anwendung ist ## A1. Zweck in einem Satz Die WinForms-App hilft dabei, 1. ein **Zertifikat als Datei zu erkennen und lokal zu prüfen**, und 2. einen **Sonic-/ESB-Container remote neu zu starten** – so ähnlich wie der Restart-Button in der **Sonic Management Console (SMC)**. ## A2. Was sie bewusst *nicht* macht (aktuell) | Nicht aktiv | Erklärung | |-------------|-----------| | Zertifikat auf den Server **kopieren** | Deploy-Button ist ausgeblendet | | Nach dem Deploy **TLS gegen den Endpoint prüfen** | früher TLS-Probe – entfernt/deaktiviert | | **XApi** importieren | nicht mehr im Pfad | | Neustart per **`stopcontainer.bat`** | oft in SMC-only-Installationen nicht vorhanden | | Neustart per **WinRM / Windows-Login** | SMC-User ≠ Windows-User | | Eigene **HTTP-REST-API** der App | die App *ist* kein Server; sie *ruft* Sonic auf | ## A3. Die wichtigsten Namen in eurer Umgebung | Name | Typ | Beispiel | |------|-----|----------| | Verbindungs-Alias | Eintrag in `appsettings` | `DE-Test` | | Domain | Sonic-Domain | `proalpha-test` | | Container (kurz) | Laufzeit-Container | `ct-ZADBService` | | ObjectName (JMX) | vollständige Agent-Adresse | `proalpha-test.ct-ZADBService:ID=AGENT` | | ConnectionUrl | Domain-Manager wie in SMC | `tcp://dekun-painwbdet:13070` | | Login | SMC-Credentials | `Administrator` / `Administrator` | | Sonic-Libs | Client-JARs | `C:\DEV\MQ10.0\lib` | | Java | Runtime für das Hilfstool | JRE 1.8+ | **Merksatz:** `DE-Test` = Verbindung. `ct-ZADBService` = Container. Nicht vertauschen. --- # Teil B – Programmstart (was zuerst passiert) ## B1. Start der App 1. `Program.cs` startet `Form1`. 2. `AppSettingsLoader` liest `appsettings.json` (aus dem Output-Ordner der App). 3. Es werden gebaut: - `DeploymentOrchestrator` (Neustart-Orchestrierung) - `SonicContainerDiscovery` (Container-Liste optional laden) 4. Die UI (Dark-Design) wird aufgebaut. 5. Beim ersten Anzeigen (`Shown`) werden Ziele geladen. ## B2. Ziele laden 1. Ziele kommen aus `appsettings.json` → `SonicConnections[].KnownContainers` (kein Offline-JSON). 2. Jede Zeile hat u. a.: - Anzeigename (`DE-Test / ct-ZADBService`) - Umgebung = Domain - **ContainerName** (z. B. `ct-ZADBService`) - **SonicConnectionName** (z. B. `DE-Test`) - Status-Spalte Optional: Button **„Container laden“** fragt Sonic live per API und merged mit `KnownContainers`. --- # Teil C – Zertifikat: Erkennen & Verifizieren (Schritt für Schritt) Hier geht es **nur um die lokale Datei**. Es wird nichts auf den ESB geschrieben und kein TLS zum Server aufgebaut. ## C1. Benutzer wählt Datei 1. Klick auf Dateiauswahl in der UI. 2. `OpenFileDialog` filtert: `.cer`, `.crt`, `.pem`, `.pfx`. 3. Abbruch → nichts ändert sich. 4. Dateiendung wird geprüft (`IsSupportedCertificateFile`). 5. Unbekanntes Format → Warnung, Ende. ## C2. Datei lesen 1. Aufruf `TryReadSelectedCertificate(pfad)`. 2. Intern: `X509Certificate2` laden. 3. **PFX-Sonderfall:** - Zuerst Versuch *ohne* Passwort. - Bei `CryptographicException` → Passwort-Dialog. - Falsches Passwort → Fehlermeldung, kein Zertifikat geladen. 4. Andere Fehler (Datei kaputt, kein X.509) → Fehlermeldung. ## C3. Was aus dem Zertifikat extrahiert wird | Feld | Quelle | Anzeige | |------|--------|---------| | Subject | `GetNameInfo(SimpleName)` bzw. `Subject` | „Ausgestellt für“ | | Issuer | Issuer-SimpleName bzw. `Issuer` | „Ausgestellt von“ | | Gültig von / bis | `NotBefore` / `NotAfter` | Datum | | Fingerprint | SHA-256 Hash, mit `:` formatiert | z. B. `AB:CD:…` | | Gültigkeitsstatus | `now` zwischen NotBefore und NotAfter? | grün GÜLTIG / rot UNGÜLTIG | ## C4. Was „Verifizierung“ hier genau heißt | Prüfung | Passiert? | Bedeutung | |---------|-----------|-----------| | Datei lesbar als X.509 | ja | Format/Inhalt ok | | Zeitlich gültig | ja | nicht abgelaufen / noch nicht gültig | | Fingerprint anzeigen | ja | manueller Abgleich möglich | | Signaturkette gegen Windows-CA | **nein** | nicht implementiert | | Datei auf ESB kopieren | **nein** | Deploy aus | | TLS-Handshake zum Live-System + Fingerprint vergleichen | **nein** | TLS-Probe aus | **Erklärsatz:** > Wir verifizieren das Zertifikat **als Datei auf dem PC** (lesbar + Gültigkeitszeitraum + Fingerprint). > Wir verifizieren **nicht**, dass genau dieses Zertifikat schon am laufenden ESB hängt. > Der Neustart ist davon getrennt. ## C5. UI nach erfolgreichem Laden 1. Pfad steht im Textfeld. 2. Metadaten-Karte wird gefüllt. 3. Statuszeile: „Zertifikat ausgewählt: …“. 4. Sidebar-Schritt kann auf „Ziele“ springen. 5. Neustart braucht das Zertifikat **nicht zwingend** – der Neustart hängt am Container, nicht an der Datei. --- # Teil D – Vor dem Neustart (Preflight) ## D1. Benutzer hakt Ziel(e) an Im Grid: Checkbox „Selected“ setzen. ## D2. Button „ESB neu starten“ 1. `GetSelectedTargets()` sammelt alle angehakten Zeilen. 2. `ValidateRestartOnly` prüft für jedes Ziel: - `ContainerName` nicht leer - `SonicConnectionName` nicht leer 3. Fehler → Dialog „Neustart blockiert“ mit Liste der Probleme. 4. OK → Bestätigungsdialog (Containername, Hinweis auf Management API). 5. Nein → Abbruch. Ja → Neustart startet. --- # Teil E – Neustart Gesamtablauf (C#-Seite) Alles von hier läuft **ohne** Zertifikatskopieren. ```text Form1.RunRestartOnlyAsync → DeploymentOrchestrator.RestartOnlyAsync → für jedes Ziel: RestartExecutor.ExecuteAsync → SonicManagementClient.RestartContainerAsync → SonicMfApiExecutor.RestartAsync → java SonicMfContainerTool restart … ``` ## E1. Orchestrator Pro Ziel: 1. Status im Grid: „Neustart…“ 2. `RestartExecutor.ExecuteAsync(target)` 3. Ergebnis + Detail in Logdatei unter `Logs\` 4. Status im Grid aktualisieren 5. Am Ende: Erfolgs-/Fehlerdialog mit Tool-Ausgabe ## E2. RestartExecutor 1. Liest `target.ContainerName` (z. B. `ct-ZADBService`). 2. Sucht in `appsettings` die `SonicConnection` mit `Name == SonicConnectionName` (`DE-Test`). 3. Fehlt die Verbindung → Fehler „Sonic-Verbindung nicht gefunden“. 4. Sonst: `new SonicManagementClient(connection)` und `RestartContainerAsync(containerName)`. ## E3. SonicManagementClient Schlanke Fassade, nur MfApi: 1. Ruft `_mfApi.RestartAsync(containerName)` auf. 2. Bei Erfolg: wartet `PostRestartDelaySeconds` (z. B. 20 s), damit der Container Zeit zum Hochfahren hat. 3. Liefert Status-Text + komplette Java-Ausgabe zurück. 4. Bei Fehler: Fehlermeldung + Output für den Dialog. --- # Teil F – SonicMfApiExecutor: Java vorbereiten und starten Das ist die Brücke von .NET zu Sonic. ## F1. Java finden Reihenfolge grob: 1. `JavaPath` aus appsettings (bevorzugt) 2. `JavaHome` 3. Umgebungsvariablen / PATH / Registry / unter SonicHome Bedingung: Runtime muss **Java 8+** können (Class-File major ≥ 52). Zu alte Sonic-JREs (6/7) werden übersprungen. ## F2. Classpath bauen (Sonic-JARs) 1. `MfClientLibPath` (z. B. `C:\DEV\MQ10.0\lib`) oder Suche unter `SonicHome`. 2. Es müssen echte Client-JARs da sein, u. a.: - `mgmt_client.jar` - `mfcontext.jar` - `sonic_Client.jar` 3. **Alle** `*.jar` im Lib-Ordner werden explizit in den Classpath geschrieben (kein fragiles `lib\*` mit kaputten Quotes). 4. Das Tool-Verzeichnis `Tools\` kommt **vorne** in den Classpath, damit die richtige `SonicMfContainerTool.class` geladen wird. ## F3. Java-Tool laden 1. Bevorzugt vorcompilierte `Tools\SonicMfContainerTool.class` (Java 8, major 52). 2. Alte/zu kleine Class-Dateien werden verworfen. 3. Temp-Cache alter Compilate wird gelöscht. 4. Falls nötig: aus `.java` mit `javac --release 8` neu bauen. ## F4. Prozess starten Ungefähr: ```text "C:\...\java.exe" -cp "C:\...\Tools;C:\DEV\MQ10.0\lib\mgmt_client.jar;...;C:\DEV\MQ10.0\lib\mfcontext.jar;..." SonicMfContainerTool restart --domain proalpha-test --url tcp://dekun-painwbdet:13070 --user Administrator --container ct-ZADBService --timeout 120 ``` Wichtig: - Argumente über `ProcessStartInfo.ArgumentList` (keine doppelten Anführungszeichen). - Passwort über Umgebung `ESB_SONIC_PASSWORD`, nicht in der sichtbaren Kommandozeile. - stdout/stderr werden gelesen und an die UI zurückgegeben. ## F5. Erfolgsauswertung in C# Neustart gilt nur als Erfolg, wenn die Ausgabe enthält: ```text OK:RestartInvoked ``` Sonst: Fehlerdialog mit kompletter Tool-Ausgabe. --- # Teil G – Die Sonic Management Application API (Java-Tool) Hier passiert der eigentliche „API-Call“ – **nicht REST**, sondern **JMS/JMX Management Framework**. Offizielle Produktwelt (Aurea CX Messenger / Sonic): - Index: `doc-10.0.10/CXMessenger_2017_R3.htm` - Eintrag: **Management Application API Reference** (`Docs2017/api/mgmt_api/`) Das ist dieselbe API-Familie, die die SMC für Restart nutzt. ## G1. Warum „API“ hier kompliziert klingt Die Sonic-Produkt-API enthält **sehr viele** Bereiche: - Broker / Queues / Topics - ESB-Services - Metrics / Notifications - Directory / Config - Agent Lifecycle **Für unseren Neustart brauchen wir nur einen schmalen Teil:** 1. Verbinden zum Domain Manager 2. Agent-ObjectName ansprechen 3. Lifecycle: stop/restart Der Rest der JARs ist Produktumfang – nicht „unsere App-API mit 100 Features“. ## G2. Schritt 1 – Tool startet Ausgabe: ```text INFO:ToolVersion=2026-07-24c-mbean-stop ``` Wenn diese Zeile fehlt → oft noch eine **alte** `.class` im Einsatz. ## G3. Schritt 2 – Argumente parsen Pflicht: - Befehl: `ping` | `list` | `restart` - `--domain` - `--url` - `--user` - bei `restart`: `--container` - Passwort: `--password` oder `ESB_SONIC_PASSWORD` ## G4. Schritt 3 – Connect (der eigentliche API-Login) Java (vereinfacht, per Reflection): ```text Hashtable env: ConnectionURLs = tcp://dekun-painwbdet:13070 DefaultUser = Administrator DefaultPassword = *** JMSConnectorAddress address = new JMSConnectorAddress(env) JMSConnectorClient connector = new JMSConnectorClient() connector.connect(address, timeout) ``` Klassen kommen aus den Sonic-JARs: - `com.sonicsw.mf.jmx.client.JMSConnectorAddress` - `com.sonicsw.mf.jmx.client.JMSConnectorClient` Ausgabe bei Erfolg: ```text INFO:Connected url=tcp://dekun-painwbdet:13070 user=Administrator ``` Das entspricht dem SMC-Login gegen denselben Domain Manager. ## G5. Schritt 4 – Ziel-Agent bestimmen ObjectName: ```text proalpha-test.ct-ZADBService:ID=AGENT ``` Muster: ```text {DomainName}.{ContainerName}:ID=AGENT ``` Optional: per `queryNames` nach vorhandenen Agenten suchen; wenn das scheitert, Preferred-Name verwenden. ## G6. Schritt 5 – Lifecycle (Neustart) – drei Wege nacheinander ### Weg 1 – MBean invoke (bevorzugt remote) ```text connector.invoke(objectName, "stop", [], []) // oder "restart", "shutdown" ``` Warum zuerst `stop`? - Remote-Clients sind oft **„unbounded“**. - `IAgentProxy.restart()` wirft dann häufig: `Operation unsupported for unbounded client connector` - SMC-Restart wirkt für den Operator oft wie: **Stop + automatischer Relaunch** durch Launch Daemon / Host Manager. Erfolg: ```text OK:RestartInvoked method=MBean.stop container=ct-ZADBService domain=proalpha-test ``` ### Weg 2 – Typisierter Proxy ```text IAgentProxy agent = MFProxyFactory.createAgentProxy(connector, objectName) agent.stop() / agent.restart() / agent.shutdown() ``` Schön dokumentiert, remote oft eingeschränkt (unbounded). ### Weg 3 – DomainManager / Manager-MBeans Suche nach Operationen wie: - `restartContainer(containerName)` - `stopContainer(containerName)` Fallback, falls Agent-direkt nicht klappt. ## G7. Schritt 6 – Disconnect `connector.disconnect()` im `finally`. ## G8. Befehle des Tools im Überblick | Befehl | Zweck | |--------|--------| | `ping` | Verbindungstest + Agenten zählen | | `list` | Containernamen der Domain ausgeben | | `restart` | Lifecycle auf einem Container | --- # Teil H – Komplette Kette als nummerierte Liste So kannst du es jemandem erzählen: ### Zertifikat 1. App starten 2. Zertifikatsdatei wählen 3. Datei als X.509 lesen (PFX ggf. mit Passwort) 4. Subject, Issuer, Fingerprint, Gültigkeit anzeigen 5. Lokal „verifiziert“ = lesbar + im Gültigkeitszeitraum ### Neustart 6. Ziel im Grid anhaken (`ct-ZADBService` / Verbindung `DE-Test`) 7. „ESB neu starten“ → Preflight → Bestätigung 8. C# findet Sonic-Verbindung in appsettings 9. C# findet Java 8+ und baut Classpath aus `C:\DEV\MQ10.0\lib` 10. C# startet `SonicMfContainerTool restart …` 11. Java verbindet per Management API an `tcp://…:13070` 12. Java adressiert `proalpha-test.ct-ZADBService:ID=AGENT` 13. Java ruft Stop/Restart per MBean (Fallback Proxy/Manager) 14. Java schreibt `OK:RestartInvoked` 15. C# wartet `PostRestartDelaySeconds` 16. UI zeigt Erfolg/Fehler + Logausgabe 17. Optional in SMC prüfen: Uptime/Status des Containers --- # Teil I – Konfiguration im Detail ## I1. `appsettings.json` (Sonic-Block) | Feld | Rolle | |------|--------| | `Name` | Alias, von Zielen referenziert (`DE-Test`) | | `DomainName` | Sonic-Domain | | `ConnectionUrl` | Domain-Manager-URL (wie SMC) | | `Username` / `Password` | SMC-Login | | `SonicHome` | Installationsroot | | `MfClientLibPath` | Ordner mit Client-JARs | | `JavaPath` / `JavaHome` | Java 8+ | | `KnownContainers` | Fallback-Liste, z. B. `ct-ZADBService` | | `TimeoutSeconds` | Timeout Java/API | | `PostRestartDelaySeconds` | Wartezeit nach erfolgreichem Invoke | Felder wie `WinRm*`, `Container*Path`, `ManagementHttpPort` können noch in der JSON stehen, werden vom schlanken MfApi-Client **nicht mehr genutzt**. ## I2. Container-Liste Kein separates Sample-JSON. Container stehen in: ```json "KnownContainers": [ "ct-ZADBService" ] ``` Live-Erweiterung über UI-Button „Container laden“. --- # Teil J – Dateien und Verantwortlichkeiten | Datei | Verantwortung | |-------|----------------| | `Form1.cs` | UI, Zertifikat lesen, Neustart-Button, Dialoge | | `DeploymentOrchestrator.cs` | Neustart über alle gewählten Ziele | | `PreflightValidator.cs` | Pflichtfelder prüfen | | `RestartExecutor.cs` | Ziel → SonicConnection | | `SonicManagementClient.cs` | Fassade MfApi | | `SonicMfApiExecutor.cs` | Java/Classpath/Prozess | | `Tools/SonicMfContainerTool.java` | Connect + Lifecycle über Sonic-API | | `appsettings.json` | Laufzeitkonfiguration inkl. KnownContainers | | `Logs\` | Laufprotokolle | --- # Teil K – Erfolgs- und Fehlerbilder ## K1. Gesunde Ausgabe (Auszug) ```text INFO:ToolVersion=2026-07-24c-mbean-stop INFO:Connected url=tcp://dekun-painwbdet:13070 user=Administrator INFO:PreferredObjectName=proalpha-test.ct-ZADBService:ID=AGENT INFO:Trying MBean.invoke(stop) on … OK:RestartInvoked method=MBean.stop container=ct-ZADBService domain=proalpha-test ``` ## K2. Häufige Fehler | Meldung | Bedeutung | Typische Lösung | |---------|-----------|-----------------| | `ClassNotFoundException: JMSConnectorAddress` | JARs fehlen / Classpath kaputt | `MfClientLibPath`, neuer Build | | `UnsupportedClassVersionError` | Java-Version mismatch | Tool als Java 8 + Runtime Java 8+ | | `Operation unsupported for unbounded…` | Proxy-Restart remote gesperrt | MBean-stop-Pfad / aktuelles Tool | | Kein `ToolVersion=` | Alte Class-Datei | Neu bauen, richtigen bin-Ordner starten | | Container `DE-Test` | Alias statt Kurzname | `ct-ZADBService` | | `stopcontainer.bat` fehlt | SMC-only | normal – MfApi nutzen | --- # Teil L – Wie man es jemandem erklärt (Kurzskript) 1. **UI:** Zertifikat laden → wir sehen Subject/Fingerprint/Gültigkeit. Das ist lokale Dateiprüfung. 2. **Neustart:** Wir starten denselben Management-Weg wie die SMC, nicht per Batch-Datei und nicht per FTP. 3. **Technik:** C# orchestriert; ein kleines Java-Tool + Sonic-Client-JARs sprechen mit dem Domain Manager. 4. **API:** Sonic Management Application API (JMS/JMX). Sehr große Produkt-API, wir nutzen nur Connect + Agent-Stop/Restart. 5. **Haken:** Remote heißt „unbounded“ – deshalb oft `stop` per MBean statt `IAgentProxy.restart()`. 6. **Ergebnis:** Container `ct-ZADBService` in Domain `proalpha-test` wird neu gestartet; danach in der SMC Status/Uptime prüfen. --- # Teil M – Abgrenzung: Was ist „unsere API“ vs. Sonic-API? | Ebene | Beschreibung | |-------|--------------| | **Unsere App** | WinForms + C#-Services. Kein öffentlicher REST-Endpoint. | | **Unser Java-Tool** | Dünner Adapter (`ping`/`list`/`restart`) mit Fallbacks. | | **Sonic Management Application API** | Produkt-API in den JARs; offiziell dokumentiert; SMC nutzt dieselbe Familie. | | **Unnötig für den Use-Case** | MQ Messaging API, ESB API, Metrics, XApi, WinRM, Bat-Scripts, TLS-Probe – solange nur „Datei prüfen + Neustart“ gefragt ist. | --- *Ende der kompletten Erklärung. Bei Abweichungen gilt der Code im Projekt (Branch mit MfApi-Neustart).*