How to Configure Windows Event Forwarding (WEF) on Windows Server 2025

Windows Event Forwarding (WEF) is a built-in Windows feature that allows you to centralize event log data from multiple source computers to a single collector server — all without deploying a third-party agent. In security operations, WEF is frequently used to aggregate Security, System, and Application logs into a central location for analysis by a SIEM or log management platform. Windows Server 2025 supports WEF natively using HTTPS-based transport with mutual authentication via Kerberos or certificates, making it both efficient and secure. This tutorial covers both major subscription models, configuring the Windows Event Collector service, deploying via Group Policy, and filtering events with XPath queries.

Prerequisites

  • Windows Server 2025 designated as the collector (receives events)
  • One or more Windows Server 2025 or Windows 10/11 systems as sources (send events)
  • All systems joined to the same Active Directory domain (for Kerberos authentication)
  • Domain Administrator credentials
  • Group Policy Management Console (GPMC) on a management workstation or the collector
  • Outbound TCP 5985 (HTTP) or 5986 (HTTPS) from sources to the collector — open in firewall rules

Step 1: Understand Subscription Types

WEF supports two subscription models that differ in which side initiates the connection:

  • Collector-Initiated: The collector server pulls events by contacting each source computer individually. You must specify source computers explicitly. Best for smaller, stable inventories.
  • Source-Initiated: Source computers push events to the collector using a Group Policy-configured subscription manager URL. Scales well to large, dynamic environments because sources self-register. This is the recommended model for enterprise deployments.

This tutorial focuses primarily on the Source-Initiated model, which is more scalable and commonly used in production environments.

Step 2: Configure the Windows Event Collector Service

The Windows Event Collector (WecSvc) service must be running on the collector server and configured to accept subscriptions. Use wecutil qc (Quick Configure) to perform the initial setup:

# Run on the COLLECTOR server
# Start and configure the Windows Event Collector service
wecutil qc /q

# Verify the service is running
Get-Service -Name Wecsvc | Select-Object Name, Status, StartType

# Set service to start automatically
Set-Service -Name Wecsvc -StartupType Automatic
Start-Service -Name Wecsvc

# Add the collector's Network Service account to the Event Log Readers group
# This is required for the collector to read forwarded events
Add-LocalGroupMember -Group "Event Log Readers" -Member "NETWORK SERVICE"

# Open the Windows Remote Management firewall rule (required for WinRM transport)
Enable-NetFirewallRule -DisplayName "Windows Remote Management (HTTP-In)"

# Verify WinRM is configured
winrm get winrm/config/listener

The wecutil qc command sets the collector service to delayed-auto start and configures the necessary WinRM listener and ACLs. Running it with /q suppresses the confirmation prompt.

Step 3: Create a Subscription XML File

Subscriptions are defined in XML and imported using wecutil cs (Create Subscription). The XML specifies the subscription type, transport, event log destination, and the XPath queries that filter which events to forward. Create the subscription file on the collector:

# Create the subscription XML file
$subscriptionXml = @"
<Subscription xmlns="http://schemas.microsoft.com/2006/03/windows/events/subscription">
    <SubscriptionId>SecurityAndSystem-SourceInitiated</SubscriptionId>
    <SubscriptionType>SourceInitiated</SubscriptionType>
    <Description>Forwards Security and System events from all domain servers</Description>
    <Enabled>true</Enabled>
    <Uri>http://schemas.microsoft.com/wbem/wsman/1/windows/EventLog</Uri>
    <ConfigurationMode>Custom</ConfigurationMode>
    <Delivery Mode="Push">
        <Batching>
            <MaxItems>500</MaxItems>
            <MaxLatencyTime>30000</MaxLatencyTime>
        </Batching>
        <PushSettings>
            <Heartbeat Interval="3600000"/>
        </PushSettings>
    </Delivery>
    <Query>
        <![CDATA[
        <QueryList>
            <Query Id="0" Path="Security">
                <Select Path="Security">
                    *[System[(EventID=4624 or EventID=4625 or EventID=4634 or
                               EventID=4648 or EventID=4672 or EventID=4688 or
                               EventID=4698 or EventID=4720 or EventID=4726 or
                               EventID=4740 or EventID=4776 or EventID=5136)]]
                </Select>
            </Query>
            <Query Id="1" Path="System">
                <Select Path="System">
                    *[System[(Level=1 or Level=2) and
                      TimeCreated[timediff(@SystemTime) <= 604800000]]]
                </Select>
            </Query>
        </QueryList>
        ]]>
    </Query>
    <ReadExistingEvents>false</ReadExistingEvents>
    <TransportName>HTTP</TransportName>
    <ContentFormat>RenderedText</ContentFormat>
    <Locale Language="en-US"/>
    <LogFile>ForwardedEvents</LogFile>
    <PublisherName>EventForwarder</PublisherName>
    <AllowedSourceNonDomainComputers></AllowedSourceNonDomainComputers>
    <AllowedSourceDomainComputers>O:NSG:NSD:(A;;GA;;;DC)(A;;GA;;;DD)</AllowedSourceDomainComputers>
</Subscription>
"@

$subscriptionXml | Out-File -FilePath "C:WEFSecurityAndSystem.xml" -Encoding UTF8

# Import the subscription
wecutil cs "C:WEFSecurityAndSystem.xml"

# Verify it was created
wecutil es

The AllowedSourceDomainComputers SDDL string (A;;GA;;;DC) grants access to all domain computers, and (A;;GA;;;DD) grants access to all domain controllers. Adjust this string to restrict which computers can forward events.

Step 4: Configure Source Computers via Group Policy

For source-initiated subscriptions, each source computer must be told which collector to forward events to. This is done via GPO, under Computer Configuration → Administrative Templates → Windows Components → Event Forwarding:

# On the management server / domain controller
Import-Module GroupPolicy

# Create a GPO for WEF source configuration
$wefGpo = New-GPO -Name "WEF-SourceComputer-Configuration" `
                  -Comment "Configures Windows Event Forwarding sources to push to collector"

# Link it to the target OU (Servers OU in this example)
New-GPLink -Name "WEF-SourceComputer-Configuration" `
           -Target "OU=Servers,DC=contoso,DC=com" `
           -LinkEnabled Yes

# The key GPO setting (configure via GPMC GUI or registry-based LGPO):
# Path: Computer ConfigurationAdministrative TemplatesWindows ComponentsEvent Forwarding
# Setting: "Configure target Subscription Manager"
# Value: Server=http://WEF-COLLECTOR.contoso.com:5985/wsman/SubscriptionManager/WEC,Refresh=60

# Set via registry (for local testing or scripted deployment)
$wefRegPath = "HKLM:SOFTWAREPoliciesMicrosoftWindowsEventLogEventForwardingSubscriptionManager"
New-Item -Path $wefRegPath -Force | Out-Null
Set-ItemProperty -Path $wefRegPath -Name "1" `
    -Value "Server=http://WEF-COLLECTOR.contoso.com:5985/wsman/SubscriptionManager/WEC,Refresh=60" `
    -Type String

# Also enable WinRM on source computers via GPO
# Computer ConfigurationWindows SettingsSecurity SettingsSystem Services
# Set Windows Remote Management (WS-Management) to Automatic

# Enable WinRM via PowerShell on source (for immediate effect)
Enable-PSRemoting -Force -SkipNetworkProfileCheck
Set-Service -Name WinRM -StartupType Automatic

Step 5: Verify Event Forwarding is Working

After applying the GPO and running gpupdate /force on source computers, give the subscription a few minutes to establish. Then verify on the collector:

# On the COLLECTOR: check subscription runtime status
wecutil gr SecurityAndSystem-SourceInitiated

# List active source computers connected to the subscription
wecutil gs SecurityAndSystem-SourceInitiated

# Verify events are arriving in the ForwardedEvents log
Get-WinEvent -LogName "ForwardedEvents" -MaxEvents 20 |
    Select-Object TimeCreated, Id, MachineName, Message |
    Format-Table -Wrap

# Check event count in ForwardedEvents
(Get-WinEvent -LogName "ForwardedEvents" -MaxEvents 1000 -ErrorAction SilentlyContinue).Count

# View the ForwardedEvents log file location
$forwardedLog = "$env:SystemRootSystem32WinevtLogsForwardedEvents.evtx"
Test-Path $forwardedLog
(Get-Item $forwardedLog).Length / 1MB | ForEach-Object { Write-Host "Log size: $([math]::Round($_,2)) MB" }

Step 6: Filter Events with XPath Queries

XPath 1.0 queries are used within subscription XML to filter which events are forwarded. This is critical for controlling bandwidth and storage. Below are common XPath patterns for Security log filtering:

# Test an XPath query locally before embedding it in a subscription
# Retrieve failed logon events (4625) from the last 24 hours
$xpath = "*[System[(EventID=4625) and TimeCreated[timediff(@SystemTime) <= 86400000]]]"
Get-WinEvent -LogName Security -FilterXPath $xpath -MaxEvents 50 |
    Select-Object TimeCreated, Id, Message | Format-Table -Wrap

# XPath for Kerberos pre-authentication failures (4771) — brute force indicator
$kerbXPath = "*[System[EventID=4771]]"
Get-WinEvent -LogName Security -FilterXPath $kerbXPath -MaxEvents 20

# XPath for privileged logons (4672) — monitor for suspicious SA use
$privXPath = "*[System[EventID=4672]] and *[EventData[Data[@Name='SubjectUserName'] != 'SYSTEM']]"

# Update an existing subscription with a new XPath query
wecutil ss SecurityAndSystem-SourceInitiated `
    /q:"*[System[(EventID=4624 or EventID=4625 or EventID=4634 or EventID=4648 or EventID=4672)]]"

# Increase log size for ForwardedEvents to 1 GB
wevtutil sl ForwardedEvents /ms:1073741824

# Verify log configuration
wevtutil gl ForwardedEvents

Step 7: Expand Log Size and Configure Log Rotation

By default, the ForwardedEvents log is limited to a small size. For production WEF deployments receiving events from dozens of servers, expand the log size and configure retention policy:

# Set ForwardedEvents log to 2 GB with circular (overwrite oldest) retention
wevtutil sl ForwardedEvents /ms:2147483648 /rt:false /ab:false

# Alternatively, use PowerShell to configure via CIM
$log = Get-WinEvent -ListLog "ForwardedEvents"
$log.MaximumSizeInBytes = 2147483648L  # 2 GB
$log.LogMode = [System.Diagnostics.Eventing.Reader.EventLogMode]::Circular
$log.SaveChanges()

# Enable the ForwardedEvents log if it's not already enabled
wevtutil sl ForwardedEvents /e:true

# Optionally, archive old ForwardedEvents logs daily
$archivePath = "D:EventArchive"
New-Item -Path $archivePath -ItemType Directory -Force

$archiveFile = "$archivePathForwardedEvents_$(Get-Date -Format 'yyyyMMdd').evtx"
wevtutil epl ForwardedEvents $archiveFile
wevtutil cl ForwardedEvents

Write-Host "Events archived to: $archiveFile"

Conclusion

Windows Event Forwarding provides an enterprise-grade, agentless log centralization solution that integrates seamlessly with Active Directory authentication and Group Policy management. By configuring a source-initiated subscription, deploying the subscription manager URL via GPO, and using precise XPath filters to capture only the security-relevant event IDs, you can build a robust SIEM-ready event pipeline with minimal overhead on your source systems. Combined with proper log sizing and archival, WEF gives you the visibility you need to detect threats, meet compliance requirements, and respond to incidents — all using capabilities already built into Windows Server 2025.