How to manually update SSL certificate on v20 self-hosted 3CX?

it.support

Premier Customer
Joined
Jan 16, 2023
Messages
3
Reaction score
2
Hi all, we've updated our self-hosted 3CX instance from v18 to v20 last year. Our SSL certificate have recently expired so I tried to update it using same method in the previous year to no avail.
I would usually log into the server. Copy fqdn.key file and fqdn.pem file to C:\Program Files\3CX Phone System\Bin\nginx\conf\instance1 and rename the respective files to fqdn-crt.pem and fqdn-key.pem to match. Then restart the "3CX PhoneSystem Nginx Server" service.

We're running 3CX on Windows server 2016 and I used instructions from these posts in the past to update the certs:
https://www.3cx.com/docs/renewing-ssl-certificate/

The first link is no longer available, so I wonder if the instructions have changed. I couldn't find anything recent on 3CX forums regarding renewing SSL certificates on Windows. Hoping you guys can point me in the right directions.
 
In Version 20 the certificate files are in C:\ProgramData\3CX\Bin\nginx\conf\Instance1
 
  • Like
Reactions: Evolute IT
About the names and location for nginx and sips certs you may look at this linux example:
https://www.3cx.de/forum/threads/ssl-certificate-erneuert.114018/post-441718

edit for Windows (we use powershell there):
C:\ProgramData\3CX\Bin\nginx\conf\Instance1\domain_cert_<fqdn>.pem
C:\ProgramData\3CX\Bin\nginx\conf\Instance1\domain_key_<fqdn>.pem
C:\ProgramData\3CX\Instance1\Bin\Cert\domain_cert_<fqdn>.pem
C:\ProgramData\3CX\Instance1\Bin\Cert\domain_key_<fqdn>.pem
 
Last edited:
  • Like
Reactions: it.support
clientcert-renew-pbx.domain.de.ps1

Code:
# Pfad zur NGINX-Konfigurationsdatei
$nginxConfigFile = "C:\Program Files\3CX Phone System\Bin\nginx\conf\nginx.conf"

# Pfade der 3CX Zertifikate
$sipCertDir = "C:\ProgramData\3CX\Instance1\Bin\Cert"
$sshUsername = "sshuser" # Benutzername für Let's Encrypt Zertifikate
$homeDir = "C:\Users\$sshUsername" # Angenommener Pfad für die Let's Encrypt Zertifikate

# FQDN und Zertifikat-Pfade initialisieren
$fqdn = ""
$nginxCertPath = ""
$nginxKeyPath = ""
$actCertPath = "$homeDir\$fqdn.fullchain"
$actKeyPath = "$homeDir\$fqdn.key"
$sipCertPath = "$sipCertDir\domain_cert_$fqdn.pem"
$sipKeyPath = "$sipCertDir\domain_key_$fqdn.pem"

# NGINX-Konfiguration einlesen
$nginxConfigContent = Get-Content -Path $nginxConfigFile

# FQDN, Zertifikat und Schlüssel extrahieren
foreach ($line in $nginxConfigContent) {
    if ($line -match 'server_name\s+([^\s;]+);') { $fqdn = $matches[1] }
    if ($line -match 'ssl_certificate\s+"?([^\s;]+)"?;') { $nginxCertPath = $matches[1] }
    if ($line -match 'ssl_certificate_key\s+"?([^\s;]+)"?;') { $nginxKeyPath = $matches[1] }
}

# Aktuelle Zertifikat-Hashes berechnen
$actCertHash = (Get-FileHash $actCertPath -Algorithm MD5).Hash
$actKeyHash = (Get-FileHash $actKeyPath -Algorithm MD5).Hash

# NGINX-Zertifikat-Hashes berechnen
$nginxCertHash = (Get-FileHash $nginxCertPath -Algorithm MD5).Hash
$nginxKeyHash = (Get-FileHash $nginxKeyPath -Algorithm MD5).Hash

# SIP-Zertifikat-Hashes berechnen
$sipCertHash = (Get-FileHash $sipCertPath -Algorithm MD5).Hash
$sipKeyHash = (Get-FileHash $sipKeyPath -Algorithm MD5).Hash

# Überprüfen, ob die Zertifikate nicht übereinstimmen
if ($nginxCertHash -ne $actCertHash -or $sipCertHash -ne $actCertHash -or $nginxKeyHash -ne $actKeyHash -or $sipKeyHash -ne $actKeyHash) {
    # NGINX Zertifikate ersetzen
    Remove-Item $nginxCertPath -Force
    Remove-Item $nginxKeyPath -Force
    Copy-Item $actCertPath $nginxCertPath
    Copy-Item $actKeyPath $nginxKeyPath

    # Berechtigungen setzen
    icacls $nginxCertPath /grant "phonesystem:(R)"
    icacls $nginxKeyPath /grant "phonesystem:(R)"

    # NGINX neu laden (Nginx-Dienst muss manuell neu gestartet werden)
    Restart-Service -Name "nginx"

    # 3CX-Dienst stoppen
    Stop-Service -Name "3CXPhoneSystem01"

    # 3CX SIP Zertifikate ersetzen
    Remove-Item $sipCertPath -Force
    Remove-Item $sipKeyPath -Force
    Copy-Item $actCertPath $sipCertPath
    Copy-Item $actKeyPath $sipKeyPath

    # Berechtigungen setzen
    icacls $sipCertPath /grant "phonesystem:(R)"
    icacls $sipKeyPath /grant "phonesystem:(R)"

    # Dienste neu starten
    $services = Get-Service | Where-Object { $_.Name -like "*3CX*" }
    foreach ($service in $services) {
        if ($service.Status -ne "Running") {
            Start-Service $service.Name
        }
    }

    # Neustart des Systems, falls erforderlich?  probieren und eventuell aktivieren!
    # Restart-Computer
}

exit 1
 
Thanks guys.

I've updated the files in the new location: C:\ProgramData\3CX\Bin\nginx\conf\Instance1\
Renamed them domain_cert_<fqdn>.pem and domain_key_<fqdn>.pem
Restarted "3CX PhoneSystem Nginx Server" service via management console

After this the site have been applied with the new certificate.
 

Latest Posts

Forum statistics

Threads
111,962
Messages
589,993
Members
164,867
Latest member
swegner