Setting Up Database Monitoring for SQL Server on Amazon RDS

Database Monitoring provides deep visibility into your Microsoft SQL Server databases by exposing query metrics, query samples, explain plans, database states, failovers, and events.

Do the following steps to enable Database Monitoring with your database:

  1. Configure the AWS integration
  2. Grant the Agent access
  3. Install the Agent
  4. Install the RDS integration

Before you begin

Supported SQL Server versions
2014, 2016, 2017, 2019, 2022
Supported Agent versions
7.41.0+
Performance impact
The default Agent configuration for Database Monitoring is conservative, but you can adjust settings such as the collection interval and query sampling rate to better suit your needs. For most workloads, the Agent represents less than one percent of query execution time on the database and less than one percent of CPU.

Database Monitoring runs as an integration on top of the base Agent (see benchmarks).
Proxies, load balancers, and connection poolers
The Datadog Agent must connect directly to the host being monitored. The Agent should not connect to the database through a proxy, load balancer, or connection pooler. If the Agent connects to different hosts while it is running (as in the case of failover, load balancing, and so on), the Agent calculates the difference in statistics between two hosts, producing inaccurate metrics.
Data security considerations
Read about how Database Management handles sensitive information for information about what data the Agent collects from your databases and how to ensure it is secure.

Configure the AWS integration

Enable Standard Collection in the Resource Collection section of your Amazon Web Services integration tile.

Grant the Agent access

The Datadog Agent requires read-only access to the database server to collect statistics and queries.

Create a read-only login to connect to your server and grant the required permissions:

USE [master];
CREATE LOGIN datadog WITH PASSWORD = '<PASSWORD>';
GO
--Set context to msdb database and create datadog user
USE [msdb];
CREATE USER datadog FOR LOGIN datadog;
-- To use Log Shipping Monitoring (available in Agent v7.50+), uncomment the next line:
-- GRANT SELECT to datadog;
GO
--Switch back to master and grant datadog user server permissions
USE [master];
GRANT VIEW SERVER STATE to datadog;
GRANT VIEW ANY DEFINITION to datadog;
GO

Create the datadog user in each additional application database:

USE [database_name];
CREATE USER datadog FOR LOGIN datadog;

This is required because RDS does not permit granting CONNECT ANY DATABASE. The Datadog Agent needs to connect to each database to collect database-specific file I/O statistics.

Install the Agent

Because AWS does not grant direct host access, the Datadog Agent must be installed on a separate host where it is able to talk to the SQL Server host. There are several options for installing and running the Agent.

Note: For AlwaysOn users, the Agent must be installed on a separate server and connected to the cluster through the listener endpoint. This is because information about Availability Group (AG) secondary replicas is collected from the primary replica. Additionally, installing the Agent in this way helps to keep it up and running in the event of a failover. To start collecting SQL Server telemetry, first install the Datadog Agent.

Create the SQL Server Agent conf file C:\ProgramData\Datadog\conf.d\sqlserver.d\conf.yaml. See the sample conf file for all available configuration options.

init_config:
instances:
  - dbm: true
    host: '<HOSTNAME>,<SQL_PORT>'
    username: datadog
    password: '<PASSWORD>'
    connector: adodbapi
    adoprovider: MSOLEDBSQL
    include_ao_metrics: true  # Optional: For AlwaysOn users
    tags:  # Optional
      - 'service:<CUSTOM_SERVICE>'
      - 'env:<CUSTOM_ENV>'

To use Windows Authentication, set connection_string: "Trusted_Connection=yes" and omit the username and password fields.

The agent supports SQL Server Browser Service in versions 7.41+. To enable SSBS, provide a port of 0 in the host string: <HOSTNAME>,0.

Use the service and env tags to link your database telemetry to other telemetry through a common tagging scheme. See Unified Service Tagging on how these tags are used throughout Datadog.

Supported Drivers

Microsoft ADO

The recommended ADO provider is Microsoft OLE DB Driver. Ensure the driver is installed on the host where the agent is running.

connector: adodbapi
adoprovider: MSOLEDBSQL19  # Replace with MSOLEDBSQL for versions 18 and lower

The other two providers, SQLOLEDB and SQLNCLI, are considered deprecated by Microsoft and should no longer be used.

ODBC

The recommended ODBC driver is Microsoft ODBC Driver. Ensure the driver is installed on the host where the Agent is running.

connector: odbc
driver: '{ODBC Driver 18 for SQL Server}'

Once all Agent configuration is complete, restart the Datadog Agent.

Validate

Run the Agent’s status subcommand and look for sqlserver under the Checks section. Navigate to the Databases page in Datadog to get started.

Note: For AlwaysOn users, the Agent must be installed on a separate server and connected to the cluster through the listener endpoint. This is because information about Availability Group (AG) secondary replicas is collected from the primary replica. Additionally, installing the Agent in this way helps to keep it up and running in the event of a failover. To start collecting SQL Server telemetry, first install the Datadog Agent.

On Linux, the Datadog Agent additionally requires an ODBC SQL Server driver to be installed—for example, the Microsoft ODBC driver. Once an ODBC SQL Server is installed, copy the odbc.ini and odbcinst.ini files into the /opt/datadog-agent/embedded/etc folder.

Use the odbc connector and specify the proper driver as indicated in the odbcinst.ini file.

Create the SQL Server Agent conf file /etc/datadog-agent/conf.d/sqlserver.d/conf.yaml. See the sample conf file for all available configuration options.

init_config:
instances:
  - dbm: true
    host: '<HOSTNAME>,<SQL_PORT>'
    username: datadog
    password: '<PASSWORD>'
    connector: odbc
    driver: '<Driver from the `odbcinst.ini` file>'
    include_ao_metrics: true  # Optional: For AlwaysOn users
    tags:  # Optional
      - 'service:<CUSTOM_SERVICE>'
      - 'env:<CUSTOM_ENV>'

Use the service and env tags to link your database telemetry to other telemetry through a common tagging scheme. See Unified Service Tagging on how these tags are used throughout Datadog.

Once all Agent configuration is complete, restart the Datadog Agent.

Validate

Run the Agent’s status subcommand and look for sqlserver under the Checks section. Navigate to the Databases page in Datadog to get started.

Note: For AlwaysOn users, the Agent must be installed on a separate server and connected to the cluster through the listener endpoint. This is because information about Availability Group (AG) secondary replicas is collected from the primary replica. Additionally, installing the Agent in this way helps to keep it up and running in the event of a failover. To configure the Database Monitoring Agent running in a Docker container, set the Autodiscovery Integration Templates as Docker labels on your Agent container.

Note: The Agent must have read permission on the Docker socket for Autodiscovery of labels to work.

Replace the values to match your account and environment. See the sample conf file for all available configuration options.

export DD_API_KEY=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
export DD_AGENT_VERSION=7.35.0

docker run -e "DD_API_KEY=${DD_API_KEY}" \
  -v /var/run/docker.sock:/var/run/docker.sock:ro \
  -l com.datadoghq.ad.check_names='["sqlserver"]' \
  -l com.datadoghq.ad.init_configs='[{}]' \
  -l com.datadoghq.ad.instances='[{
    "dbm": true,
    "host": "<HOSTNAME>",
    "port": <SQL_PORT>,
    "connector": "odbc",
    "driver": "FreeTDS",
    "username": "datadog",
    "password": "<PASSWORD>",
    "include_ao_metrics": true,  # Optional: For AlwaysOn users
    "tags": [
      "service:<CUSTOM_SERVICE>"
      "env:<CUSTOM_ENV>"
    ]
  }]' \
  gcr.io/datadoghq/agent:${DD_AGENT_VERSION}

Use the service and env tags to link your database telemetry to other telemetry through a common tagging scheme. See Unified Service Tagging on how these tags are used throughout Datadog.

Validate

Run the Agent’s status subcommand and look for sqlserver under the Checks section. Alternatively, navigate to the Databases page in Datadog to get started.

Note: For AlwaysOn users, the Agent must be installed on a separate server and connected to the cluster through the listener endpoint. This is because information about Availability Group (AG) secondary replicas is collected from the primary replica. Additionally, installing the Agent in this way helps to keep it up and running in the event of a failover. If you have a Kubernetes cluster, use the Datadog Cluster Agent for Database Monitoring.

If cluster checks are not already enabled in your Kubernetes cluster, follow the instructions to enable cluster checks. You can configure the Cluster Agent either with static files mounted in the Cluster Agent container, or by using Kubernetes service annotations:

Command line with Helm

Execute the following Helm command to install the Datadog Cluster Agent on your Kubernetes cluster. Replace the values to match your account and environment:

helm repo add datadog https://helm.datadoghq.com
helm repo update

helm install <RELEASE_NAME> \
  --set 'datadog.apiKey=<DATADOG_API_KEY>' \
  --set 'clusterAgent.enabled=true' \
  --set 'clusterChecksRunner.enabled=true' \
  --set "clusterAgent.confd.sqlserver\.yaml=cluster_check: true
init_config:
instances:
  - dbm: true
    host: <HOSTNAME>\,1433
    username: datadog
    password: '<PASSWORD>'
    connector: 'odbc'
    driver: 'FreeTDS'
    include_ao_metrics: true  # Optional: For AlwaysOn users
    tags:  # Optional
      - 'service:<CUSTOM_SERVICE>'
      - 'env:<CUSTOM_ENV>'"\
  datadog/datadog

Configure with mounted files

To configure a cluster check with a mounted configuration file, mount the configuration file in the Cluster Agent container on the path: /conf.d/sqlserver.yaml:

cluster_check: true  # Make sure to include this flag
init_config:
instances:
  - dbm: true
    host: '<HOSTNAME>'
    port: <SQL_PORT>
    username: datadog
    password: '<PASSWORD>'
    connector: 'odbc'
    driver: 'FreeTDS'
    include_ao_metrics: true  # Optional: For AlwaysOn users
    tags:  # Optional
      - 'service:<CUSTOM_SERVICE>'
      - 'env:<CUSTOM_ENV>

Configure with Kubernetes service annotations

Rather than mounting a file, you can declare the instance configuration as a Kubernetes Service. To configure this check for an Agent running on Kubernetes, create a Service in the same namespace as the Datadog Cluster Agent:

apiVersion: v1
kind: Service
metadata:
  name: sqlserver-datadog-check-instances
  annotations:
    ad.datadoghq.com/service.check_names: '["sqlserver"]'
    ad.datadoghq.com/service.init_configs: '[{}]'
    ad.datadoghq.com/service.instances: |
      [
        {
          "dbm": true,
          "host": "<HOSTNAME>",
          "port": "<SQL_PORT>",
          "username": "datadog",
          "password": "<PASSWORD>",
          "connector": "odbc",
          "driver": "FreeTDS",
          "include_ao_metrics": true,  # Optional: For AlwaysOn users
          "tags": ["service:<CUSTOM_SERVICE>", "env:<CUSTOM_ENV>"]  # Optional
        }
      ]      
spec:
  ports:
  - port: 1433
    protocol: TCP
    targetPort: 1433
    name: sqlserver

The Cluster Agent automatically registers this configuration and begins running the SQL Server check.

To avoid exposing the datadog user’s password in plain text, use the Agent’s secret management package and declare the password using the ENC[] syntax.

Example Agent Configurations

Connecting with DSN using the ODBC driver on Linux

  1. Locate the odbc.ini and odbcinst.ini files. By default, these are placed in the /etc directory when installing ODBC.

  2. Copy the odbc.ini and odbcinst.ini files into the /opt/datadog-agent/embedded/etc folder.

  3. Configure your DSN settings as follows:

    odbcinst.ini must provide at least one section header and ODBC driver location.

    Example:

    [ODBC Driver 18 for SQL Server]
    Description=Microsoft ODBC Driver 18 for SQL Server
    Driver=/opt/microsoft/msodbcsql18/lib64/libmsodbcsql-18.3.so.2.1
    UsageCount=1
    

    odbc.ini must provide a section header and a Driver path that matches odbcinst.ini.

    Example:

    [datadog]
    Driver=/opt/microsoft/msodbcsql18/lib64/libmsodbcsql-18.3.so.2.1
    
  4. Update the /etc/datadog-agent/conf.d/sqlserver.d/conf.yaml file with your DSN information.

    Example:

    instances:
      - dbm: true
        host: 'localhost,1433'
        username: datadog
        password: '<PASSWORD>'
        connector: 'odbc'
        driver: '{ODBC Driver 18 for SQL Server}' # This is the section header of odbcinst.ini
        dsn: 'datadog' # This is the section header of odbc.ini
    
  5. Restart the Agent.

Using AlwaysOn

Note: For AlwaysOn users, the Agent must be installed on a separate server and connected to the cluster through the listener endpoint. This is because information about Availability Group (AG) secondary replicas is collected from the primary replica. Additionally, installing the Agent in this way helps to keep it up and running in the event of a failover.

instances:
  - dbm: true
    host: 'shopist-prod,1433'
    username: datadog
    password: '<PASSWORD>'
    connector: adodbapi
    adoprovider: MSOLEDBSQL
    include_ao_metrics: true  # If Availability Groups is enabled
    include_fci_metrics: true   # If Failover Clustering is enabled

One Agent connecting to multiple hosts

It is common to configure a single Agent host to connect to multiple remote database instances (see Agent installation architectures for DBM). To connect to multiple hosts, create an entry for each host in the SQL Server integration config. In these cases, Datadog recommends limiting the number of instances per Agent to a maximum of 10 database instances to guarantee reliable performance.

init_config:
instances:
  - dbm: true
    host: 'example-service-primary.example-host.com,1433'
    username: datadog
    connector: adodbapi
    adoprovider: MSOLEDBSQL
    password: '<PASSWORD>'
    tags:
      - 'env:prod'
      - 'team:team-discovery'
      - 'service:example-service'
  - dbm: true
    host: 'example-service–replica-1.example-host.com,1433'
    connector: adodbapi
    adoprovider: MSOLEDBSQL
    username: datadog
    password: '<PASSWORD>'
    tags:
      - 'env:prod'
      - 'team:team-discovery'
      - 'service:example-service'
  - dbm: true
    host: 'example-service–replica-2.example-host.com,1433'
    connector: adodbapi
    adoprovider: MSOLEDBSQL
    username: datadog
    password: '<PASSWORD>'
    tags:
      - 'env:prod'
      - 'team:team-discovery'
      - 'service:example-service'
    [...]

Storing passwords securely

While it is possible to declare passwords directly in the Agent configuration files, it is a more secure practice to encrypt and store database credentials elsewhere using secret management software such as Vault. The Agent is able to read these credentials using the ENC[] syntax. Review the secrets management documentation for the required setup to store these credentials. The following example shows how to declare and use those credentials:

init_config:
instances:
  - dbm: true
    host: 'localhost,1433'
    connector: adodbapi
    adoprovider: MSOLEDBSQL
    username: datadog
    password: 'ENC[datadog_user_database_password]'

Running custom queries

To collect custom metrics, use the custom_queries option. See the sample sqlserver.d/conf.yaml for more details.

init_config:
instances:
  - dbm: true
    host: 'localhost,1433'
    connector: adodbapi
    adoprovider: MSOLEDBSQL
    username: datadog
    password: '<PASSWORD>'
    custom_queries:
    - query: SELECT age, salary, hours_worked, name FROM hr.employees;
      columns:
        - name: custom.employee_age
          type: gauge
        - name: custom.employee_salary
           type: gauge
        - name: custom.employee_hours
           type: count
        - name: name
           type: tag
      tags:
        - 'table:employees'

Working with hosts through a remote proxy

If the Agent must connect to a database host through a remote proxy, all telemetry is tagged with the hostname of the proxy rather than the database instance. Use the reported_hostname option to set a custom override of the hostname detected by the Agent.

init_config:
instances:
  - dbm: true
    host: 'localhost,1433'
    connector: adodbapi
    adoprovider: MSOLEDBSQL
    username: datadog
    password: '<PASSWORD>'
    reported_hostname: products-primary
  - dbm: true
    host: 'localhost,1433'
    connector: adodbapi
    adoprovider: MSOLEDBSQL
    username: datadog
    password: '<PASSWORD>'
    reported_hostname: products-replica-1

Discovering ports automatically

SQL Server Browser Service, Named Instances, and other services can automatically detect port numbers. You can use this instead of hardcoding port numbers in connection strings. To use the Agent with one of these services, set the port field to 0.

For example, a Named Instance config:

init_config:
instances:
  - host: <hostname\instance name>
    port: 0

Install the RDS integration

To collect more comprehensive database metrics and logs from AWS, install the RDS integration.

Further reading