✨ New: Try our AI‑powered Search (Ctrl + K) — Read more

Telemetry Ingestion via SNMP

Prev Next

This article describes how to configure the Telemetry Collector to poll SNMP-enabled network devices for metrics and forward them through the Sensor Collector to Crosswork Assurance. This approach is useful for ingesting interface statistics, system information, and operational data from routers, switches, firewalls, and other network equipment -- including legacy and multi-vendor devices that do not support streaming telemetry.

Out-of-the-box vs. Custom Telemetry

Crosswork Assurance provides default Telemetry Collector configurations for IOS-XE and IOS-XR routers. This guide covers SNMP as a custom data source that requires a custom Telegraf configuration (TOML). For custom telemetry ingestion engagements, contact your Cisco CX or Partner representative.

The Telemetry Collector embeds Telegraf, which includes the snmp input plugin. By customizing the Telemetry Collector's Telegraf configuration (TOML), you can configure it to poll SNMP agents on network devices and convert the results to OpenMetrics format for ingestion into Crosswork Assurance.

Note: This approach replaces the older Scraper-mode Sensor Collector pattern (polling an external snmp-exporter), which is still supported but no longer recommended. The Telegraf-based Telemetry Collector approach provides more flexibility and is the standard method for custom telemetry ingestion.

Prerequisites

  • A deployed Gateway Sensor Collector with the OpenMetrics Gateway connector enabled.
  • Target network devices with SNMP enabled (v2c or v3).
  • Knowledge of SNMP community strings (v2c) or SNMPv3 credentials (username, auth/privacy protocols and passwords).
  • Network connectivity from the Telemetry Collector to target devices on UDP port 161.
  • Access to the Crosswork Assurance UI with permissions to create Telemetry Collector configurations.
  • An ingestion dictionary created via Telemetry Ingestion Staging that defines the metrics and dimensions for your SNMP data.

Step 1: Design the Telegraf Configuration (TOML)

The Telemetry Collector's runtime behavior is controlled by a Telegraf TOML configuration file. When you create a Telemetry Collector with a Custom Telegraf configuration in the UI, you upload a TOML file that defines:

  • Inputs -- which SNMP agents to poll and which OIDs/tables to collect
  • Processors -- how to build session identity tags for Crosswork Assurance

Important: Do not include an [[outputs.*]] section in the TOML file. The product automatically appends its own output configuration for forwarding data to the Sensor Collector. Including an output section causes a "violation of Telegraf's configuration" error.

Key Design Principles

  • The objectType tag is required. The Telemetry Collector agent requires an objectType tag whose value matches the name of the ingestion dictionary that defines the metrics and dimensions being ingested for the objects. Use Telemetry Ingestion Staging to create and manage your ingestion dictionaries.

  • Session identity processors are required. The Telemetry Collector opens one reporting stream per sessionId. Include [[processors.template]] blocks that build sessionId and sessionName from your parsed tags.

  • Use field for single OID values, table for SNMP tables. Fields retrieve individual OIDs (like snmpget). Tables walk entire MIB tables (like snmptable), creating one metric row per table entry.

SNMP Versions

The snmp input plugin supports SNMPv1, SNMPv2c, and SNMPv3:

Version Authentication Use Case
v1 Community string Legacy devices only. Limited functionality.
v2c Community string Most common for read-only monitoring. Supports GETBULK for efficient table retrieval.
v3 Username + auth/privacy protocols Required when security policies mandate encrypted SNMP. Supports SHA/SHA-256 authentication and AES encryption.

Example: SNMP TOML Configuration (SNMPv2c)

The following example polls interface statistics and system information from network devices using SNMPv2c.

###############################################################################
# SNMP Input -- poll network devices
###############################################################################
[[inputs.snmp]]
  ## List of SNMP agents (devices) to poll
  agents = ["udp://switch-1:161", "udp://router-1:161"]

  ## Polling interval
  interval = "60s"

  ## SNMP version: 1, 2, or 3
  version = 2

  ## SNMPv2c community string
  community = "public"

  ## Timeout per request
  timeout = "10s"

  ## Number of retries
  retries = 3

  ## Tag the source device for identification
  agent_host_tag = "source"

  # objectType must match the ingestion dictionary name.
  [inputs.snmp.tags]
    objectType = "snmp_device_metrics"

  ##---------------------------------------------------------------------------
  ## System-level fields (single OID values)
  ##---------------------------------------------------------------------------
  [[inputs.snmp.field]]
    oid = "RFC1213-MIB::sysName.0"
    name = "sysName"
    is_tag = true

  [[inputs.snmp.field]]
    oid = "RFC1213-MIB::sysUpTime.0"
    name = "sysUptime"
    conversion = "float(2)"

  [[inputs.snmp.field]]
    oid = "RFC1213-MIB::sysDescr.0"
    name = "sysDescr"

  ##---------------------------------------------------------------------------
  ## Interface table -- one row per interface
  ##---------------------------------------------------------------------------
  [[inputs.snmp.table]]
    oid = "IF-MIB::ifTable"
    name = "interface"
    inherit_tags = ["sysName"]

    [[inputs.snmp.table.field]]
      oid = "IF-MIB::ifDescr"
      name = "ifDescr"
      is_tag = true

    [[inputs.snmp.table.field]]
      oid = "IF-MIB::ifOperStatus"
      name = "ifOperStatus"

    [[inputs.snmp.table.field]]
      oid = "IF-MIB::ifInOctets"
      name = "ifInOctets"

    [[inputs.snmp.table.field]]
      oid = "IF-MIB::ifOutOctets"
      name = "ifOutOctets"

    [[inputs.snmp.table.field]]
      oid = "IF-MIB::ifInErrors"
      name = "ifInErrors"

    [[inputs.snmp.table.field]]
      oid = "IF-MIB::ifOutErrors"
      name = "ifOutErrors"

###############################################################################
# Session Identity (required)
#
# Build sessionId from the device name and interface.
# Each device+interface pair produces its own reporting stream.
###############################################################################
[[processors.template]]
  namepass = ["snmp*", "interface*"]
  tag = "sessionId"
  template = '{{ .Tag "sysName" }}_{{ .Tag "ifDescr" }}_snmp'

[[processors.template]]
  namepass = ["snmp*", "interface*"]
  tag = "sessionName"
  template = '{{ .Tag "sysName" }}_{{ .Tag "ifDescr" }}_snmp'

Example: SNMPv3 Configuration

For environments requiring SNMPv3 authentication and encryption, replace the community line with SNMPv3 parameters:

[[inputs.snmp]]
  agents = ["udp://secure-router:161"]
  version = 3

  ## SNMPv3 Security
  sec_name = "snmpuser"
  auth_protocol = "SHA256"
  auth_password = "${SNMP_AUTH_PASSWORD}"
  sec_level = "authPriv"
  priv_protocol = "AES256"
  priv_password = "${SNMP_PRIV_PASSWORD}"

  agent_host_tag = "source"

  [inputs.snmp.tags]
    objectType = "snmp_device_metrics"

  # ... fields and tables same as above ...

Security note: Use environment variables (${SNMP_AUTH_PASSWORD}) for SNMP credentials rather than hardcoding them in the TOML file. Telegraf supports secret stores for managing sensitive values.

SNMP Input Plugin Reference

The snmp input plugin supports many additional options including SNMP table walking, MIB translation (via gosmi or netsnmp backends), secondary index tables, and bulk request tuning.

For the complete list of configuration options, see the Telegraf SNMP input plugin documentation.


Step 2: Create the Telemetry Collector in the UI

For general instructions on creating and managing Telemetry Collector configurations, see Configure Telemetry Collector. The steps below are specific to uploading a custom SNMP TOML configuration.

  1. In the Crosswork Assurance UI, navigate to Sensors > Collectors.
  2. Click the + button to add a new collector.
  3. In the New collector dialog, select Telemetry and click Configure collector.
  4. Enter a Name for the Telemetry Collector (e.g., SNMP_Device_Collector).
  5. Set the Telegraf Configuration dropdown to Custom.
  6. In the Custom Telegraf.conf section, click the upload icon and select your TOML file.
  7. Enter the Sensor Collector Data Address -- the hostname or IP of your Gateway Sensor Collector.
  8. Enter the Sensor Collector Data Port -- the data port of your Gateway Sensor Collector (e.g., 39888).
  9. Configure SSL options as needed:
    • Use SSL communication -- enable for encrypted connections to the Sensor Collector
    • Allow self-signed certificates -- enable if the Sensor Collector uses self-signed certificates
    • Skip SSL hostname check -- enable if the hostname does not match the certificate
  10. Click the checkmark (save) button.

Generate the Auth Token

After saving the Telemetry Collector configuration:

  1. On the Summary tab, click Generate auth token.
  2. Copy the Agent secret (YAML) content. This contains the agentId and authenticationToken that the Telemetry Collector container needs to authenticate with Crosswork Assurance.
  3. Save this content as secrets.yaml in your deployment directory.

Important: The auth token is displayed only once. Copy and save it immediately.

Alternative: API Method (Base64)

You can also create the Telemetry Collector configuration via API by Base64-encoding the TOML file and submitting it as the customTransformationConfig field.

  1. Base64-encode your TOML file:
    base64 -w 0 my-config.toml > config_base64.txt
    
  2. Use the Agent Configuration API to create the Telemetry Collector. For detailed API instructions, see Telemetry Collector Configuration - MDT Dial-Out (alternate API method).

Step 3: Deploy the Telemetry Collector

Deploy the Telemetry Collector container using the standard procedure for your environment:

The Telemetry Collector connects to the Sensor Collector, receives its custom TOML configuration, and begins polling the configured SNMP agents.

Note: Ensure the Telemetry Collector container has network access to the target devices on UDP port 161. For Docker deployments, the container must be on a network that can reach the device management interfaces. For Kubernetes deployments, verify that UDP traffic to port 161 is not blocked by network policies.


Step 4: Verify

  1. Check the Telemetry Collector logs for successful startup:
    Config watcher started
    Loading config: /etc/Telemetry/Telemetry.conf
    
  2. Confirm that metrics appear in the Crosswork Assurance UI under the expected monitored objects.
  3. To enable debug logging for troubleshooting:
    docker exec -it <container_id> sh
    agentstatus telemetry datapathLogging true
    exit
    docker logs <container_id> -f
    

Troubleshooting

Symptom Cause Resolution
No data from device Wrong community string or device unreachable For example, test with snmpwalk -v2c -c <community> <host> sysName.0. Verify UDP port 161 is open.
Timeout errors Device slow to respond or network latency Increase timeout (e.g., "15s") and retries in the TOML configuration.
"no such object" errors OID not supported by device Verify the device supports the requested MIB/OID. For example, use snmpwalk to discover available OIDs.
Authentication failure (v3) Wrong credentials or security level Verify sec_name, auth_protocol, auth_password, sec_level, priv_protocol, and priv_password match the device's SNMPv3 user configuration.
Missing interface rows GETBULK max-repetitions too low Increase max_repetitions (default 10) for devices with many interfaces.
"violation of Telegraf's configuration" Output section defined in the TOML Remove any [[outputs.*]] blocks from the TOML file. The product manages the output automatically.
Collector status "Unregistered" Container not deployed or not connected Deploy the Telemetry Collector container and verify it can reach the Sensor Collector address and port.