In an ASP.NET MVC webapp I developed years ago in C#, there is an action / controller that downloads an image of Google maps and saves it to disk for later use, using WebClient.DownloadData
.
This action / controller is requested 4 or 5 times a day. This web app (and the action / controller) worked perfectly in development and production (in-house server, Windows Server 2008 R2 Foundation, IIS 7.5, .NET Framework v4.0).
Recently, the app was moved to a new virtual server in AWS (Windows Server 2019 Datacenter, IIS 10, .NET CLR v4.0). The whole web app seems to work fine except for the action / controller that I mentioned previously.
If I use the URL in chrome installed in the new virtual server the map is downloaded without issues. But when the action / controller is requested it times out (exception):
The code is simple:
string url = "http://maps.googleapis.com/maps/api/staticmap?key=[API_KEY]¢er=" + lat + "," + long + "&size=355x255&markers=color:red|" + lat + "," + long;
WebClient web = new WebClient();
byte[] bs = web.DownloadData(url);
// save bs in disk
This is an example of a map that it should be downloaded
http://maps.googleapis.com/maps/api/staticmap?key=[API_KEY]¢er=25.670984,-100.285016&size=355x255&markers=color:red|25.670984,-100.285016
I checked the WebClient.DownloadData
documentation and I haven't found any hint of what can cause the problem.
Again, this action / controller worked perfectly fine for years but after the migration it started to fail.
I build a console application which contains only the next code (using different API_KEYs without limitations):
WebClient web = new WebClient();
byte[] bs = web.DownloadData("http://maps.googleapis.com/maps/api/staticmap?key=API_KEY¢er=25.670984,-100.285016&size=355x255&markers=color:red|25.670984,-100.285016");
File.WriteAllBytes("mapa.jpg", bs);
And still got Timeout Exception.
Then, I installed mitmproxy to monitor the traffic (maybe it was a problem with the network?) and it worked perfectly.
Code using the proxy (changed https to http):
WebClient web = new WebClient();
WebProxy proxy = new WebProxy("127.0.0.1", 8080);
byte[] bs = web.DownloadData("http://maps.googleapis.com/maps/api/staticmap?key=API_KEY¢er=25.670984,-100.285016&size=355x255&markers=color:red|25.670984,-100.285016");
File.WriteAllBytes("mapa.jpg", bs);
BUT I can't let mitmproxy running all the time in the server, something is still off.
Found the problem: was the default proxy of the server.
Thanks to this question How to bypass the system proxy when using WebClient the path to the solution was there.
WebClient webclient = new WebClient();
webclient.Proxy = null;
According to the WebClient.Proxy Property documentation:
The proxy is set by the system using configuration files and the Internet Explorer Local Area Network settings. To specify that no proxy should be used, set the Proxy property to null.
And the default proxy of the server (AWS) does not allow the request that I was trying to perform.
Now, because I can not modify the code (right now) in the webapp (action/controller), I had to search How to disable proxy server via web.config file and it worked.
<system.net>
<defaultProxy>
<proxy usesystemdefault="False"/>
</defaultProxy>
</system.net>
Obviously, the value was "True" and changed it to "False".