CompanyFlex Re-Registrierung Gespräche brechen ab.

ANHU

Bronze Partner
Mitglied seit
20. Januar 2025
Beiträge
4
Hallo Zusammen,

Wir haben einen SIP Trunk Telekom CompanyFlex VoiceData Konfiguriert und seit einiger Zeit, brechen die Gespräche ab. Die 3CX hängt direkt hinter dem DTAG Anschluss mit statischer IP.
Wie ich festgestellt habe, schickt die Telekom bei einer fehlerhaften Authorization bzw. wenn keine mitgeschickt wird, ein TCP RST, dabei brechen die Gespräche ab.

So wie ich das verstanden habe laut: https://www.3cx.com/docs/sip-trunk-registration-authentication
Wird zuerst die Registration ohne Authorization versucht, und es kommt ein 407 Proxy Authentication Required” or “401 Unauthorized versucht anschließend die 3CX die Registration mit Authorization, die dann auch funktioniert. Leider brechen wie gesagt zuvor die Gespräche ab, da die Telekom ein TCP RST sendet falls keine Authorization mitgeliefert wird.

Hat hierzu jemand eine Idee? Bzw. ist es mögliche die 3CX anzuweisen immer die Auth mitzugeben?

Die Version der 3CX ist die aktuelle V20. Anfangs lag der Verdacht auf der PFSense Firewall, um das auszuschließen habe ich die 3CX direkt hinter einen HPE MSR3044 Router gehängt, dieser macht auch die PPPoE Einwahl.

Vielen Dank
Andreas Huser
 

Anhänge

  • Bildschirmfoto_20250120_094613.png
    Bildschirmfoto_20250120_094613.png
    128 KB · Aufrufe: 12
So wie ich das verstanden habe laut: https://www.3cx.com/docs/sip-trunk-registration-authentication
Wird zuerst die Registration ohne Authorization versucht, und es kommt ein 407 Proxy Authentication Required” or “401 Unauthorized versucht anschließend die 3CX die Registration mit Authorization, die dann auch funktioniert.
Das ist das übliche Verfahren: VOIP Registrierung per HTTP Digest Access Authentication. Du hast die richtige Beschreibung ja schon gefunden. Weiteres steht in der RFC8760 und RFC7616. Client und Sender handeln so die Verschlüsselung aus. In der ersten Abweisung (407) sendet der Server (T-Com) als challenge request überhaupt erst das nonce mit dem der Anfrager (die 3CX) ihre Authenthifizierung verschlüsselt übertragen kann. Dann kommt die Antwort mit Statuscode 200 und alles ist gut für die nächsten 240 Sekunden.

Leider brechen wie gesagt zuvor die Gespräche ab, da die Telekom ein TCP RST sendet falls keine Authorization mitgeliefert wird.
Mit der zweiten Anfrage von der 3CX (mit per nonce verschl. Anmeldedaten) sollte die Authentifizierung immer erfolgreich verlaufen (HTTP Statuscode 200). Dabei dürfen Gespräche auch nicht abgebrochen werden. Passiert das nachweislich?
Bzw. ist es mögliche die 3CX anzuweisen immer die Auth mitzugeben?
s.o., das muss so sein, das geht rein technisch gar nicht anders
Anfangs lag der Verdacht auf der PFSense Firewall
Da gibt es von 3CX eine sehr genaue Anleitung für die Einrichtung. Die könnte auch von uns sein:
https://www.3cx.de/docs/pfsense-firewall
Prinzipiell genau so richten wir alle unsere pfSense schon immer ein (wobei wir nach erfolgreichem Firewall Test den SIP Port für alle Quellen außer dem Provider sperren und kein Hairpin NAT benutzen).

Fazit: dein Problem ist ein klein wenig anders.

  1. Lassen sich die Abbrüche reproduzieren?
  2. Treten die Abrüche vielleicht ausschließlich bei einem 401 Fehler auf? Das wäre vielleicht sogar i.O..
  3. Trat das Problem erst mit dem Upgrade auf v20 auf?
  4. Wurde der SIP Trunk schon einmal testweise neu angelegt (den jetzigen Trunk dafür deaktivieren indem die Registrierung z.B. auf localhost erfolgt)?
  5. Welche DNS Server verwendet die 3CX?
 
Zuletzt bearbeitet:
Vielen Dank für deine ausführliche und gute Antwort!

Mit dem SIP Auth Mechanismus, habe ich mich bislang noch nicht befasst, wir nutzen 3CX aktuell nur intern.
Vor einigen Wochen hat es noch funktioniert, welcher Softwarestand das war kann ich allerdings nicht mehr sagen.

Der Firewall Test zeigt OK. Die PFSense sollte richtig Konfiguriert gewesen sein. Das mit den Quellen hatte ich über die Aliase denke ich mal ähnlich geregelt.

Wie gesagt, hängt die PFSense nicht mehr dazwischen. Die 3CX hängt direkt am Router, der auch die Einwahl macht. Damit wollte ich einen möglichen Fehler der PFSense ausschließen. Auf dem MSR Router ist lediglich ein Port Forwarding und ein no-pat konfiguriert. Auch hier zeigt der Firewall-Test von der 3CX ein "Bestanden".

Den Trunk habe ich bereits gelöscht und neu Konfiguriert, sowie auch in der Benutzereinstellung SRTP varianten versucht. Alles ohne erfolg.

Die 3CX bekommt via DHCP die DNS von der Telekom (PPPoE):
nameserver 217.237.150.51
nameserver 217.237.148.22

Ja es ist reproduzierbar:
- Telefonat zwischen 3CX und Mobiltelefon.
Nach einiger Zeit bekommt das Mobiltelefon ein Abbruch, dass geschieht zeitgleich mit dem Request Register und dem darauffolgendem RST. Die RTP Verbindung seitens 3CX Telefon bleibt jedoch bestehen, man hört lediglich nichts mehr von der Gegenstelle (Mobiltelefon). Hierzu habe ich auch mal die Sprachübertragung auf die 3CX umgestellt und via tcpdump beobachtet. Der RTP Stream läuft munter weiter.

Anbei ein Screenshot:
Die 3CX baut mit der IPA 217.0.149.240 die Verbindung auf. Nach 7m 5s initialisiert die 3CX erneut den Request Register zur gleichen IPA 217.0.149.240, die wiederum ein RST sendet. Damit bricht die Verbindung einseitig ab. Der darauffolgende Request Register, wird dann an eine andere IPA gesendet, in dem Fall die 217.0.149.16. Dieser funktioniert dann.

- Die Zeiten der Abbrüche sind unterschiedlich und liegen zwischen 6 und 10 min. Request Register ist hier ausschlaggebend
- Die IPAs der Telekom variieren beim Verbindungsaufbau, es ist also nicht spezifisch auf eine IPA zurückzuführen
- Der RST kommt immer direkt nach dem Request Register

Was ich mir noch vorstellen könnte, ist die Expires Time von 600sec. Diese ist auch im 3CX Provider Template hinterlegt und die Telekom gibt im 1TR119 ein maximum von 600 vor. Eventuell ist das zu knapp und die DTAG schickt nach dem erreichen vom dem maximum ein RST.

Gibt es vielleicht eine Möglichkeit die Expires Time in der 3CX herunter zu schrauben um diese Theorie zu testen?
 

Anhänge

  • Bildschirmfoto_20250120_171708_1.png
    Bildschirmfoto_20250120_171708_1.png
    191,1 KB · Aufrufe: 4
Gibt es vielleicht eine Möglichkeit die Expires Time in der 3CX herunter zu schrauben um diese Theorie zu testen?
Nicht in der normalen 3CX Verwaltung. Entweder per API setzen, direkt im Trunk im Dateisystem ändern oder den Trunk exportieren, anpassen und wieder einspielen.

Was für ein Template wurde denn verwendet?
 
Problem gelöst, es ist tatsächlich die Expires Time von 600.

Kommt das "Register Request" nur einen Bruchteil nach dem vorgegebenen maximum von 600 Sekunden der Telekom an, dann schickt die Telekom als Antwort ein RST Paket. Dei Vorgabe von 600 Sekunden im Template der 3CX ist also zu knapp und, kann sich daher leicht überscheiden.

Ich bin jetzt folgend vorgegangen:
  1. Export des SIP Trunks und anschließendes Löschen
  2. Über Erweitert > Vorlagen > Provider Vorlagen, habe mir dort aus dem XML Template Deutsche Telekom (CompanyFlex - VoiceData) den parameter <field name="TimeBetweenRegistration">600</field> kopiert
  3. Diesen habe ich in den exportieren SIP Trunk eingefügt und mit dem wert 300 versehen.
  4. Den SIP Trunk wieder importieren und fertig Konfigurieren
Ich habe anschließend rund 20min mit mir selbst Telefoniert ohne RST und Verbindungsabbruch. Siehe Anhang.
 

Anhänge

  • Bildschirmfoto_20250120_190650_2.png
    Bildschirmfoto_20250120_190650_2.png
    382,4 KB · Aufrufe: 8
  • Like
Reaktionen: Grundguetiger
Nicht in der normalen 3CX Verwaltung. Entweder per API setzen, direkt im Trunk im Dateisystem ändern oder den Trunk exportieren, anpassen und wieder einspielen.

Was für ein Template wurde denn verwendet?
CompanyFlex - VoiceData

Wo finde ich denn im Dateisystem die Config vom Trunk?
 
CompanyFlex - VoiceData

Wo finde ich denn im Dateisystem die Config vom Trunk?
/var/lib/3cxpbx/Instance1/Data/Http/Templates/provider/telekomcompanyflexvoicedata.pv.xml

Aber ich würde das im Trunk direkt und live ändern, z.B. mittels REST API und Powershell.

3cx-powershell-xapi-set-sip-trunk-reregtime.ps1

Code:
$tcxurl="mypbx.mydomain.de"     # needs port if not 443

$jsonauthbody = (@{
    Username="988"              # 3CX user, maybe email address
    Password="Super_Secret0815" # 3CX user password
    SecurityCode=""
} | ConvertTo-Json)

Add-Type -AssemblyName Microsoft.VisualBasic

$LoginResponse = Invoke-RestMethod -Uri "https://$tcxurl/webclient/api/Login/GetAccessToken" -Body $jsonauthbody -Method POST -ContentType "application/json"

if( $LoginResponse.Status -ne "AuthSuccess" ) {
    Write-Host "abort: authentication not successful"
    exit -1
}

$headers = @{Authorization = "Bearer $($LoginResponse.Token.access_token)"}

$uri="https://$tcxurl/xapi/v1/Trunks"
$tcxtrunks=(Invoke-RestMethod -uri $uri -headers $headers -Method GET -ContentType "application/json").Value

Write-Host "found SIP trunks:"
Foreach( $tcxtrunk in $tcxtrunks) {
    Write-Host "trunk ID:  $($tcxtrunk.Id)       name:  $($tcxtrunk.Gateway.Name)"
}

$msg   = 'enter trunk ID to change TimeBetweenReg or enter 0 to leave'
$tcxtid = [Microsoft.VisualBasic.Interaction]::InputBox($msg, 'get trunk ID')
$msg   = 'enter seconds for trunk value TimeBetweenReg or enter 0 to leave'
$tcxret = [Microsoft.VisualBasic.Interaction]::InputBox($msg, 'get TimeBetweenReg time')


If( ($tcxtid -ne 0) -and  ($tcxtid.Length -ne 0) -and ($tcxret -ne 0) -and  ($tcxret.Length -ne 0)) {
    Write-Host "for the SIP trunk with ID  $($tcxtrunk.Id)  and name $($tcxtrunk.Gateway.Name) change the TimeBetweenReg to $tcxret"
    $uri="https://$tcxurl/xapi/v1/Trunks($tcxtid)"
    $tcxtbodyjson=@{Gateway=@{TimeBetweenReg=$tcxret}} | ConvertTo-Json
    Invoke-RestMethod -uri $uri -headers $headers -Method PATCH -body $tcxtbodyjson -ContentType "application/json"
    # show all trunk values
    Invoke-RestMethod -uri $uri -headers $headers -Method GET -ContentType "application/json"
}

... und erzähle mir bitte nicht, du hast nur Macs und nirgends Powershell zur Verfügung ...
 
Zuletzt bearbeitet:
  • Like
Reaktionen: fxbastler
  • Like
Reaktionen: mbehrens
Hi zusammen,
hi fxbastler,

erstmal ein Hallo ins Forum :), bin hier jetzt schon länger am lesen, eigentlich findet man für alles eine Antwort, super!

Jetzt habe ich aber ein Problem auf das ich keine Antwort finde. Das liegt aber eventuell auch an der mangelnden Erfahrung mit REST-API, Tokens usw. :)
Wir haben auch das Problem, dass es zu Verbindungsabbrüchen bei den CoFlex Trunks kommt, die Trunks liegen alle nicht am eigentlichen Standort sondern bei uns in der Zentrale. Die Clients kommen also größtenteils von Extern über WAN in die Anlage, das läuft alles soweit auch ganz schick, bis auf die sporadischen Abbrüche, umschalten von TCP auf UDP hat auch nichts gebracht.
Jetzt habe ich versucht nach Deiner (fxbastler) Anleitung via REST-API den Trunk zu ändern, dass hat offensichtlich auch soweit funktioniert, er hat das Timeout auf 300 gestellt, leider ist der Trunk danach aber nicht mehr erreichbar. Er wird rot angezeigt und lässt sich dann nur noch löschen. Hat jemand eine Idee, was ich falsch mache?

Code:
$tcxurl="unserFQDN.on3cx.de"     # needs port if not 443

$jsonauthbody = (@{
    Username="UnserBenutzername"              # 3CX user, maybe email address
    Password="UnserPasswort" # 3CX user password
    SecurityCode=""
} | ConvertTo-Json)

Add-Type -AssemblyName Microsoft.VisualBasic

$LoginResponse = Invoke-RestMethod -Uri "https://$tcxurl/webclient/api/Login/GetAccessToken" -Body $jsonauthbody -Method POST -ContentType "application/json"

if( $LoginResponse.Status -ne "AuthSuccess" ) {
    Write-Host "abort: authentication not successful"
    exit -1
}

$headers = @{Authorization = "Bearer $($LoginResponse.Token.access_token)"}

$uri="https://$tcxurl/xapi/v1/Trunks"
$tcxtrunks=(Invoke-RestMethod -uri $uri -headers $headers -Method GET -ContentType "application/json").Value

Write-Host "found SIP trunks:"
Foreach( $tcxtrunk in $tcxtrunks) {
    Write-Host "trunk ID:  $($tcxtrunk.Id)       name:  $($tcxtrunk.Gateway.Name)"
}

$msg   = 'Welcher Trunk soll geaendert werden'
$tcxtid = [Microsoft.VisualBasic.Interaction]::InputBox($msg, 'get trunk ID')
$msg   = 'Timeout?'
$tcxret = [Microsoft.VisualBasic.Interaction]::InputBox($msg, 'get TimeBetweenReg time')


If( ($tcxtid -ne 0) -and  ($tcxtid.Length -ne 0) -and ($tcxret -ne 0) -and  ($tcxret.Length -ne 0)) {
    Write-Host "for the SIP trunk with ID  $($tcxtrunk.Id)  and name $($tcxtrunk.Gateway.Name) change the TimeBetweenReg to $tcxret"
    $uri="https://$tcxurl/xapi/v1/Trunks($tcxtid)"
    $tcxtbodyjson=@{Gateway=@{TimeBetweenReg=$tcxret}} | ConvertTo-Json
    Invoke-RestMethod -uri $uri -headers $headers -Method PATCH -body $tcxtbodyjson -ContentType "application/json"
    # show all trunk values
    Invoke-RestMethod -uri $uri -headers $headers -Method GET -ContentType "application/json"
}

Ergebnis:
found SIP trunks:
trunk ID: 30 name: WebMeeting bridge
trunk ID: 52 name: Standort1 (Der wurde gewählt und sollte geändert werden)
trunk ID: 55 name: Standort2
trunk ID: 65 name: Standort3
trunk ID: 71 name: Standort4
trunk ID: 74 name: Standort5
trunk ID: 84 name: Standort6
trunk ID: 119 name: Standort7
trunk ID: 127 name: Standort8
trunk ID: 184 name: Standort9
trunk ID: 187 name: Standort10
trunk ID: 207 name: Standort11
for the SIP trunk with ID 207 and name Standort11 change the TimeBetweenReg to 300 (?)



@odata.context : https://unserfqdn.on3cx.de/xapi/v1/$metadata#Trunks/$entity
IsOnline : False
AuthID : +49199xxxxx
Direction : Both
ExternalNumber : +49xxxxxx
OutboundCallerID : +49xxxxxx
SimultaneousCalls : 10
DidNumbers : {+49xxxx, ...}
UseSeparateAuthId : True
SeparateAuthId : [email protected]
SecondaryRegistrar : 55xxxxx.secondary.companyflex.de
PublicIPinSIP :
E164ProcessIncomingNumber : False
DiversionHeader : True
EnableInboundCalls : True
EnableOutboundCalls : True
IPRestriction : IPV4
TransportRestriction : TLS
PublishInfo : False
PublicInfoGroups : {GRP0001}
ReceiveInfo : False
RemotePBXPreffix :
TunnelEnabled : False
TunnelRemoteAddr :
TunnelRemotePort : 0
Tags : {}
DisableVideo : True
CertificateName :
Number : 10000
Id : 52
AuthPassword : @{Value=xXxXxXx}
Messaging : @{Enabled=False}
Gateway : @{Codecs=System.Object[]; DeliverAudio=True; DestNumberInRemotePartyIDCalled=False; DestNumberInRequestLineURI=True; DestNumberInTo=True; SRTPMode=SRTPEnforced;
Host=tel.t-online.de; ProxyHost=xxxxxxxxxxxxx.primary.companyflex.de; Internal=False; Lines=0; MatchingStrategy=MatchAnyFields; Name=Standort1;
OutboundCallerID=; Port=0; ProxyPort=5060; RequireRegistrationFor=InOutCalls; SupportReinvite=False; SupportReplaces=False;
TemplateFilename=telekomcompanyflex.pv.xml; TimeBetweenReg=300; Type=Unknown; UseIPInContact=False; IPInRegistrationContact=External;
SpecifiedIPForRegistrationContact=; Id=7; InboundParams=System.Object[]; OutboundParams=System.Object[]; SourceIdentification=System.Object[];
VariableChoices=System.Object[]}
InCIDFormatting : {}
OutCIDFormatting : {}
TrunkRegTimes : {}


Wo kommt der in der Anlage erstellte Token denn eigentlich rein, oder verstehe ich das einfach falsch, habe mit Programmierung bisher leider wenig Erfahrung. Würde da aber gerne etwas fitter werden.
Die Verbindung wird ja offensichtlich hergestellt, leider aber der Trunk gekillt. Neustart hat auch nicht geholfen, musste das Backup einspielen, dann hat sofort alles wieder funktioniert.

Ich hoffe ich habe das alles einigermaßen schlüßig geschildert, Rückfragen sind ausdrücklich erwünscht. :)

Unser System:
3CX Enterprise V20 Update 6 (Build 724)
self hostet auf einer VM, einen SBS haben wir bisher nicht
bis jetzt 16 Sprachkanäle
bis jetzt 100 Teilnehmer
bis jetzt 10 Trunks (Telekom CoFlex Voicedata, aber auch verschiedene andere T-Com Trunks)
1x Plusnet Trunk, auf den sollen mittelfristig alle Außenstellen (alle innerhalb von Deutschland insgesamt ca. 60)
Endgeräte sind bunt gemischt von Auerswald über Snom bis Yeahlink
 
Zuletzt bearbeitet:
er hat das Timeout auf 300 gestellt, leider ist der Trunk danach aber nicht mehr erreichbar.
Naja, in der originalen Vorlage in der 3CX stehen 600 Sekunden drin.
Wenn man das VOIP Geschehen des SIP Trunk auf der 3CX mitschneidet und sich mit Wireshark anschaut lässt sich feststellen was die Telekom sich da vorstellt und was genau bei Register als Fehler kommt.

Wo kommt der in der Anlage erstellte Token denn eigentlich rein
Was meinst du damit? Welcher in der Anlage erstellte Token? Bitte ein Bild ...

Eine (ganz) andere Frage:
Lassen sich bei diesem SIP Trunk - nach o.b. Änderung des ReReg Timeouts in der 3CX - die sonstigen Einstellungen im Dialog noch wie zuvor normal aufrufen / geht der Dialog auf?
 
Zuletzt bearbeitet:
Hallo fxbastler,

kurz zur Erklärung, ich bin noch 3cx Neuling, haben/hatten immer Auerswald Anlagen und entprechenden Support dazu. Also bitte hab(t) Nachsicht, wenn einiges wirklich komplettes Neuland für mich ist.

Ja, leider, verstehe auch nicht, warum man die Einstellungen der Trunks nicht ein bisschen frei konfigurierbarer lässt.

Einen Mitschnitt habe ich bisher nicht gemacht, die Abbrüche treten leider auch nicht reproduzierbar auf.

Ich habe das so verstanden, dass ich über REST-API, erst nach vorheriger Erstellung eines Token in die Konfiguration eingreifen kann!? Wie gesgt, fange fast bei 0 an. ;)
Screenshot 2025-08-22 131631.jpg
 
Ja, leider, verstehe auch nicht, warum man die Einstellungen der Trunks nicht ein bisschen frei konfigurierbarer lässt.
Das geht mehr in der 3CX Verwaltungsoberfläche einer 3CX v20 (mehr). Das geht über Export, Ändern und Import der Vorlage. Das ist der offizielle Weg.

Über die Config API / xapi geht das auch. Das alles und noch mehr. Dafür gibt es nicht nur div. einzelne Skripte für Automatisierung usw. sondern auch div. Skripte die eine GUI bieten um das zu tun - mehr demnächst ...

Ich habe das so verstanden, dass ich über REST-API, erst nach vorheriger Erstellung eines Token in die Konfiguration eingreifen kann!?
Das ist nur eine Möglichkeit um auf die API zuzugreifen und es gibt nicht nur diese eine API.

Du wie so viele andere auch wollen einfach nur Dinge auslesen oder einstellen, hier und da vielleicht mehr oder einfach nur anders als man es in der 3CX Verwaltungsoberfläche sieht und tut. Dazu kann man sich auch als Systemeigentümer per Skript an der 3CX anmelden (NSt. Nummer oder E-Mail Adresse, Passwort und wenn eingestellt auch mit 2FA Token). Das ist das was du in dem von dir oben geposteten Powershell Skript letztendlich tust. Dazu braucht man dieses Token aus dem Bild von deinem Dialog nicht. Das kann man machen, muss man nicht. Dieses Token (das aus dem Bild) braucht man vor allem für die 3CX Call Control API. Das ist eine andere API und eine andere Welt.

Ich erkläre es mal so:
Grundsätzlich alles (was in der 3CX Verwaltungsoberfläche geklickt werden kann) wird im Browser auch über eine REST API, die 3CX Configuration API (auch xapi genannt), gemacht. Das heißt, das alles (oder fast) kann man ferngesteuert, automatisiert und auch mit Skripten tun. Da ist ganz viel offiziell von 3CX dokumentiert. Vieles Andere findet man schnell heraus, indem man sich das Geklicker einfach mal mit den Browser Development Tools (meist F12) anschaut. Auch das geht. Die Nutzung und Möglichkeiten dieser API gehen noch weiter, weiter als dokumentiert und man ohne weiteres mit den DevTools findet. Da darf man sich mal durchstöbern, das ist persönliche Forschungs- und Feldarbeit. Das muss man auch nicht alles auf einer Kommandozeile tun. Es gibt Beispiele von Skripten die eine grafische Oberfläche bieten, dieses Tools z.B.:
https://www.3cx.com/community/threads/holiday-manager-powershell-script-with-gui.134737/

Man kann sich ja einfach mal so als ersten Einstieg die Ausgabe von
Code:
(Invoke-RestMethod -uri "https://$tcxurl/xapi/v1" -headers $headers -Method GET -ContentType "application/json").value
anschauen. Das ist ein Anfang ;)
 
Zuletzt bearbeitet:
  • Like
Reaktionen: bitn2

Statistik des Forums

Themen
44.411
Beiträge
232.704
Mitglieder
78.328
Neuestes Mitglied
as7h