windowsdnsip-addresswfp

How do I write a function that blocks or firewalls off traffic to a website that has multiple IP addresses in Windows?


The Question:

I want to write a function that has the following pseudocode signature:

/**
 * Blocks all traffic to the given website.
 * 
 * @param {String} domain The domain name of the site to block
 */
function blockSite (domain) {
  // TODO
}

I want to have the following constraints, however:


Insights:

Content filtering can happen at different stages of networking. A solution that uses Windows firewall works at layer 4, the transport layer. Other solutions might use layer 7, the application layer. Cold Turkey is a commercial application that works on layer 7 by requiring a plugin to be installed on every browser and filtering content via the plugins.

One challenge that extends the complexity of blocking sites is shared web hosting. Some websites, like youtube.com, for example, shares the same set of IP Addresses with sites like google.com. For the sake of simplicity, satisfying the problem of shared web hosting can be ignored. I just want the site in question blocked, regardless of what other collateral sites get blocked with it.

A solution to the shared web hosting problem is to use DNS based filtering (instead of IP based filtering). A common solution proposed for the task of blocking a site is to make use the hosts file c:\windows\system32\drivers\etc\hosts. Consider the following function, written in powershell, as a solution that does just that:

function Block-Site([String] $domain) {
    $hosts = 'C:\Windows\System32\drivers\etc\hosts'
    $isBlocked = Get-Content -Path $hosts | Select-String -Pattern ([regex]::Escape($domain))

    If(-not $isBlocked) {
        Add-Content -Path $hosts -Value "127.0.0.1 $domain"
        Add-Content -Path $hosts -Value "127.0.0.1 www.$domain"
    }
}

The problem with the solution above is that it has many trivial workarounds. One workaround, for example, is to just google the name of the website and click on the website from Google. As such, I'm not very content with the solution, since it doesn't actually block or firewall off traffic.

Update: I believe the Windows filter platform might be the most comprehensive solution available. I'm investigating its potential, and adding a tag for it.


The Research:

I've checked every relevant stackoverflow and superuser question I could find, but none were sufficient in providing an answer. See:

Stack Overflow:

Super User:


Solution

  • The following function is written in powershell, and will block a website by creating a Windows Firewall rule that blocks all TCP traffic to the ip addresses found associated with the website.

    function Block-TrafficToURL([String] $domain) {
        [System.Collections.ArrayList]$IPs = @()
        Resolve-DnsName -Name $domain -NoHostsFile | Foreach {$IPs.Add("$($_.IPAddress)")}
        New-NetFirewallRule -DisplayName "Block $domain" -Direction Outbound -Protocol TCP -Action Block -RemoteAddress $IPs
    }
    

    The documentation for function calls used are below:

    This function was tested and worked for Stackoverflow.com and Reddit.com, both which have multiple IP addresses. The function fails with YouTube.com, however, as calling Resolve-DnsName for YouTube.com returns only a single IP address, but can be a different IP when called multiple times. Likewise, blocking all YouTube IP's would probably result in blocking services like Google Drive and Google.com, which might not be desirable.