Documentation Index

Fetch the complete documentation index at: https://docs.traceable.ai/llms.txt

Use this file to discover all available pages before exploring further.

Mutual TLS

Prev Next

Mutual Transport Layer Security (mTLS) is an authentication method in which both the client and server verify each other’s SSL/TLS certificates. This two-way validation establishes a trusted relationship and ensures secure, authenticated communication.

Configurations

You can set up the mTLS authentication using either of the following methods:

For setting up mTLS authentication using the Traceable platform, you must have the following configurations:

Configuration

Description

Client Certificate

A client certificate is a digital certificate that the client presents during the TLS handshake to prove its identity to the server. This server validates this certificate along with its own to establish a secure and authenticated communication channel. The certificate must be provided in PEM format.

Client Key

A client key is the private key associated with the client's digital certificate.

Client Key Passphrase

A client key passphrase is the password used to protect the private key associated with the client's digital certificate.

Client Authority Certificate

A bundle of trusted CA certificates for validating the server's certificate.

You can set up mTLS authentication directly from the CLI using a JSON file and environment variables. To do so, use the following syntax:

{
    "host:port" : {
        "client_cert": <Path to the Client Certificate>,
        "client_key": <Path to the Client Key>,
        "root_ca": <Path to the Client Authority Certificate>,
        "passphrase": <(Optional) Path to the Client Key Passphrase>
    }
    "host:port" : {
        "client_cert": <Path to the Client Certificate>,
        "client_key": <Path to the Client Key>,
        "root_ca": <Path to the Client Authority Certificate>,
    },
    "default" : {
        "client_cert": "/certs/client_default.crt",
        "client_key": "/certs/client_default.key",
        "root_ca": "/certs/CA_default.pem"
    }
}

Note

The default section in the above JSON acts as a fallback mechanism when Traceable does not find any matching host.

For example, the JSON file would look like the following:

{
    "mysite.local:8443" : {
        "client_cert": "/home/work/traceable/ast/pov_tools/mtls/certs/cas.client.crt",
        "client_key": "/home/work/traceable/ast/pov_tools/mtls/certs/cas.client.key",
        "root_ca": "/home/work/traceable/ast/pov_tools/mtls/certs/CA.pem",
        "passphrase": ""   # This represents an empty passphrase
    }
    "anotherhost.com:443" : {
        "client_cert": "/certs/client.crt",
        "client_key": "/certs/client.key",
        "root_ca": "/certs/CA.pem",
    },
    "default" : {
        "client_cert": "/certs/client_default.crt",
        "client_key": "/certs/client_default.key",
        "root_ca": "/certs/CA_default.pem"
    }
}

After defining the JSON file, export one of the following environment variables in the shell, invoking the CLI:

  • Use one environment variable, for example:

    export TARGET_TLS_CONFIG_FILE = /path/mtls_config.json

    You can define the JSON file (mtls_config.json) like the one above.

    Note

    This method authenticates all hosts mentioned in the JSON file.

  • Use multiple environment variables, for example:

    export ROOT_CA_FILE = /path/CA.pem
    export TARGET_CLIENT_CERT_FILE = /path/client.crt
    export TARGET_CLIENT_KEY_FILE = /path/client.key
    export TARGET_CLIENT_KEY_PASSPHRASE = "<passphrase>"

Example

The following are some samples that you can use to configure the JWT mechanism in the Advanced mode:

Sample 1

from traceable import config
import io
import tempfile
from traceable.ast.constants import (
    DEFAULT_HOST,
    CLIENT_CERT,
    CLIENT_KEY,
    KEY_PASSPHRASE,
    ROOT_CA
)

def mtls_hook(scanctx: ScanContext, pluginctx: PluginContext, testcase: TestCase, **kwargs) -> list[Assertion]:
    def string_to_absolute_filepath(content, file_extension='.txt'):
        # Create a temporary file in a secure location
        with tempfile.NamedTemporaryFile(mode='w', suffix=file_extension, delete=False) as temp_file:
            # Write the string content to the temporary file
            temp_file.write(content)

            # Get the absolute path of the temporary file
            absolute_filepath = os.path.abspath(temp_file.name)

        # The temporary file will be automatically closed and deleted
        # as it goes out of scope, but you can also explicitly delete it here:
        return absolute_filepath
    attributes = testcase.get_attributes()
    url = attributes.get_one("mutated.http.request.url", default="")
    http_client = testcase.get_http_client(url)
    # Typecase http_client
    attributes = testcase.get_attributes()
    # Set the certificate and key contents as strings
    client_cert = "client_cert"
    client_key = "client_key"
    root_ca = "root_ca"

    mtls_dict = {CLIENT_CERT: string_to_absolute_filepath(client_cert),
                 CLIENT_KEY: string_to_absolute_filepath(client_key),
                 }
    if len(root_ca) > 0:
        mtls_dict[ROOT_CA] = string_to_absolute_filepath(root_ca)

    config.TLS_CONFIG[DEFAULT_HOST][CLIENT_CERT] = mtls_dict[CLIENT_CERT]
    config.TLS_CONFIG[DEFAULT_HOST][CLIENT_KEY] = mtls_dict[CLIENT_KEY]
    if ROOT_CA in mtls_dict:
        config.TLS_CONFIG[DEFAULT_HOST][ROOT_CA] = mtls_dict[ROOT_CA]
    return []