TransWikia.com

How to set up reverse-proxy to an external server in IIS

Server Fault Asked by bugmagnet on November 4, 2021

So the scenario we have in mind is as follows.

We have an IFRAME. Said IFRAME wants to point to a resource on https://trees.com. It might be, for example, https://trees.com/ficus/macrophylla. However, despite all our requests to trees.com, they refuse to allow us to link directly to their site, blocking the cross-origin request.

So we decide we want to set up a reverse-proxy. We’ve heard about nginx and apache but we’ve got a corporate commitment to Microsoft’s technology, for better or worse, so decide in favour of IIS.

Using one of our Azure servers, we create a website, let’s call it https://figs.wild.com.au. We configure the IFRAMEs so that a request to https://trees.com/ficus/macrophylla actually goes to https://figs.wild.com.au/trees/ficus/macrophylla.

At this point we go slightly insane.

Is it actually possible for the request https://figs.wild.com.au/trees/ficus/macrophylla to be converted, on the figs.wild.com.au server, to a request for https://trees.com/ficus/macrophylla and for the response to that to be fed back to the originator of the IFRAME request?

We’ve done a lot of searching and we keep finding things that almost work. What actually does work? Is IIS’s Url Rewrite the thing to use, and if so, what should the rule/s look like? Or should we be using some C#-y thing instead?

2 Answers

In regards to the question and considering the comments, redirection to an external URL is possible in IIS as shown here.

<system.webServer>
  <rewrite>
    <rules>
      <rule name="External Redirect" stopProcessing="true">
        <match url="^VirtualDirectory" negate="true" />
        <conditions>
          <add input="{HTTP_HOST}" ignoreCase="true" negate="true" pattern="hostname"/>
          <!-- add this input condotion to make this redirect url not work with http://hostname/VirtualDirectory -->
        </conditions>
        <action type="Redirect" url="{your url}" redirectType="Found" />
      </rule>
    </rules>
  </rewrite>
</system.webServer>

Also, a simple redirect is possible using NGIX and is addressed, for instances, in this answer.

server {
    listen 80;
    server_name     example.com;
    return          301 http://www.example.com$request_uri;

server {
    listen 80;
    server_name     www.example.com;
    [...]

and in this answer

server {
  listen 80;
  server_name localhost;
  merge_slashes off;

  location /rdr {
    location /rdr/http:// {
      rewrite ^/rdr/(.*)$ $1 permanent;
    }
    rewrite ^/rdr/(.*)$ http://$1 permanent;
  }
}

Yet, what you want isn't to see the content of that page but to save that data anywhere and then redirect again. Where will that data be coming from then to feed the IFRAME?


Instead of doing this redirect > save data > redirect, I would suggest to do that separately. More specifically, you'd get the data from https://trees.com/ficus/macrophylla and save it in the location of https://figs.wild.com.au/trees/ficus/macrophylla and use what you want from that file for the IFRAMEs.

To get the content of the file in the location https://trees.com (without JS and CSS coming from other files) and save it in an html file, you'd do something like

from urllib.request import urlopen
html = urlopen("http://trees.com").read().decode('utf-8')
#print(html)
with open("test.html", "w") as file:
    file.write(html)

This will save the content in an HTML file named test present in the same location of this script.

(If CSS and JS is also required, do check this SO question).

If you don't want to go through that hustle, there's tools like HTTrack that allow to download complete websites. This way you wouldn't need to know the mapsite to then iterate over the possible variations.


I can see the convenience of what you want. Will investigate further and let you know if find that super-automated way to do this but would help to know "Where will that data be coming from then to feed the IFRAME?".

Answered by Tiago Martins Peres on November 4, 2021

If I go to http://www.trees.com/ficus/macrophylla using the browser, then will get

not found

If I go to http://www.trees.com/ will also get the following

Not sure if that's how it should look like


Using SSL Request to trees.com

SSL Request

Clicking "Click here to ignore the mismatch...", will then get

SSL Request trees.com

In the configuration,

SSL Request configuration

we can see TLS 1.0, 1.1, 1.2 and 1.3 are supported. Yet, green color for TLS 1.2 and 1.3.

We can configure PowerShell to use TLS 1.3

[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls13

And confirm it will be using it

[Net.ServicePointManager]::SecurityProtocol

TLS13 PowerShell


In PowerShell (as Administrator), if one uses Invoke-WebRequest

Invoke-WebRequest -Uri trees.com/ficus/macrophylla

then will get

404 not found

and if one uses

Invoke-WebRequest -Uri trees.com

then will get

it worked


So far so good. But if we want to test it for CORS from the https://figs.wild.com.au,

(Invoke-WebRequest -Uri 'http://trees.com' -Headers @{ "Origin" = "https://figs.wild.com.au" }).Headers

we get

Key                           Value
---                           -----
Transfer-Encoding             chunked
X-Adblock-Key                 MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBAL/3/SrV7P8AsTHMFSpPmYbyv2PkACHwmG9Z+1IFZq3vA54IN7pQcGnhgNo+8SN9r/KtUWCb9OPqTfWM1N4w/EUCAwEAAQ==_FamzgofQ7ugTniHINrZ7yp35i/Nqkt7q/gZsgPGyvhOwIQhj04Bd9+/nir6OLAFDPB56kU4m0GgS7SvEoFqRbQ==
Access-Control-Allow-Origin   *
Access-Control-Allow-Methods  *
Access-Control-Request-Method *
Access-Control-Allow-Headers  *
Access-Control-Max-Age        86400
X-UA-Compatible               IE=Edge,chrome=1
X-Request-Id                  556905ec3cb435a1168cc1b28d70875f
X-Runtime                     0.048014
X-Rack-Cache                  miss
Cache-Control                 max-age=0, private, must-revalidate
Content-Type                  text/html; charset=utf-8
Date                          Mon, 20 Jul 2020 09:40:37 GMT
ETag                          "8e51e434b70033ee6a90cb7397af53f9"
Set-Cookie                    _digiadmin2_session=BAh7B0kiD3Nlc3Npb25faWQGOgZFVEkiJTNmOWRlMDA5NjRiZWZlMzgyZTRmN2NlOWIzZmQxZjIzBjsAVEkiEF9jc3JmX3Rva2VuBjsARkkiMVFOckhMdElRMWc1cGZBcGl5OGQ1WkVNeXo3elpobWRwc2QyR0djTFlNUEE9BjsARg%3D%3D--e55261be794bb9f95ee407c73a3e2b315ef...
Server                        nginx/1.10.1

Headers key Value

Notice that Access-Control-Allow-Origin has the value asterisk (*) which means that any domain is allowed. Then, if we use the following command

Invoke-WebRequest -Uri 'http://trees.com' -Headers @{ "Origin" = "https://figs.wild.com.au" }

we will get the following result

As expected


In other words, it's allowing cross-origin request and not blocking like you're mentioning in the question. Could be that you're giving fictitious URLs too just for the sake of the explanation.

Answered by Tiago Martins Peres on November 4, 2021

Add your own answers!

Ask a Question

Get help from others!

© 2024 TransWikia.com. All rights reserved. Sites we Love: PCI Database, UKBizDB, Menu Kuliner, Sharing RPP