Configure DNS over HTTPS
With Cloudflare Gateway, you can filter DNS over HTTPS (DoH) requests by DNS location or by user without needing to install the WARP client on your devices.
Location-based policies require that you send DNS requests to a location-specific DoH endpoint, while identity-based policies require that requests include a user-specific DoH token.
Filter DoH requests by location
Location-based policies require that you send DNS requests to a unique DoH endpoint assigned to the location:
https://<YOUR_DOH_SUBDOMAIN>.cloudflare-gateway.com/dns-query
Prerequisites
Obtain your location’s DoH subdomain.
Configure browser for DoH
Browsers can be configured to use any DNS over HTTPS (DoH) endpoint. If you choose to configure DoH directly in your browser, you must choose a Gateway DNS location as your DoH endpoint, otherwise DNS filtering will not occur in that browser.
Mozilla Firefox
- In Firefox, go to Settings.
- In the General menu, scroll down to Network Settings.
- Select Settings.
- Select Enable DNS over HTTPS.
- In the Use Provider drop-down menu, select Custom.
- In the Custom field, enter
https://<YOUR_DOH_SUBDOMAIN>.cloudflare-gateway.com/dns-query
. - Select OK.
Google Chrome
- In Chrome, go to Settings > Privacy and security > Security.
- Scroll down and turn on Use secure DNS.
- Select With Custom.
- In the Enter custom provider field, enter
https://<YOUR_DOH_SUBDOMAIN>.cloudflare-gateway.com/dns-query
.
Read more about enabling DNS over HTTPS on Chrome.
Microsoft Edge
- In Microsoft Edge, go to Settings.
- Select Privacy, Search, and Services, and scroll down to Security.
- Turn on Use secure DNS.
- Select Choose a service provider.
- In the Enter custom provider field, enter
https://<YOUR_DOH_SUBDOMAIN>.cloudflare-gateway.com/dns-query
.
Brave
- In Brave, go to Settings > Security and Privacy > Security.
- Turn on Use secure DNS.
- Select With Custom.
- In the Enter custom provider field, enter
https://<YOUR_DOH_SUBDOMAIN>.cloudflare-gateway.com/dns-query
.
Safari
Your DNS queries will now be sent to Gateway for filtering. To filter these requests, build a DNS policy using the DNS Location selector.
Configure operating system for DoH
Windows 11
-
Obtain the
A
andAAAA
record values associated with your location’s DoH endpoint.- Run the following command to obtain your
A
record values:
nslookup -type=A <your-subdomain>.cloudflare-gateway.com- Obtain your
AAAA
record values.
nslookup -type=AAAA <your-subdomain>.cloudflare-gateway.com- Copy the resulting IP addresses.
- Run the following command to obtain your
-
Add the addresses to your list of known DoH servers.
- Run the following command for each address:
Add-DnsClientDohServerAddress -ServerAddress <IP-address> -DohTemplate https://<your-subdomain>.cloudflare-gateway.com/dns-query -AllowFallbackToUdp $False -AutoUpgrade $False- Confirm the addresses were added.
Get-DnsClientDohServerAddress -
In Windows, go to Settings > Network & internet > your active Internet connection. This option may be either Ethernet or Wi-Fi.
-
Under DNS server assignment, select Edit.
-
In the drop-down menu, choose Manual.
-
Enable IPv4.
-
In Preferred DNS and Alternate DNS, enter the IPv4 addresses from your
A
record command. Set DNS over HTTPS to On (automatic template). -
Enable IPv6.
-
In Preferred DNS and Alternate DNS, enter the IPv6 addresses from your
AAAA
record command. Set DNS over HTTPS to On (automatic template).
Windows Server 2022
Obtain the A
and AAAA
record values associated with your location’s DoH endpoint.
- Run the following command to obtain your
A
record values:
nslookup -type=A <your-subdomain>.cloudflare-gateway.com
- Obtain your
AAAA
record values.
nslookup -type=AAAA <your-subdomain>.cloudflare-gateway.com
- Copy the resulting IP addresses.
- Add the addresses to your list of known DoH servers.
- Configure the Windows Server client or set up a Group Policy to use DoH.
For more information, refer to Microsoft’s DoH guide for Windows Server 2022 and newer.
Filter DoH requests by user
In order to filter DoH queries based on user identity, each query must include a user-specific authentication token. If you have several devices per user and want to apply device-specific policies, you will need to map each device to a different email.
Currently, authentication tokens can only be generated through the API. You can run this interactive Python script which automates the setup procedure, or follow the steps described below.
1. Create a service token for the account
curl -X POST "https://api.cloudflare.com/client/v4/accounts/<ACCOUNT_ID>/access/service_tokens" \-H "X-Auth-Email: <EMAIL>" \-H "X-Auth-Key: <API_KEY>" \-H "Content-Type: application/json" \--data '{"name":"ACME Corporation service token"}'
Save the service token’s client_id
, client_secret
, and id
.
Example response
{"result": {"client_id": "88bf3b6d86161464f6509f7219099e57.access","client_secret": "bdd31cbc4dec990953e39163fbbb194c93313ca9f0a6e420346af9d326b1d2a5","created_at": "2022-06-09T01:59:17Z","expires_at": "2023-06-09T01:59:17Z","id": "f174e90a-fafe-4643-bbbc-4a0ed4fc8415","name": "ACME Corporation service token","updated_at": "2022-06-09T01:59:17Z"},"success": true,"errors": [],"messages": []}
2. Enable DoH functionality for the service token
curl --request PUT "https://api.cloudflare.com/client/v4/accounts/<ACCOUNT_ID>/access/organizations/doh/<ID>" \--header "X-Auth-Email: <YOUR_EMAIL>" \--header "X-Auth-Key: <API_KEY>" \--header "Content-Type: application/json"
If you get an access.api.error.service_token_not_found
error, check that <SERVICE_TOKEN_ID>
is the value of id
and not client_id
.
Example response
{"result": {"client_id": "88bf3b6d86161464f6509f7219099e57.access","created_at": "2022-06-09T01:59:17Z","expires_at": "2023-06-09T01:59:17Z","id": "f174e90a-fafe-4643-bbbc-4a0ed4fc8415","name": "ACME Corporation service token","updated_at": "2022-06-09T01:59:17Z","duration": "8760h"},"success": true,"errors": [],"messages": []}
3. Create a user
Create a new user and optionally add them to a group.
curl -X POST "https://api.cloudflare.com/client/v4/accounts/<ACCOUNT_ID>/access/users" \-H "X-Auth-Email: <EMAIL>" \-H "X-Auth-Key: <API_KEY>" \-H "Content-Type: application/json" \--data '{"name":"John Doe","email":"jdoe@acme.com","custom": {"groups":[{"id": "02fk6b3p3majl10", "email": "finance@acme.com", "name": "Finance"}]}}'
Save the user’s id
returned in the response.
Example response
{"result": {"id": "54d425de-7a78-4186-9975-d43c88ee7899","created_at": "2022-03-16T21:18:39.93598Z","updated_at": "2022-05-17T23:50:39.598345Z","uid": "54d425de-7a78-4186-9975-d43c88ee7899","name": "John Doe","email": "jdoe@acme.com","custom": {"groups": [{"email": "finance@acme.com","id": "02fk6b3p3majl10","name": "Finance"}]}},"success": true,"errors": [],"messages": []}
4. Generate a DoH token for the user
Request a DoH token for the user, using your service token to authenticate into your team domain.
curl -s -X GET "https://<TEAM_NAME>.cloudflareaccess.com/cdn-cgi/access/doh-token?account-id=<ACCOUNT_ID>&user-id=<USER_ID>&auth-domain=<TEAM_NAME>.cloudflareaccess.com" \-H "Cf-Access-Client-Id: <CLIENT_ID>" \-H "Cf-Access-Client-Secret: <CLIENT_SECRET>" \-H "Content-Type: application/json"
The response contains a unique DoH token associated with the user. This token expires in 24 hours. We recommend setting up a refresh flow for the DoH token instead of generating a new one for every DoH query.
Example response
{"token":"y2khbGciOiJSUzI1NiIsImtpZCI6ImJlZjVkYjg4ZTEwMjk3ZDEwNzhkMmEyYjE0MjMxZTljYTQwMjQ2NjAwOTQzNmJhOTQwOGJkODY3ZmI4OWFiOGQifQ.eyJ0eXBlIjoiZG9oIiwiYXVkIjoiY2xvdWRmbGFyZS1nYXRld2F5LmNvbSIsImlhdCI6MTY1NDc1MTg3NSwiZXhwIjoxNjU0ODM4Mjc1LCJhY2NvdW50LWlkIjoiMTA4MDM0OGIyZGYzYmQwN2QxZmI1MjM3Y2Q1ZDU5M2EiLCJ1c2VyLWlkIjoiNTRkNDI1ZGUtN2E3OC00MTg2LTk5NzUtZDQzYzg4ZWU3ODk5In0.I5p4WsH2dPhQ8vwy84zF05PsoBHCsUSXAaMpNhEH36oFZ3tXcs9ksLz7OzpZ_x3HxUfO3n57LlpAF1VehaBt2i94XCkvSgtHpYcwd_qZydLp-BGtcyfU1LbdXQC3m6zxKcIWu5VySi8I-J25UYlpyJhYgZ4DQUZIpqbSSt6WcVRKvA7OBa7xjkTux4OcqWAViO_ZS-GLwl-fqhvolmiwk37seBD3YuV1zG06VeWXfrMkZ5MbhooHD1DZDBHOZpTtmN8MbeKeI4tlY1mb_O3-jE-um6F9Hrl4NQm89MKFzsum-_Rywi5m4PTSlDza7fjdJs7RzFgJd3VWgzG-jgyQKw"}%
5. Send an authenticated DoH query
Send DoH queries to the resolver at https://<ACCOUNT_ID>.cloudflare-gateway.com/dns-query
, making sure to include the user’s DoH token in the CF-Authorization
header.
curl -s 'https://<ACCOUNT_ID>.cloudflare-gateway.com/dns-query?name=example.com' \-H 'accept: application/dns-json' \-H 'CF-Authorization: <USER_DOH_TOKEN>' | jq
If the site is blocked and you have enabled Display block page for the policy, the query will return 162.159.36.12
(the IP address of the Gateway block page). If the block page is disabled, the response will be 0.0.0.0
.
Example response
{"Status": 0,"TC": false,"RD": true,"RA": true,"AD": false,"CD": false,"Question": [{"name": "example.com","type": 1}],"Answer": [{"name": "example.com","type": 1,"TTL": 60,"data": "162.159.36.12"}]}
You can verify that the request was associated with the correct user email by checking your Gateway DNS logs. To filter these requests, build a DNS policy using any of the Gateway identity-based selectors.