> ## Documentation Index
> Fetch the complete documentation index at: https://docs.flashduty.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Wazuh alert integration

> Send Wazuh alerts to Flashduty On-call through the manager's built-in Shuffle integration.

The Wazuh manager's Integrator module (integratord) has a built-in `shuffle` integration: it POSTs each Wazuh alert as JSON to the configured `hook_url`, with no authentication header. Set `hook_url` to your Flashduty push URL to send Wazuh alerts to Flashduty On-call. Each Wazuh alert becomes one Flashduty alert.

<div className="hide">
  ## In Flashduty On-call

  ***

  You can get the integration push URL in either of the following ways.

  ### Use a dedicated integration

  1. In the Flashduty console, select **Channel** and open a channel
  2. Select **Configuration** → **Integrations** → **Private integration**, then click **Add an integration**
  3. Select **Wazuh** and click **Save**
  4. Open the new integration card and copy the **Push URL**

  ### Use a shared integration

  1. In the Flashduty console, select **Integration Center → Alert Events**
  2. Select **Wazuh** and enter an integration name
  3. Configure the default route and select a channel. You can add more rules under **Routes** after creation
  4. Click **Save** and copy the generated **Push URL**
</div>

## In Wazuh

***

The Integrator module runs only on the Wazuh manager. The configuration file is `/var/ossec/etc/ossec.conf`, and you need root access on the manager.

<Steps>
  <Step title="Add the shuffle integration">
    Add the following to `<ossec_config>` in `ossec.conf`, replacing `hook_url` with the Flashduty push URL:

    ```xml theme={null}
    <integration>
      <name>shuffle</name>
      <hook_url>https://api.flashcat.cloud/event/push/alert/wazuh?integration_key=YOUR_INTEGRATION_KEY</hook_url>
      <level>10</level>
      <alert_format>json</alert_format>
    </integration>
    ```

    * `<alert_format>json</alert_format>` is required. Flashduty parses only JSON alerts
    * `<level>` forwards only alerts whose rule level is at or above the value. A fresh manager sends a burst of level-7 SCA checks, so `10` is a good starting value; set `7` if you want lower-level alerts and filter them with `<rule_id>` or `<group>`. You can also filter with `<rule_id>` (comma-separated rule IDs), `<group>` (rule groups) and `<event_location>` (log source)
    * Do not set `<api_key>`. Flashduty authenticates with the `integration_key` in the URL
    * Do not use `<options>` to override the `id` field. Flashduty uses it to tell alerts apart
  </Step>

  <Step title="Restart the manager">
    ```bash theme={null}
    systemctl restart wazuh-manager
    ```

    For Docker deployments, restart the manager container.
  </Step>

  <Step title="Trigger and verify">
    1. On a monitored host, trigger an alert at or above `<level>`, for example several failed SSH password attempts (rule 5763, level 10)
    2. Confirm the alert arrives in Flashduty
    3. If nothing arrives, check `/var/ossec/logs/integrations.log` and `/var/ossec/logs/ossec.log` on the manager

    Wazuh has no "send test notification" feature. The shuffle script skips alerts from rules 5710, 86001-86003, 87900-87904, 87924, 87928, 87929, 87932 and 80710 (triggered by Docker and SSH probes, to avoid self-alerting loops in Shuffle), so do not use those rules to test.
  </Step>
</Steps>

## Events and recovery

***

Wazuh pushes each alert once and never sends an update or a recovery notification. Every Wazuh alert has a unique alert ID, which Flashduty uses as the Alert Key: a redelivery of the same alert merges, different alerts each open their own Flashduty alert, and none resolves automatically.

Turn on the channel's [auto-resolve timeout](/en/on-call/channel/create-edit) (24 hours suggested), or close alerts by hand after handling them. When the same rule fires repeatedly on the same host, configure a noise-reduction rule on the channel to merge them into one incident.

## Alert Key

***

The Alert Key is computed from the Wazuh alert's `id` field (for example `1790000101.123456`). A request without `id` is rejected with an invalid-parameter error. This includes requests in the Slack integration format: Flashduty supports only the `shuffle` integration.

## Severity mapping

***

Flashduty maps `all_fields.rule.level` (the Wazuh rule level, 0-15):

| Wazuh rule level | Flashduty severity |
| :- | :- |
| 12-15 | Critical |
| 7-11 | Warning |
| 0-6 | Info |

When `all_fields.rule.level` is missing, the shuffle script's `severity` field is used: `3` (rule level 8 and above) is Warning, and `1` and `2` are Info. When both are missing, the severity is Warning.

## Labels

***

| Label | Source |
| :- | :- |
| `check` | Rule description, same as the title |
| `alert_id` | Alert ID |
| `rule_id` / `rule_level` / `rule_groups` | Rule ID, level, and rule groups (comma-separated) |
| `wazuh_severity` | The shuffle script's `severity` (1-3) |
| `agent_id` / `agent_name` / `agent_ip` | The agent that raised the alert |
| `host` | Agent name |
| `manager` | Wazuh manager name |
| `decoder` | Decoder name |
| `location` | Log source, for example `/var/log/auth.log` |
| `src_ip` / `src_user` | Decoded source IP and user, when present |

Flashduty neither reads nor stores the raw log (`text` and `full_log`). The shuffle script still sends the whole alert to `hook_url`, and it can contain usernames, IP addresses, file paths and command lines. Filter with `<level>`, `<rule_id>` and `<group>`, and avoid forwarding raw authentication logs.

## Troubleshooting

***

* **Flashduty returns an invalid-parameter error**: make sure you use the `shuffle` integration with `<alert_format>` set to `json`, and check the `integration_key` in `hook_url`
* **No alerts arrive**: confirm the manager was restarted, the alert level is at or above `<level>`, the rule is not in the skip list above, and check `integrations.log`
* **Too many alerts**: raise `<level>`, or filter with `<rule_id>` / `<group>`
* **Alerts never close**: Wazuh sends no recovery, so turn on the channel's auto-resolve timeout

For more options, see the [Wazuh documentation on integrating with external APIs](https://documentation.wazuh.com/current/user-manual/manager/integration-with-external-apis.html).
