Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(client/cordova/apple): [1980] randomize list of dns severs #2008

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

serge-r
Copy link

@serge-r serge-r commented May 8, 2024

Just add a simple shuffle for list of dns servers

According to issue #1980

@serge-r serge-r requested a review from a team as a code owner May 8, 2024 09:59
Copy link

google-cla bot commented May 8, 2024

Thanks for your pull request! It looks like this may be your first contribution to a Google open source project. Before we can look at your pull request, you'll need to sign a Contributor License Agreement (CLA).

View this failed invocation of the CLA check for more information.

For the most up to date status, view the checks section at the bottom of the pull request.

@daniellacosse daniellacosse requested a review from fortuna May 8, 2024 18:21
@daniellacosse daniellacosse changed the title fix(outline-client): [1980] randomize list of dns severs fix(client/cordova/apple): [1980] randomize list of dns severs May 8, 2024
@daniellacosse daniellacosse changed the title fix(client/cordova/apple): [1980] randomize list of dns severs feat(client/cordova/apple): [1980] randomize list of dns severs May 8, 2024
@@ -70,6 +70,8 @@ public class OutlineTunnel: NSObject, Codable {
@objc public static func getTunnelNetworkSettings(tunnelRemoteAddress: String) -> NEPacketTunnelNetworkSettings {
// The remote address is not used for routing, but for display in Settings > VPN > Outline.
let settings = NEPacketTunnelNetworkSettings(tunnelRemoteAddress: tunnelRemoteAddress)
var dnsList = ["1.1.1.1", "9.9.9.9", "208.67.222.222", "208.67.220.220"]
dnsList.shuffle()
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's not clear to me this will fix the issue. You will still get 1.1.1.1 for all queries in 1/4 of the sessions.

How does the server selection work on iOS/macOS? Will the system not automatically fallback to the next DNS address? Why does the api take multiple addresses?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My goal is not to completely remove queries to 1.1.1.1, but to reduce queries to this DNS provider. It's not a complete fix, and I'm not sure that a full fix is possible, as I still have no answer from Cloudflare. However, it will help reduce the chance of receiving REFUSED responses from Cloudflare. I'm pretty sure that Cloudflare has limitations, which is reasonable, especially for DOT/DOH, but they have said nothing.

How does the server selection work on iOS/macOS? Will the system not automatically fallback to the next DNS address? Why does the api take multiple addresses?

This is a good question. I tried to ask Apple support about this in this thread: https://discussions.apple.com/thread/255581809?sortBy=best, but I still have no answer to my questions.

Probably, MacOS/iOS doesn't switch to another DNS because we didn't get a DNS timeout error, but a REFUSED response instead. I didn't find any RFC that describes client behavior in such a case.

I did some tests and can confirm that MacOS/iOS caches REFUSED queries for some time. You can see logs of MacOS mDNSResponder in my thread with Apple which confirm this. So, that's the big problem for mobile users and mobile apps.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@fortuna, could you please approve this MR? It is crucial for many iOS users. My team and I independently identified this issue because our app has been experiencing numerous DNS problems as a result. Resolving this matter promptly will significantly enhance the user experience and stability of our application. Your approval will help us address this critical issue and prevent further disruptions for our users. Thank you for your attention to this urgent matter.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@serge-r could you seek Apple assistance again? Your original question is not getting to the core of the question.

The question is about the VPN API. NETunnelNetworkSettings.dnsSettings takes a list of servers: https://developer.apple.com/documentation/networkextension/nednssettings

Why are they not falling back to the next DNS in case of failure? What does Apple do with the list? Is the list pointless?

Do we have the same problem on other platforms?

If we are changing this, we should change it on all platforms. Or else the product will get inconsistent.

A better approach may be to allow specification of the dns resolvers in the key. But that needs some wiring work.

/cc @sbruens

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The issue appeared on iOS and macOS.

Perhaps we could change the order of DNS servers and use other public DNS servers like 8.8.8.8 and 8.8.4.4 instead of CloudFlare's 1.1.1.1? We did not reproduce the issue with these addresses.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like Android have another implementation and in case of error with DNS request during VPN connection it will fallback to other system DNS addresses

But in iOS it doesn't work that way and if VPN connection have just one DNS server and it have some issues (like throttling that 1.1.1.1 has) users face failed network requests

So i also think that changing default DNS server to 8.8.8.8 (we didn't notice throttling with it with our users) or adding several more DNS servers (not just 1.1.1.1) will drastically improve Outline VPN stability for iOS users

@serge-r serge-r force-pushed the dns-randomize branch 4 times, most recently from 7012b41 to ef05a87 Compare May 9, 2024 11:48
@serge-r
Copy link
Author

serge-r commented May 9, 2024

fixed tests

@serge-r serge-r requested a review from fortuna May 10, 2024 09:33
@SanchesS
Copy link

@fortuna sorry for disturbing you, but this fix also will help our app with millions of users — a lot of them use Outpost VPN and this VPN by default use only 1.1.1.1 DNS server and we see using our client metrics that sometimes a small ratio of DNS requests is throttled (and then failed) by 1.1.1.1 and our users facing issues within our app

We investigated a lot into this issue (we spend a weeks into it) and DNS server rotation (not only 1.1.1.1) will definitely improve network stability requests for people using Outline VPN as their main VPN service

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants