How to Enable or Disable Windows 10 Data Collection (PowerShell Script)

In the digital age, data privacy and security have become paramount. As Windows 10 has grown in popularity, so too have concerns about its data collection features. For IT professionals and Managed Service Providers (MSPs), understanding and controlling these features is crucial. This article delves into a PowerShell script designed to enable or disable Windows 10’s data collection capabilities.

Background

Windows 10, like many modern operating systems, has built-in telemetry and data collection features. These are intended to improve user experience by collecting data on usage patterns, errors, and more. However, for various reasons, including privacy concerns and regulatory compliance, IT professionals and MSPs often need to control these features. The provided script offers a streamlined way to manage these settings.

The Script

#Requires -Version 5.1

<#
.SYNOPSIS
    Enables or Disabled Windows 10 Linguistic Data Collection, Advertising ID, and Telemetry
.DESCRIPTION
    Enables or Disabled Windows 10 Linguistic Data Collection, Advertising ID, and Telemetry
.EXAMPLE
    No Params needed to Disable Windows 10 Linguistic Data Collection, Advertising ID, and Telemetry
.EXAMPLE
     -Enable
    Enables Linguistic Data Collection, Advertising ID, and Telemetry
.EXAMPLE
    PS C:> Set-Windows10KeyLogger.ps1
    Disables Windows 10 Linguistic Data Collection, Advertising ID, and Telemetry
.EXAMPLE
    PS C:> Set-Windows10KeyLogger.ps1 -Enable
    Enables Windows 10 Linguistic Data Collection, Advertising ID, and Telemetry
.OUTPUTS
    None
.NOTES
    Minimum OS Architecture Supported: Windows 10
    Release Notes:
    Initial Release
By using this script, you indicate your acceptance of the following legal terms as well as our Terms of Use at https://www.ninjaone.com/terms-of-use.
    Ownership Rights: NinjaOne owns and will continue to own all right, title, and interest in and to the script (including the copyright). NinjaOne is giving you a limited license to use the script in accordance with these legal terms. 
    Use Limitation: You may only use the script for your legitimate personal or internal business purposes, and you may not share the script with another party. 
    Republication Prohibition: Under no circumstances are you permitted to re-publish the script in any script library or website belonging to or under the control of any other software provider. 
    Warranty Disclaimer: The script is provided “as is” and “as available”, without warranty of any kind. NinjaOne makes no promise or guarantee that the script will be free from defects or that it will meet your specific needs or expectations. 
    Assumption of Risk: Your use of the script is at your own risk. You acknowledge that there are certain inherent risks in using the script, and you understand and assume each of those risks. 
    Waiver and Release: You will not hold NinjaOne responsible for any adverse or unintended consequences resulting from your use of the script, and you waive any legal or equitable rights or remedies you may have against NinjaOne relating to your use of the script. 
    EULA: If you are a NinjaOne customer, your use of the script is subject to the End User License Agreement applicable to you (EULA).
.COMPONENT
    OSSecurity
#>

[CmdletBinding()]
param (
    [Parameter()]
    [Switch]
    $Enable
)

begin {
    function Test-IsElevated {
        $id = [System.Security.Principal.WindowsIdentity]::GetCurrent()
        $p = New-Object System.Security.Principal.WindowsPrincipal($id)
        if ($p.IsInRole([System.Security.Principal.WindowsBuiltInRole]::Administrator))
        { Write-Output $true }
        else
        { Write-Output $false }
    }
    function Set-ItemProp {
        param (
            $Path,
            $Name,
            $Value,
            [ValidateSet('DWord', 'QWord', 'String', 'ExpandedString', 'Binary', 'MultiString', 'Unknown')]
            $PropertyType = 'DWord'
        )
        New-Item -Path $Path -Force | Out-Null
        if ((Get-ItemProperty -Path $Path -Name $Name -ErrorAction SilentlyContinue)) {
            Set-ItemProperty -Path $Path -Name $Name -Value $Value -Force -Confirm:$false | Out-Null
        }
        else {
            New-ItemProperty -Path $Path -Name $Name -Value $Value -PropertyType $PropertyType -Force -Confirm:$false | Out-Null
        }
    }
    $Type = "DWORD"
}
process {
    if (-not (Test-IsElevated)) {
        Write-Error -Message "Access Denied. Please run with Administrator privileges."
        exit 1
    }

    $Value = if ($PSBoundParameters.ContainsKey("Enable") -and $Enable) { 1 }else { 0 }

    try {
        @(
            # Linguistic Data Collection
            [PSCustomObject]@{
                Path = "HKLM:SOFTWAREMicrosoftWindowsCurrentVersionPoliciesTextInput"
                Name = "AllowLinguisticDataCollection"
            }
            # Advertising ID
            [PSCustomObject]@{
                Path = "HKLM:SOFTWAREMicrosoftWindowsCurrentVersionAdvertisingInfo"
                Name = "Enabled"
            }
            # Telemetry
            [PSCustomObject]@{
                Path = "HKLM:SOFTWAREPoliciesMicrosoftWindowsDataCollection"
                Name = "AllowTelemetry"
            }
        ) | ForEach-Object {
            Set-ItemProp -Path $_.Path -Name $_.Name -Value $Value -PropertyType $Type
            Write-Host "$($_.Path)$($_.Name) set to $(Get-ItemPropertyValue -Path $_.Path -Name $_.Name)"
        }

        if ($PSBoundParameters.ContainsKey("Enable") -and $Enable) {
            Write-Host "Enabling DiagTrack Services"
            Get-Service -Name DiagTrack | Set-Service -StartupType Automatic | Start-Service
        }
        else { 
            Write-Host "Disabling DiagTrack Services"
            Get-Service -Name DiagTrack | Set-Service -StartupType Disabled | Stop-Service
        }

        Write-Host "DiagTrack Service status: $(Get-Service -Name DiagTrack | Select-Object -Property Status -ExpandProperty Status)"
        Write-Host "DiagTrack Service is set to: $(Get-Service -Name dmwappushservice | Select-Object -Property StartType -ExpandProperty StartType)"

        if ($PSBoundParameters.ContainsKey("Enable") -and $Enable) {
            Get-Service -Name dmwappushservice | Set-Service -StartupType Manual
        }
        else { 
            Get-Service -Name dmwappushservice | Set-Service -StartupType Disabled | Stop-Service
        }

        Write-Host "dmwappushservice Service status: $(Get-Service -Name dmwappushservice | Select-Object -Property Status -ExpandProperty Status)"
        Write-Host "dmwappushservice Service is set to: $(Get-Service -Name dmwappushservice | Select-Object -Property StartType -ExpandProperty StartType)"

        $tasks = "SmartScreenSpecific", "ProgramDataUpdater", "Microsoft Compatibility Appraiser", "AitAgent", "Proxy", "Consolidator",
        "KernelCeipTask", "BthSQM", "CreateObjectTask", "WinSAT", #"Microsoft-Windows-DiskDiagnosticDataCollector", # This is disabled by default
        "GatherNetworkInfo", "FamilySafetyMonitor", "FamilySafetyRefresh", "SQM data sender", "OfficeTelemetryAgentFallBack",
        "OfficeTelemetryAgentLogOn"
        
        if ($PSBoundParameters.ContainsKey("Enable") -and $Enable) {
            Write-Host "Enabling telemetry scheduled tasks"
            $tasks | ForEach-Object {
                Write-Host "Enabling $_ Scheduled Task"
                # Note: ErrorAction set to SilentlyContinue so as to skip over any missing tasks. Enable-ScheduledTask will still error if it can't be enabled.
                Get-ScheduledTask -TaskName $_ -ErrorAction SilentlyContinue | Enable-ScheduledTask
                $State = Get-ScheduledTask -TaskName $_ -ErrorAction SilentlyContinue | Select-Object State -ExpandProperty State
                Write-Host "Scheduled Task: $_ is $State"
            }
        }
        else { 
            Write-Host "Disabling telemetry scheduled tasks"
            $tasks | ForEach-Object {
                Write-Host "Disabling $_ Scheduled Task"
                # Note: ErrorAction set to SilentlyContinue so as to skip over any missing tasks. Disable-ScheduledTask will still error if it can't be disabled.
                Get-ScheduledTask -TaskName $_ -ErrorAction SilentlyContinue | Disable-ScheduledTask
                $State = Get-ScheduledTask -TaskName $_ -ErrorAction SilentlyContinue | Select-Object State -ExpandProperty State
                Write-Host "Scheduled Task: $_ is $State"
            }
        }
    }
    catch {
        Write-Error $_
        exit 1
    }
    
    gpupdate.exe /force
    exit 0
}
end {}

 

Access 300+ scripts in the NinjaOne Dojo

Get Access

Detailed Breakdown

The script is a PowerShell cmdlet that toggles Windows 10’s linguistic data collection, advertising ID, and telemetry. Here’s a step-by-step breakdown:

  1. Prerequisites: The script requires PowerShell version 5.1.
  2. Parameters: The script accepts an optional -Enable switch. If provided, it enables the data collection features; otherwise, it disables them.
  3. Functions:
    1. Test-IsElevated: Checks if the script is running with administrator privileges.
    2. Set-ItemProp: Sets or creates a registry key value.
  4. Process:
    1. First, the script checks for administrator privileges. If not present, it exits.
    2. It then determines whether to enable or disable the features based on the -Enable switch.
    3. The script modifies specific registry keys corresponding to the linguistic data collection, advertising ID, and telemetry.
    4. It also manages the DiagTrack and dmwappushservice services, which are related to telemetry.
    5. Finally, it toggles various telemetry-related scheduled tasks.
  5. Execution: The script concludes by forcing a group policy update.

Potential Use Cases

Imagine an MSP managing IT for a healthcare provider. Due to HIPAA regulations, they need to ensure minimal data leakage. Using this script, the MSP can quickly disable all data collection features on all Windows 10 machines in the network, ensuring compliance and enhancing patient data privacy.

Comparisons

While there are GUI-based tools and manual methods to toggle these settings, this script offers a more efficient, repeatable, and scalable solution. Manual methods can be time-consuming and prone to errors, especially across multiple machines. GUI tools might not offer the granularity or automation capabilities that a PowerShell script does.

FAQs

  • Can I run this script on older Windows versions?
    No, this script is designed specifically for Windows 10.
  • Do I need administrator privileges to run the script?
    Yes, the script requires administrator rights to modify registry keys and manage services.

Implications

Using this script can significantly enhance data privacy, especially in sectors with strict regulations. However, disabling some features might limit certain functionalities or feedback mechanisms in Windows 10. IT professionals should weigh the benefits against potential limitations.

Recommendations

  • Always backup registry settings before making changes.
  • Test the script in a controlled environment before deploying it widely.
  • Regularly review and update scripts to accommodate any changes in future Windows 10 updates.

Final Thoughts

For IT professionals and MSPs, tools like NinjaOne can be invaluable in managing and monitoring IT environments. When combined with scripts like the one discussed, they can ensure a secure, compliant, and efficient IT infrastructure. As Windows 10 data collection features evolve, having a robust toolset and knowledge base will be essential for success.

Next Steps

Building an efficient and effective IT team requires a centralized solution that acts as your core service deliver tool. NinjaOne enables IT teams to monitor, manage, secure, and support all their devices, wherever they are, without the need for complex on-premises infrastructure.

Learn more about NinjaOne Remote Script Deployment, check out a live tour, or start your free trial of the NinjaOne platform.

Categories:

You might also like

×

See NinjaOne in action!

By submitting this form, I accept NinjaOne's privacy policy.

NinjaOne Terms & Conditions

By clicking the “I Accept” button below, you indicate your acceptance of the following legal terms as well as our Terms of Use:

  • Ownership Rights: NinjaOne owns and will continue to own all right, title, and interest in and to the script (including the copyright). NinjaOne is giving you a limited license to use the script in accordance with these legal terms.
  • Use Limitation: You may only use the script for your legitimate personal or internal business purposes, and you may not share the script with another party.
  • Republication Prohibition: Under no circumstances are you permitted to re-publish the script in any script library belonging to or under the control of any other software provider.
  • Warranty Disclaimer: The script is provided “as is” and “as available”, without warranty of any kind. NinjaOne makes no promise or guarantee that the script will be free from defects or that it will meet your specific needs or expectations.
  • Assumption of Risk: Your use of the script is at your own risk. You acknowledge that there are certain inherent risks in using the script, and you understand and assume each of those risks.
  • Waiver and Release: You will not hold NinjaOne responsible for any adverse or unintended consequences resulting from your use of the script, and you waive any legal or equitable rights or remedies you may have against NinjaOne relating to your use of the script.
  • EULA: If you are a NinjaOne customer, your use of the script is subject to the End User License Agreement applicable to you (EULA).