SafeDNS Shield

Overview

SafeDNS Shield is an on-premises web filtering and security solution that operates as a DNS proxy. It processes every DNS query to identify the requesting user, evaluates the queried domain against that user’s filtering policy, and then allows or blocks the request.

When a domain is blocked, the proxy resolves it to the IP address of a block page instead of returning the actual IP. The block page can be a custom corporate page hosted outside the solution, or the default block page built into SafeDNS Shield, which can also be customized.

If a domain is allowed, the proxy forwards the DNS request to the next server in the resolution chain. This server can be a local corporate DNS server, an ISP’s caching DNS resolver, or any public DNS service (for example, Google Public DNS or Cloudflare).

Because SafeDNS Shield inspects all DNS traffic, it enables comprehensive, per‑user traffic analysis. Every request is logged, providing access to detailed statistical information.

Architecture and deployment

Components

image-1772786479925.png

SafeDNS Shield is composed of the following components:

The DNS Proxy writes its binary query logs to a designated host path (HostPATH), from which StatsLoader reads them.

External dependencies
The following elements are not part of SafeDNS Shield but are required for operation:

Deployment options

SafeDNS Shield supports multiple deployment options to accommodate different network topologies. This section describes the most common scenarios.

For ISPs

This deployment option is used in ISP networks, where NAT separates end users from the on-premises DNS infrastructure, making it impossible to identify them solely by their individual IP addresses.

 
For corporate clients

image-1772786346085.png

or

image-1772786395390.png

This deployment option is used in corporate networks where end users can be identified by their individual IP addresses at the point where SafeDNS Shield is deployed. Depending on whether the organization has its own caching DNS server, requests are forwarded to that server or to an external resolver, such as an ISP’s DNS or a public DNS service (e.g., 1.1.1.1 or 8.8.8.8).

User Identification

User Identification

To apply filtering policies and to separate statistics on a per‑user basis, SafeDNS Shield must identify each end user. Identification is based on the source address of the DNS request and can be configured using one of the following methods:

The appropriate method depends on the network topology and the level of user separation required.

Setup and requirements

Product setup and support

Custom Local Deployment

Setup, maintenance, and support for an on-premises deployment are managed entirely by SafeDNS specialists, establishing a clear division of responsibilities. The client provides the required hardware and full remote access, after which SafeDNS performs the complete turnkey installation.

Following deployment, SafeDNS specialists work with the client to configure the initial filtering rules and provide training to enable the client’s staff to make future adjustments independently. A dedicated support line is available for clients using on-premises solutions.

VM Deployment via ISO Image

As an alternative to a physical server installation, SafeDNS Shield can be deployed as a virtual appliance by mounting the provided ISO image in a virtual machine. This method streamlines deployment in environments that rely on virtualization infrastructure.

System requirements

The following specifications apply to a server running the SafeDNS Shield components. All deployments require Debian 12 (x86‑64).

DNS Proxy Module

Choose a configuration based on the expected peak query load.

CPU: Intel 12th‑generation or later, Intel Xeon Silver/Gold, or equivalent AMD Ryzen/Epyc.

Queries per second (QPS) CPU Cores RAM Storage Network
Up to 1,000 4 8 GB 200 GB NVMe 1 Gbps
Up to 15,000 12 16 GB 512 GB SSD (RAID 1) 1 Gbps
Up to 310,000 64 128 GB 2 TB SSD/NVMe (RAID 1) 1 Gbps
Up to 2,000,000 128 2 TB 16 TB SSD/NVMe (RAID 1) 25 Gbps
ClickHouse Cluster (Statistics Storage)

The ClickHouse cluster stores and analyzes DNS request logs. A single node meets the following minimum:

Example configuration for 75,000 QPS and one year of log retention:

We recommend a minimum cluster of 4 data servers arranged as 2 shards × 2 replicas. This provides parallel read/write operations and redundancy. A load balancer distributes incoming statistics across the nodes.

For lower traffic volumes, a standalone ClickHouse server can be deployed without ClickHouse Keeper, eliminating the need for the coordination layer.

Miscellaneous

Working with statistics

The DNS Proxy generates binary logs, which are stored directly on the SafeDNS Shield server. A dedicated parsing module processes these logs and exports the resulting data to an external DBMS for analysis and report generation. The module includes a connector for ClickHouse, which provides the best performance for this data type, but logs can also be exported to other databases if required.

The local binary log storage acts as a buffer: if the connection to ClickHouse is temporarily lost, logs generated during the outage are retained on disk and automatically exported once connectivity is restored. No data is lost during short interruptions, provided the local storage on the Shield server does not become completely full.

Although the statistics module is not essential for the core filtering functionality, it is indispensable for assessing system performance and investigating incidents effectively.

Note on HTTPS block pages

To display the built‑in block page for HTTPS requests, the SafeDNS root certificate must be added to the trusted certificate store on every end user device. Without the certificate, web browsers cannot validate the block page’s TLS certificate; instead of the block page, users will see a TLS/SSL error. Access to the requested resource will still be denied.
Displaying the block page over HTTP does not require the certificate.
If an externally hosted block page is used, certificate requirements depend on your own hosting configuration.

REST API overview

All administration and configuration of SafeDNS Shield is performed through the REST API. The API listens on port 8080 of the same IP address that handles DNS queries. By default, access is restricted to a set of whitelisted IP addresses specified during deployment.

Initial Configuration Example

The following example demonstrates the initial configuration workflow. Send the following request:

 
{
    "profiles": [
        {
            "profile": {
                "id": 1,
                "page_id": 1
            },
            "cat_ids": [3, 4, 12],
            "app_ids": [1, 12, 93]
        }
    ],
    "blockpages": [
        {
            "id": 1,
            "type": 0
        },
        {
            "id": 2,
            "type": 1
        }
    ],
    "bw_lists": [
       {
            "profile_id": 1,
            "type": "deny",
            "domains": [
                "example1.com",
                "example2.com",
                "example3.com"
            ]
        }
    ],
    "nets": [
        {
            "ip": "100.100.100.100",
            "profile_id": 1,
            "prefix_len": 32
        },
        {
            "ip": "100.110.110.0",
            "profile_id": 1,
            "prefix_len": 24
        },
        {
            "ip": "100.120.0.0",
            "profile_id": 1,
            "prefix_len": 16
        }
    ],
    "nets6": [],
    "napts": []
}

The initialization query defines the full configuration applied to SafeDNS Shield. The following settings are processed in sequence:

  1. Filtering profile and block page – A filtering profile (ID=1) and a block page (ID=1) are created.

  2. Blocked categories – Three DNS categories are blocked for the profile: malware, phishing, and botnets.

  3. Blocked applications – Three AppBlocker categories are blocked: Slack, AnyDesk, and Netflix.

  4. Block pages – Two block pages of different types are created:

    • Type 0 – displays the blocked domain name.

    • Type 1 – does not display the blocked domain name.

  5. Blacklist – Three domains are added to the blacklist for filtering profile 1.

  6. IP assignment – The profile is assigned one specific IP address and two subnets (/16 and /24). DNS requests from these sources are filtered according to the profile’s policy.

  7. IPv6 and NAT‑port identification – The nets6 (IPv6) and napts (NAT port‑based identification) sections are included but left empty. These fields must be present in the request even if not used, to trigger the creation of the initial configuration.

Once the request is sent and a successful response (HTTP status 204) is received, the initial configuration is complete. All subsequent DNS traffic processed by the server is handled according to the specified rules.

Modifying Filtering Categories

To modify the filtering categories for an existing profile, you must update the entire list of categories assigned to that profile. Adding new categories requires sending the full set (both current and new categories) in a single request.

For example, the initial configuration created profile id=1 with three blocked categories: malware, phishing, and botnets. To add Cryptojacking, DGA, and Ransomware, the request must include all six categories:

 
{
  "cat_ids": [3, 4, 12, 66, 70, 71],
  "app_ids": [1, 12, 93],
  "profile": {
    "page_id": 1
  }
}

In this request, the profile ID is specified directly in the URL. The request body contains the updated list of categories (original three and three new) while the AppBlocker categories and block page remain unchanged.

Adding a Domain to the Allowlist

To exempt a specific domain from category-based blocking, add it to the allowlist of the relevant filtering profile. For profile id=1, send the following request:

 
{
  "type": "allow",
  "domain": "example4.com"
}

This adds the domain to the allowlist, giving it priority over category-based blocking.

Adding Domains to the Denylist

To block specific domains that are not covered by the configured categories, add them directly to the denylist for the filtering profile. The following request adds domains in a batch operation for profile id=1:

 
{
  "type": "deny",
  "domains": ["example5.com", "example6.com", "example7.com", "example8.com", "example9.com"]
}
Adding a Network or IP Address for Filtering

To assign a new IP address or subnet to a filtering profile, send the following request. The example adds a single IP address by specifying a /32 network prefix for profile id=1:

 
{
    "ip": "100.100.100.101",
    "profile_id": 1,
    "prefix_len": 32
}

To add an entire subnet, adjust the prefix length accordingly. For instance, a /24 subnet would be specified as:

{
    "ip": "100.100.101.0",
    "profile_id": 1,
    "prefix_len": 24
}
Removing an IP Address from Filtering

To remove a previously assigned IP address or subnet from a filtering profile, send the following request:

This request has no body. The IP address must be provided in decimal format in the URL. Use the exact address originally submitted, without the mask - for example, 100.100.100.101 or 100.100.101.0 from the earlier examples. You can convert an IP address to decimal format using a tool like this one.

Modifying the Filtering Profile for a Specific IP

To change the filtering profile assigned to an existing IP address or subnet, send the following request. The IP address must be provided in decimal format in the URL. This example reassigns the address 100.100.101.0 (originally a /24 subnet) from profile id=1 to profile id=2:

 
{
    "ip": "100.100.101.0",
    "profile_id": 2,
    "prefix_len": 24
}

To change the network prefix (for example, from /24 to /16), you must delete the existing record and add a new one with the correct network address. In this case, you would delete 100.100.101.0 and add 100.100.0.0 with the /16 prefix.

Creating a New Filtering Profile

Before an IP can be reassigned to a different profile, that profile must exist. The following request creates a new filtering profile:

 


{ "profile": { "id": 2, "page_id": 1 }, "cat_ids": [3, 4, 12, 66, 70, 71, 13], "app_ids": [1, 12, 93] }

This creates profile id=2, configured with the same block page type and the same categories and AppBlocker settings as profile id=1, with the addition of the "Adult Related" category.

REST API reference

User data methods

 
Initialize user data database (batch data creation)

Profile methods

 
Fetch all profiles
Add a profile
Fetch a specific profile
Update a specific profile

Blockpage methods

 
Get all blockpages
Create a blockpage
Get a specific blockpage
Update a blockpage
Delete a blockpage

Lists methods

 
Create an allow- or denylist
Create an allow- or denylist with multiple entries
Update a domain in an allow- or denylist

Delete a domain from an allow- or denylist:

IPv4 network methods

 
Create an IPv4 address entry
Get an IPv4 address entry
Update an IPv4 address entry
Delete an IPv4 address

IPv6 network methods

 
Create an IPv6 address entry
Get an IPv6 address entry
Update an IPv6 address entry
Delete an IPv6 address

IPv4 NAT methods

 
Create an IPv4 NAT entry
Create multiple IPv4 NAT entries
Get all IPv4 NAT entries by IP
Get a specific IPv4 NAT entry
Update an IPv4 NAT entry
Delete an IPv4 NAT entry
Delete multiple IPv4 NAT entries

AppBlocker methods

Get a list of all available AppBlocker categories