Skip to main content

Tutorial: Configure External PKI with Futurex CryptoHub for Access Server

Abstract

Learn how to integrate Access Server with a Futurex CryptoHub using PKCS #11 to protect TLS private keys and strengthen your external PKI security.

Overview

This tutorial explains how to integrate Access Server with a Futurex CryptoHub to use an external public key infrastructure (PKI) for TLS authentication. Access Server supports external keys stored on PKCS #11–compliant hardware security modules. By storing the TLS server private key and the CA signing key on the CryptoHub rather than on the Access Server host, you keep the most sensitive cryptographic material protected. The private keys never leave the CryptoHub, reducing the risk of compromise even if the Access Server system is breached.

Prerequisites

Access Server host requirements

  • Minimum 4 GB RAM.

  • Supported Linux OS:

    • Ubuntu 24.04 LTS.

    • Debian 13.

    • Debian 12.

    • RHEL 9 (And RHEL 9 Clones).

  • Console (root) access

CryptoHub requirements

  • A Futurex CryptoHub appliance (version 7.0.2.x or later) with initial setup completed, including:

    • Platform Master Key loaded.

    • Network configuration in place.

    • Administrator access to the CryptoHub

Network requirements

  • Network connectivity from the Access Server host to the CryptoHub:

    • Outbound TCP port 2001 (default host API port) allowed.

    • Destination allowed by FQDN (e.g., cryptohub.example.com) or CIDR range.

    • CryptoHub FQDN exempt from TLS/SSL inspection or proxy filtering.

Required tools on the Access Server host

  • OpenSSL (version 3.x or newer).

  • pkcs11-tool (available via the opensc package).

  • Python 3.6+.

  • uri2pem.py utility.

  • Python library asn1crypto.

  1. Sign in to the CryptoHub under dual control using your administrator identities.

  2. In the left navigation panel, select Services, and find the service called OpenVPN Access Server.

    Tip

    You can also find OpenVPN Access Server using the search bar.

  3. Click Deploy.

  4. Configure the following Service Setup settings:

    • Service Name: Leave as default (application name).

    • Service Category: Leave as default.

  5. Click Next.

  6. Configure the following Access Control settings:

    • Authorized Resources: Your role has access to this service by default.

    • Add Additional Resources: Optional.

  7. Click Next.

  8. Configure the following Service Info setting:

    • Authentication Mechanisms: Leave as default.

  9. Click Deploy.

This endpoint is a device authorized to access the OpenVPN service you deployed in the previous step.

  1. In the left navigation panel, click Home.

  2. Under Deployed Services, locate and select OpenVPN Access Server.

  3. Click ENDPOINTS.

  4. Under Manage Endpoints, click Add New.

  5. In the Add Endpoint dialog:

    • Endpoint Identifier: Enter an identifier or leave it empty for auto-generation.

    • CryptoHub Hostname: Leave as default.

    • Platform: Select the Platform for the endpoint.

  6. Click Add Endpoint.

    • The browser prompts you to download a ZIP file containing the Futurex PKCS #11 module, TLS certificates, and a preconfigured configuration file to connect to your CryptoHub instance.

Tip

If you want to change an endpoint's PIN/password, go to Identity and Access > Applications & Partitions. Find the application you deployed, and under Manage, click Authentication. This opens a dialog where you can change the endpoint's PIN or password.

  1. Download the FXPKCS11 package from your CryptoHub deployment (the ZIP file downloaded in the previous step).

  2. Move the FXPKCS11 package to the Access Server host. (This system must have access to CryptoHub to use external keys.)

Install FXPKCS11 on the Access Server host

Perform the following steps to install and configure FXPKCS11 on your Access Server Linux host.

Step 1: Extract the CryptoHub package and create the FXPKCS11 directory

  1. Connect to the Access Server console and get root privileges.

  2. Transfer the ZIP file downloaded from CryptoHub to the server.

  3. Extract the ZIP file. The ZIP contains:

    • CryptoHub 1234567890.cer

    • Futurex Test Root CA (ECC).cer

    • PKCS11Manager

    • ca-chain.pem

    • client-cert.pem

    • client.p12

    • configTest

    • fxpkcs11.cfg

    • libfxpkcs11.so

    Tip

    In this example, files are stored in the root directory.

    Important

    The number in CryptoHub 1234567890.cer will vary. Replace it with your file's value in the commands below.

  4. Create the following directory:

    mkdir /usr/local/lib/fxpkcs11

Step 2: Move the extracted files

  1. Move the extracted files to /usr/local/lib/fxpkcs11:

    cp 'CryptoHub 1234567890.cer' 'Futurex Test Root CA (ECC).cer' PKCS11Manager ca-chain.pem client-cert.pem client.p12 configTest fxpkcs11.cfg libfxpkcs11.so /usr/local/lib/fxpkcs11
  2. After this, move the following files to /etc (default expected location):

    • CryptoHub 1234567890.cer

    • Futurex Test Root CA (ECC).cer

    • client.p12

    • fxpkcs11.cfg

    cp 'CryptoHub 1234567890.cer' 'Futurex Test Root CA (ECC).cer' client.p12 fxpkcs11.cfg /etc

Optional: Use a custom configuration location

If you prefer to store the configuration file elsewhere, define the environment variable:

export FXPKCS11_CFG=/path/to/your/fxpkcs11.cfg

Step 4: Configure secrets (PKCS #12 password)

  1. Extract the password from fxpkcs11.cfg (between <PROD-TLS-KEY-PASS> and </PROD-TLS-KEY-PASS>) and write it to a file:

    echo "export PKCS11_P12=$(grep PROD-TLS-KEY-PASS /etc/fxpkcs11.cfg | sed 's/.*<PROD-TLS-KEY-PASS>\s*\(.*\)\s*<\/PROD-TLS-KEY-PASS>.*/\1/')" > /etc/profile.d/fxpkcs11.sh
  2. Confirm the file contains export PKCS11_P12=password where password is the password value between <PROD-TLS-KEY-PASS> and </PROD-TLS-KEY-PASS>:

    cat /etc/profile.d/fxpkcs11.sh
    
    • This takes effect for new login shells. Sign out and back in, or start a new shell session before validating or running applications that rely on PKCS11_P12.

Step 6: Troubleshoot validation issues

If ConfigTest fails:

  1. Check the FxPKCS11 log file:

    • Default location: same directory as fxpkcs11.cfg.

    • To customize, modify the LOG-FILE setting in fxpkcs11.cfg.

  2. Verify:

    • fxpkcs11.cfg is located at /etc/fxpkcs11.cfg (or confirm FXPKCS11_CFG is set correctly)

    • client.p12 is in the same directory as fxpkcs11.cfg

    • PKCS11_P12 is set correctly:

      echo "$PKCS11_P12"

Install the pkcs11-provider module from Latchset. This module allows OpenSSL 3.x to use PKCS #11 tokens through a provider interface. Follow the steps for your Linux version.

Install on Ubuntu / Debian

  1. Install the required packages:

    sudo apt update && sudo apt upgrade -y
    sudo apt install -y git build-essential meson libssl-dev pkg-config python3-asn1crypto opensc libnss3 libnss3-dev libnss3-tools p11-kit libp11-kit-dev
  2. Create a source directory and change into it:

    mkdir -p ~/src
    cd ~/src
  3. Clone the pkcs11-provider repository:

    git clone https://github.com/latchset/pkcs11-provider.git
    cd pkcs11-provider
  4. Build the provider:

    meson setup builddir
    meson compile -C builddir
  5. Install the provider:

    sudo meson install -C builddir

    Note

    During installation, the pkcs11.so module is copied to the OpenSSL modules directory. You'll need this path when updating the OpenSSL configuration file.

    Example output:

    Installing src/pkcs11.so to /usr/lib/x86_64-linux-gnu/ossl-modules

    In this example, pkcs11.so is installed in /usr/lib/x86_64-linux-gnu/ossl-modules.

Install on RHEL

Important

This step includes enabling the EPEL and CodeReady Builder (CRB) repository, so ensure you have a valid RHEL subscription.

  1. Enable EPEL and CodeReady Builder (CRB):

    • RHEL 9:

      subscription-manager repos --enable codeready-builder-for-rhel-9-$(arch)-rpms
      dnf install https://dl.fedoraproject.org/pub/epel/epel-release-latest-9.noarch.rpm
    • Alma and Rocky Linux 9:

      dnf config-manager --set-enabled crb
      dnf install https://dl.fedoraproject.org/pub/epel/epel-release-latest-9.noarch.rpm
  2. Refresh metadata:

    sudo dnf makecache
  3. Install the prerequisites:

    sudo dnf check-update
    sudo dnf install -y git gcc gcc-c++ meson ninja-build pkgconfig openssl-devel nss-devel p11-kit-devel opensc python3-asn1crypto

    Tip

    Use yum if dnf isn't available.

  4. Change to a source directory:

    cd /usr/local/src
  5. Clone the repository:

    git clone https://github.com/latchset/pkcs11-provider.git
    cd pkcs11-provider
  6. Build the provider:

    meson setup builddir
    meson compile -C builddir
  7. Install the provider:

    sudo meson install -C builddir

    Note

    During installation, the pkcs11.so module is copied to the OpenSSL modules directory. You'll need this path when updating the OpenSSL configuration file.

    Example output:

    Installing src/pkcs11.so to /usr/lib64/ossl-modules

    In this example, pkcs11.so is installed in /usr/lib64/ossl-modules.

Configure OpenSSL to load the provider

  1. Locate the OpenSSL configuration file. You can verify it with the following command openssl version -d. For instance:

    • For Ubuntu/Debian:

      root@openvpnas:~# openssl version -d
      OPENSSLDIR: "/usr/lib/ssl"
    • For RHEL:

      root@openvpnas:~# openssl version -d
      OPENSSLDIR: "/etc/pki/tls"

    Important

    This tutorial assumes openssl.cnf is located in /usr/lib/ssl/. Update the path in the following commands accordingly.

  2. Create a backup of the OpenSSL configuration file before making changes:

    cp /usr/lib/ssl/openssl.cnf /usr/lib/ssl/openssl-backup.cnf
  3. Open the OpenSSL configuration file for editing:

    nano /usr/lib/ssl/openssl.cnf
  4. At the top of the file, add the following line if it's not already present:

    openssl_conf = openssl_init
  5. At the bottom of the file, add the following configuration block. Update the paths as needed for your system:

    [openssl_init]
    providers = provider_init
    
    [provider_init]
    default = default_init
    pkcs11 = pkcs11_init
    
    [default_init]
    activate = 1
    
    [pkcs11_init]
    module = /path/to/pkcs11-provider/pkcs11.so1
    pkcs11-module-path = /usr/local/lib/fxpkcs11/libfxpkcs11.so
    pkcs11-module-token-pin = file:/path/to/file_with_pin.txt
    activate = 1

    1

    Update the paths accordingly. In our example:

    • Replace /path/to/pkcs11-provider/pkcs11.so with /usr/lib/x86_64-linux-gnu/ossl-modules/pkcs11.so

    • Replace /path/to/file_with_pin.txt with /root/pkcs11-pin.txt

    Tip

    If you're not sure where pkcs11.so is on your system, run this command:

    find / -type f -path '*/ossl-modules/pkcs11.so' 2>/dev/null
  6. Save the file and exit — Ctrl-X, Y, then Enter.

  7. Verify that the PKCS#11 provider loads correctly:

    openssl list -providers
    • You should see both default and pkcs11 listed.

    • Example output:

      root@openvpnas:~# openssl list -providers
      Providers:
        default
          name: OpenSSL Default Provider
          version: 3.0.13
          status: active
        pkcs11
          name: PKCS#11 Provider
          version: 1.1
          status: active
  8. Reboot the Access Server host:

    reboot

Troubleshoot the validation with PKCS11Manager

  1. Check the FxPKCS11 log file:

    • Default location: same directory as fxpkcs11.cfg.

    • To customize, modify the LOG-FILE setting in fxpkcs11.cfg.

  2. Verify that the PKCS #11 PIN is correct.

  3. To update the PKCS #11 PIN:

    • Sign in to the CryptoHub dashboard.

    • Navigate to Identity and Access.

    • Select the Applications & Partitions tab.

    • Locate your deployed application.

    • In the Manage section, select Authentication.

    • Update the PIN/password for the endpoint in the dialog.

This step prepares the keys and certificates used by Access Server and securely stores them in the CryptoHub. You generate the CA, server, and client certificates using PKCS #11 operations, so that private keys never leave the hardware module.

Important

If you use an external CA, this tutorial doesn't cover how to apply the Access Server's required v3 extensions during certificate signing. Follow your CA’s documentation for extension handling.

Note

VPN clients rely on the CA certificate to validate the server. If the CA certificate expires, client connections will fail until it's replaced.

Important

Futurex can't provide support for issues arising from the use of an external CA; refer to your CA's documentation for guidance on extension handling and certificate issuance.

Ensure you have enough permissions to create/manage a key group:

  1. Sign in to the CryptoHub under dual control using your administrator identities.

  2. In the left navigation panel, select Classic Tools.

  3. Under the Administration tab, click GO TO CONFIGURATION TASKS.

  4. Locate Host API Options (or use the search bar) and double-click it.

  5. Under ATKG, check all the options (add, modify, delete, get).

  6. Click Save.

Set FXPKCS11 environment variables

  • Export the PKCS #11 module path:

    export FXPKCS11_MODULE=/path/to/libfxpkcs11.so1

    1

    Update the path accordingly. For our example, we use /usr/local/lib/fxpkcs11/libfxpkcs11.so.

Configure Access Server for external PKI

  1. Connect to the Access Server console and get root privileges.

  2. Edit as.conf for external PKI usage:

    nano /usr/local/openvpn_as/etc/as.conf
  3. Comment out certs_db:

    # certificates database
    # certs_db=sqlite:///~/db/certs.db
  4. Save and exit the file — Ctrl-X, Y, then Enter.

    • Access Server no longer uses the certificate database. Instead, an external system must handle this.

Generate the CA key on CryptoHub

Tip

We use OpenSSL to generate the files. Skip this section if you're using an external CA.

Note

We're storing the files in the root directory.

  1. Generate the private key:

    pkcs11-tool --module $FXPKCS11_MODULE --login --key-type rsa:2048 --pin "$(cat /root/pkcs11-pin.txt)" --label "OpenVPN-CA-Key" --id 01 --keypairgen --usage-sign
  2. Generate the PKCS #11 URI reference file for the CA key:

    • For Ubuntu/Debian:

      python3 ~/src/pkcs11-provider/tools/uri2pem.py "pkcs11:type=private;object=OpenVPN-CA-Key" > /root/ca.key
    • For RHEL:

      python3 /usr/local/src/pkcs11-provider/tools/uri2pem.py "pkcs11:type=private;object=OpenVPN-CA-Key" > /root/ca.key
  3. Generate the CA certificate:

    openssl req -new -x509 -provider pkcs11 -provider-path $FXPKCS11_MODULE -key ca.key -out ca.crt -days 3650 -subj "/CN=OpenVPN_CA"
    • The above commands output two files:

      • CA key (ca.key)

      • CA certificate (ca.crt)

Create OpenSSL configuration for the server certificate

  1. Copy the default OpenSSL configuration file to a new file named openssl-server.cnf:

    OUT="/usr/lib/ssl/openssl-server.cnf"
    cp /usr/lib/ssl/openssl.cnf "$OUT"
  2. Update the [ req ] section:

    sed -i '/^\[ req \]/,/^\[/{/req_extensions/ d}' "$OUT"
    sed -i '/^\[ req \]/,/^\[/{/x509_extensions/ a\
    req_extensions = v3_req
    }' "$OUT"
  3. Update the [ v3_req ] section:

    sed -i '/^\[ v3_req \]/,/^\[/{s/basicConstraints.*/basicConstraints = critical, CA:FALSE/}' "$OUT"
    sed -i '/^\[ v3_req \]/,/^\[/{s/keyUsage.*/keyUsage = critical, digitalSignature, keyEncipherment/}' "$OUT"
    sed -i '/^\[ v3_req \]/,/^\[/{/extendedKeyUsage/ d}' "$OUT"
    sed -i '/keyUsage = critical, digitalSignature, keyEncipherment/ a\
    extendedKeyUsage = serverAuth
    ' "$OUT"

Create OpenSSL configuration for the client certificate

  1. Copy the default OpenSSL configuration file to a new file named openssl-client.cnf:

    OUT="/usr/lib/ssl/openssl-client.cnf"
    cp /usr/lib/ssl/openssl.cnf "$OUT"
  2. Update the [ req ] section:

    sed -i '/^\[ req \]/,/^\[/{/req_extensions/ d}' "$OUT"
    sed -i '/^\[ req \]/,/^\[/{/x509_extensions/ a\
    req_extensions = v3_req
    }' "$OUT"
  3. Update the [ v3_req ] section:

    sed -i '/^\[ v3_req \]/,/^\[/{s/basicConstraints.*/basicConstraints = critical, CA:FALSE/}' "$OUT"
    sed -i '/^\[ v3_req \]/,/^\[/{s/keyUsage.*/keyUsage = critical, digitalSignature/}' "$OUT"
    sed -i '/^\[ v3_req \]/,/^\[/{/extendedKeyUsage/ d}' "$OUT"
    sed -i '/^\[ v3_req \]/,/^\[/{/nsCertType/ d}' "$OUT"
    sed -i '/keyUsage = critical, digitalSignature/ a\
    extendedKeyUsage = clientAuth
    ' "$OUT"
    sed -i '/extendedKeyUsage = clientAuth/ a\
    nsCertType = client
    ' "$OUT"

Generate the server key and certificate

Tip

We're storing the files in the root directory.

Important

This tutorial assumes openssl.cnf is located in /usr/lib/ssl/. Update the path in the following commands accordingly.

  1. Generate the server private key on CryptoHub:

    pkcs11-tool --module $FXPKCS11_MODULE --login --key-type rsa:2048 --pin "$(cat /root/pkcs11-pin.txt)" --label "OpenVPN-Server-Key" --id 02 --keypairgen --usage-sign
  2. Generate the PKCS #11 URI reference file for the server key:

    • For Ubuntu/Debian:

      python3 ~/src/pkcs11-provider/tools/uri2pem.py "pkcs11:type=private;object=OpenVPN-Server-Key" > server.key
    • For RHEL:

      python3 /usr/local/src/pkcs11-provider/tools/uri2pem.py "pkcs11:type=private;object=OpenVPN-Server-Key" > server.key
  3. Generate the server CSR:

    openssl req -new -key server.key -out server.csr -subj "/CN=OpenVPN Server" -config /usr/lib/ssl/openssl-server.cnf
  4. Sign the server certificate:

    openssl x509 -req -in server.csr -CA ca.crt -CAkey ca.key -CAcreateserial -out server.crt -days 365 -extfile /usr/lib/ssl/openssl-server.cnf -extensions v3_req
    • From the above commands, you get three files:

      • Server key (server.key)

      • Server certificate (server.crt)

      • Server CSR (server.csr)

Generate the client certificate and package

Tip

We're storing the files in the root directory.

Important

This tutorial assumes openssl.cnf is located in /usr/lib/ssl/. Update the path in the following commands accordingly.

  1. Generate the client private key:

    openssl genpkey -algorithm RSA -out client.key -pkeyopt rsa_keygen_bits:2048
  2. Generate the client CSR:

    openssl req -new -key client.key -out client.csr -subj "/CN=etest" -config /usr/lib/ssl/openssl-client.cnf
  3. (Optional) Generate the client CSR compatible with auto-login:

    openssl req -new -key client.key -out client.csr -subj "/role=AUTOLOGIN/CN=etest" -config /usr/lib/ssl/openssl-client.cnf
  4. Sign the client certificate:

    openssl x509 -req -in client.csr -CA ca.crt -CAkey ca.key -CAcreateserial -out client.crt -days 365 -extfile /usr/lib/ssl/openssl-client.cnf -extensions v3_req
  5. Create the P12 bundle:

    openssl pkcs12 -export -inkey client.key -in client.crt -out etest.p12 -name "etest"
  6. Enter the P12 password when prompted.

    • From the above commands, you get four files:

      • Client key (client.key)

      • Client certificate (client.crt)

      • Client CSR (client.csr)

      • Client P12 file (etest.p12)

This step integrates the certificates and keys generated earlier into Access Server. The server uses the PKCS #11-backed keys stored in the CryptoHub, while Access Server reads the associated certificate and parameter files from its configuration database. You’ll then configure a test user and connect with a server-locked profile.

Prepare the Access Server key directory

  1. Connect to the Access Server console and get root privileges.

  2. Create a directory for your external PKI files:

    mkdir epki && cd epki
  3. Copy the required files into the directory:

    cp ../ca.crt ./
    cp ../server.crt ./
    cp ../server.key ./

Generate required OpenVPN keys and parameters

  1. Generate a tls_auth key:

    /usr/local/openvpn_as/scripts/certool --tls_auth
  2. Generate Diffie-Hellman parameters for the OpenVPN server:

    openssl dhparam -out dh.pem 2048
  3. For Access Server 2.7 and newer, you must also generate your auth token and add the generated file:

    /usr/local/openvpn_as/scripts/certool --auth_token 
  4. Configure X509 explicit/extended key usage based on RFC3280 TLS rules:

    /usr/local/openvpn_as/scripts/sacli --key "external_pki.remote_cert_usage" --value eku ConfigPut
  5. Configure the use of the X509 “role” attribute for the declaration of auto-login permission:

    /usr/local/openvpn_as/scripts/sacli --key "external_pki.autologin_x509_spec" --value "role,,AUTOLOGIN" ConfigPut
  6. Generate the tls-crypt-v2 key (for Access Server 2.9.0 and higher only):

    /usr/local/openvpn_as/scripts/certool --tls_crypt2_server 

Import certificates and keys into Access Server

  1. Load the files into the Access Server configuration database:

    /usr/local/openvpn_as/scripts/sacli --key "external_pki.ta_key" --value_file ta.key ConfigPut
    /usr/local/openvpn_as/scripts/sacli --key "external_pki.ca_crt" --value_file ca.crt ConfigPut
    /usr/local/openvpn_as/scripts/sacli --key "external_pki.server_crt" --value_file server.crt ConfigPut
    /usr/local/openvpn_as/scripts/sacli --key "external_pki.server_key" --value_file server.key ConfigPut
    /usr/local/openvpn_as/scripts/sacli --key "external_pki.dh_pem" --value_file dh.pem ConfigPut
    /usr/local/openvpn_as/scripts/sacli --key "external_pki.auth_token_key" --value_file auth_token.key ConfigPut
    /usr/local/openvpn_as/scripts/sacli --key "external_pki.tls_cryptv2_server" --value_file tls_crypt2.key ConfigPut
  2. Restart Access Server:

    systemctl restart openvpnas

Create and configure a test client

To test our example, we generate a test client, etest.

  1. Sign in to the Admin Web UI.

  2. Click User Management > User Permissions.

  3. Create the new user, etest, and click More Settings to enter a password.

  4. (Optional, for environments using auto-login profiles). Check Allow Auto-login for the user.

  5. Finally, generate a server-locked profile. The profile will be stored in etest.ovpn:

    /usr/local/openvpn_as/scripts/sacli GetGeneric >etest.ovpn
    • For generating an auto-login profile:

      /usr/local/openvpn_as/scripts/sacli --user etest GetAutologin >etest.ovpn
  6. Copy these two files to the client machine:

    • Client P12 file (etest.p12)

    • Client profile (etest.ovpn)

Install the profile and certificate in OpenVPN Connect v3

  1. Launch OpenVPN Connect v3.

  2. Import the connection profile, etest.ovpn.

  3. Click Menu > Certificate & Tokens.

  4. Under PKCS#12, click the Add icon.

  5. Select your client P12 file (etest.p12).

  6. Enter the password for this file that you previously configured and click OK.

  7. Go back to the Home.

  8. Click Menu > My Profiles.

  9. Click or tap the Edit icon for the profile.

  10. Under Certificate and Key, click or tap Assign.

  11. Select the digital certificate file and click Confirm.

  12. Save the changes.

  13. Click or tap to connect.

With the release of Access Server 2.14.2, we've made configuring client connection profiles for ePKI easier. Previously, creating these profiles required using the command line, as noted in the tutorial. However, in version 2.14.2 and later, you can now create and manage ePKI client connection profiles directly from Access Server's Client Web UI.

There are two types of ePKI profiles available:

  1. Generic ePKI profile:

    epki-generic.png
    • This profile requires the user to authenticate with a password when connecting.

    • Ideal for environments where a password-based security layer is needed in addition to certificate-based authentication.

  2. Auto-login ePKI profile;

    epki-autologin.png
    • This profile automatically uses the certificate for authentication without requiring a password.

    • Suitable for unattended devices or systems where automatic, certificate-based login is needed.

In addition, the Import Profile from URL functionality in OpenVPN Connect allows users to import these connection profiles directly, making the configuration process faster and more seamless.

This update simplifies the ePKI setup, providing more flexibility and reducing the reliance on the command line.