Setting up hook for DCV DNS in TBSCertBot
It is possible to validate DCV controls via TBSCertBot using different methods, including DNS TXT and CNAME tokens.
This documentation explains how to configure and use the DCV DNS functionality, highlighting the differences between the Sectigo and DigiCert methods, how to view DCV values and their statuses, and how the information can be updated in cron mode.
Configuring the DCV parameter
The DCV (Domain Control Validation) parameter can be configured in two different ways:
- In the configuration file: You can set the DCV parameter directly in the configuration file:
[REQUEST] domainControlValidation = CNAME_CSR_HASH
- In command line: You can specify the DCV parameter when running the TBSCertBot order command. Here is an example of a command line:
#php tbscertbot.php order --product ssl --maindomain domain.tld --dcv DNSTXT_CSR_HASH
The available values for the DCV method in the configuration file are:
- HTTP_CSR_HASH: text file to place in your website accessible in HTTP
- HTTPS_CSR_HASH: text file to place in your website accessible in HTTPS
- CNAME_CSR_HASH: CNAME entry to add to your DNS configuration
- DNSTXT_CSR_HASH (for DigiCert products only): TXT entry to add to your DNS configuration
- Email address: a valid email address among admin@, administrator@, hostmaster@, postmaster@, webmaster@domain.tld
DCV Hook for automation of DNS DCV values
In order for the DNS DCV values to be correctly placed at the registrar, it is essential to configure the DCV hook in TBSCertBot.
The DCV hook allows TBSCertBot to communicate with the DNS registrar and create or update DNS records needed for domain validation.
Environment variables
The following environment variables are set to use the DCV DNS functionality:
- PHP_TBS_DCV_METHOD: DCV method (e.g. dns-txt-token or dns-cname-token)
- PHP_TBS_DCV_DOMAIN_ROOT: Root domain for DCV
- PHP_TBS_DCV_DOMAIN_SUB: Subdomain for DCV
- PHP_TBS_DCV_VALUE: Value for DCV
- PHP_TBS_DNS_ACTION: Action for DNS (CREATE or UPDATE)
- PHP_TBS_REGISTRAR: Domain registrar (for example, GANDI SAS or OVH SAS)
DCV Hook Configuration
- In the configuration file: Add the DCV hook configuration to the conf.ini file. Here is an example:
[HOOKS] dcv = /path/to/exportDCVScript.sh
Scripts
You can use one of the following example scripts for Gandi and OVH registrars, or write your own hook if your registrar is different from the ones provided as examples.
Example script exportDCVScript.sh
# Path of the script configured for TBSCertbot PATH_SCRIPT="/root" # Only if dns-txt-token or dns-cname-token if [ "$PHP_TBS_DCV_METHOD" = "dns-txt-token" ] || [ "$PHP_TBS_DCV_METHOD" = "dns-cname-token" ]; then # check if the registrar is Gandi if [ "$PHP_TBS_REGISTRAR" = "GANDI SAS" ]; then echo "Registrar is Gandi" # Call the script dns-gandi.sh echo "Call the script dns-gandi.sh" $PATH_SCRIPT/dns-gandi.sh exit 1 fi # check if the registrar is OVH if [ "$PHP_TBS_REGISTRAR" = "OVH SAS" ]; then echo "Registrar is OVH" # Call the script dns-ovh.sh echo "Call the script dns-ovh.sh" $PATH_SCRIPT/dns-ovh.sh exit 1 fi echo "No script for this registrar ($PHP_TBS_REGISTRAR)" fi
Example script for Gandi (dns-gandi.sh)
#Script for TBSCertbot that sends DNS DCV to Gandi # Define token Gandi GANDI_TOKEN="" echo "Check all parameters" # test if $PHP_TBS_DCV_DOMAIN_ROOT is not empty if [ -z "$PHP_TBS_DCV_DOMAIN_ROOT" ]; then echo "Error: PHP_TBS_DCV_DOMAIN_ROOT is empty" exit 1 fi # test if $PHP_TBS_DCV_DOMAIN_SUB is not empty if [ -z "$PHP_TBS_DCV_DOMAIN_SUB" ]; then echo "Error: PHP_TBS_DCV_DOMAIN_SUB is empty" exit 1 fi # test if $PHP_TBS_DCV_VALUE is not empty if [ -z "$PHP_TBS_DCV_VALUE" ]; then echo "Error: PHP_TBS_DCV_VALUE is empty" exit 1 fi # test if $GANDI_TOKEN is not empty if [ -z "$GANDI_TOKEN" ]; then echo "Error: GANDI_TOKEN is empty" exit 1 fi # Send the DNS entry to Gandi response=$(curl -s -X POST https://api.gandi.net/v5/livedns/domains/"$PHP_TBS_DCV_DOMAIN_ROOT"/records \ -H "authorization: Bearer $GANDI_TOKEN" \ -H "content-type: application/json" \ -d "{\"rrset_name\":\"$PHP_TBS_DCV_DOMAIN_SUB\",\"rrset_type\":\"TXT\",\"rrset_values\":[\"$PHP_TBS_DCV_VALUE\"]}") echo "$response"
Displaying DCV values and their statuses
DCV values and their statuses can be displayed using the TBSCertBot status command. Here is an example:
#php tbscertbot.php status REFERENCE
example result:
DCV: test.domain.tld: unapproved -> DCV Method: dns-cname-token -> DCV Domain Name: _252F2682B6A2B01A4139F33164A88893.test.domain.tld. -> DCV Verification Value: 24beebb3a9dbd12709dc8399e0454dcc.2ec37b5d5243686e2fc702c968ce6403.tz43e7ZtlmXpy62bjCEa.trust-provider.com. -> DNS value matches the expected value
Updating information in cron mode
If the DCV is not known at the time of the order, TBSCertBot can be run in cron mode to receive the information to set the values. Once configured, reissuances will use the same mechanics.
Sectigo order Example
Here is a command example to order a Sectigo SSL certificate with TBSCertBot:
#php tbscertbot.php order --product COMs2ssl --maindomain test.domain.tld --dcv CNAME_CSR_HASH Ordering product : Sectigo SSL (COMs2ssl) Validity : 1 Validating all parameters... All parameters are OK! Generating new cryptographic key... - Type = RSA - Length = 2048 New cryptographic key generated! Generating new CSR... - CN = test.domain.tld - O = COMPANY - L = CITY - C = FR New CSR generated! Checking DCV for domain: test.domain.tld DCV for domain test.domain.tld is: CNAME_CSR_HASH Running DCV hook: /exportDCVScript.sh Method : dns-cname-token Registrar is Gandi Call the script dns-gandi.sh Check all parameters Parameters OK Send the new entry to the Registrar {"rrset_name":"_252F2682B6A2B01A4139F33164A88893.test.domain.tld.","rrset_type":"CNAME","rrset_values":["24beebb3a9dbd12709dc8399e0454dcc.2ec37b5d5243686e2fc702c968ce6403.tz43e7ztlmxpy62bjcea.trust-provider.com."]} {"message":"DNS Record Created"} Placing order... Order taken into account under the reference 1444444444. Checking if certificate reference 1444444444 (CN = test.domain.tld) is available... -> Certificate is NOT AVAILABLE now, its current state is "Processing". -> Additional information: "Awaiting payment". DCV: test.domain.tld: unapproved -> DCV Method: dns-cname-token -> DCV Domain Name: _252F2682B6A2B01A4139F33164A88893.test.domain.tld. -> DCV Verification Value: 24beebb3a9dbd12709dc8399e0454dcc.2ec37b5d5243686e2fc702c968ce6403.tz43e7ZtlmXpy62bjCEa.trust-provider.com. -> DNS value matches the expected value
Explanation of the steps:
- Order: The order is placed for a Sectigo SSL product (COMs2ssl) with test.domain.tld as the main domain. The DCV method CNAME_CSR_HASH is chosen.
- Validation of parameters: TBSCertBot validates all necessary parameters for the command.
- Cryptographic key generation: A new 2048-bit RSA key is generated.
- CSR Generation: A new Certificate Signing Request (CSR) is generated with the information provided.
- DCV Check: TBSCertBot checks the DCV method for the domain and executes the configured DCV hook.
- Executing the DCV hook: The dns-gandi.sh script is called to update the DNS record at the Gandi registrar.
- Placing the order: The order is placed and an order reference is generated.
- Checking certificate availability: TBSCertBot checks if the certificate is available and displays the current status.
- DCV: The DCV validation details are displayed, including method, domain name, and verification value.
Following this example, you can see how TBSCertBot automates the process of ordering and validating Sectigo SSL certificates.
DigiCert order Example
Here is an example command to order a DigiCert SSL certificate with TBSCertBot:
#php tbscertbot.php order --product ssl --maindomain test.domain.tld --dcv DNSTXT_CSR_HASH Ordering product : Thawte SSL Standard (ssl) Validity : 1 Validating all parameters... All parameters are OK! Generating new cryptographic key... - Type = RSA - Length = 2048 New cryptographic key generated! Generating new CSR... - CN = test.domain.tld - O = COMPANY - L = CITY - ST = Calvados - C = FR New CSR generated! Checking DCV for domain: test.domain.tld DCV for domain test.domain.tld is: DNSTXT_CSR_HASH Placing order... Order taken into account under the reference 1444444444. Checking if certificate reference 1444444444 (CN = test.domain.tld) is available... -> Certificate is NOT AVAILABLE now, its current state is "Processing". -> Additional information: "Awaiting payment".
Explanation of the steps:
- Order: The order is placed for a Thawte SSL Standard (ssl) product with test.domain.tld as the primary domain. The DNSTXT_CSR_HASH method is chosen.
- Validation of parameters: TBSCertBot validates all necessary parameters for the command.
- Cryptographic key generation: A new 2048-bit RSA key is generated.
- CSR Generation: A new Certificate Signing Request (CSR) is generated with the information provided.
- DCV Check: TBSCertBot checks the DCV method for the domain.
- Placing the order: The order is placed and an order reference is generated.
- Checking certificate availability: TBSCertBot checks if the certificate is available and displays the current status.
For DigiCert, the DCV information is only available after the order, so no hook call is made at this point. However, by running the status command or in cron mode, the hook will be executed and the value will be set:
#php tbscertbot.php status 1444444444 Order status: Status message: Processing Extra information: Awaiting DCV DCV: test.domain.tld: unapproved -> DCV Method: dns-txt-token -> DCV Domain Name: test.domain.tld -> DCV Token Value: _w3azpuswcsshujtcq5qj6mhq7pbqexw -> DNS value does not match the expected value or not present. Running DCV hook: /exportDCVScript.sh Method : dns-txt-token Registrar is Gandi Call the script dns-gandi.sh Check all parameters Parameters OK Send the new entry to the Registrar {"message":"DNS Record Created"}
When you run the status command, TBSCertBot checks the order status and the DCV information. If the DCV information is available and the validation has not yet been performed, the configured DCV hook will be executed. In this example, the dns-gandi.sh script is called to update the DNS record at the Gandi registrar.
The script checks the settings, sends the new DNS entry to the registrar, and confirms the creation of the DNS record. Once the DNS record is successfully updated and the DCV value matches the expected one, TBSCertBot continues the validation process.
If everything is correct, the certificate will be issued and you can check its status by using the status command again.
How DNS entries created by TBSCertBot are handled
When you submit a new request then an entry is created in your DNS configuration. During renewals and reissuances and if you use the same CSR then the tool checks for the presence of a DNS entry. In this case the tool will update the existing entry. Otherwise a new entry will be created.
What to do with DNS entries once your certificate is delivered?
Once your certificate is delivered, the DNS entry is no longer useful. It is therefore possible to delete it. It is then possible to update the delivery hook to remove the obsolete entries.
Hooks creation
You can create as many hooks as you like. A testing feature called "test-hook" exists within TBSCertBot specifically for testing your hooks.
How to test your hooks?
To test a hook, you must use the command:
php tbscertbot.php test-hook NAME_OF_THE_HOOK [TBS reference].
The TBS reference is optional. Indicate it if you want to test your hook on a specific command. Example:
php tbscertbot.php test-hook download 1234567890.
This command will restart the script related to the download hook on command 1234567890. You can find some example hooks in the data/testhooks directory of your TBSCertBot installation.
Sandbox Server for Testing
A sandbox server is available to allow you to test the entire process from order to delivery. This sandbox server provides you with a secure environment to experiment and validate your configurations without affecting your production systems.
To set up a test environment, simply contact us. We will be happy to help you configure and use the sandbox server for your testing needs.
Contact us today to start testing with our sandbox server!