1

This is a Django website being tested via the little server that comes with Django:

python manage.py runserver 8080

The testing client comes in from a browser running on a machine on an external network. I.e. the browser is not running on the server, but rather is running on a desktop and the requests come in over the Internet. A request would have a typical form of https://sub.awebsite.com/path

An ajax POST view incorporates a vendor call that you might recognize:

    class view_class ...
       def post(self, request) 
          ...
          new_session = stripe.checkout.Session.create(
             api_key=djstripe.settings.STRIPE_SECRET_KEY
            ,line_items=[item]
            ,payment_method_types=['card']
            ,success_url='https://a.awebsite.com/path?session_id={CHECKOUT_SESSION_ID}'
            ,cancel_url='https://a.awebsite.com/other_path'
            )

Note the last two arguments are embedding literal URI strings into the website. To python and Django those do not have any special meaning. They are just strings. However later the client will use them to redirect back to awebsite. This literal encoding is really a problem because the site changes depending on who is testing it or if it has been released. I would much rather use the functions build_absolute_uri, or get_current_site, to build those strings. However these functions just print 'localhost'. E.g. I put these two print statements just above the function call to stripe.checkout.Session.create:

print("get_current_site: ", get_current_site(request))
print("post absolute uri: ", request.build_absolute_uri())

And they print:

 get_current_site:  localhost:8080
 absolute uri:  http://localhost:8080/...

I guess absolute_uri is getting its information from the same place as get_current_site.

Now yes, in the settings file, localhost is also listed as an allowed host. If I remove it, then I get a Django splash panel telling me that I need to add localhost to the ALLOWED_HOSTS list. (I am guessing this will not be a problem when coming in through wsgi because it requires an allowed host with the correct name.)

So why are these not printing the site name? Where is localhost coming from? .. and how do I get the actual site name that the client types into the browser to get to the site?

  • 1
    Because you make requests to the localhost. The browser has made a request to `localhost:8080/some/path/to/view`. – Willem Van Onsem May 08 '20 at 19:12
  • the URI typed into the browser has the actual site name. Say the site is called `awebsite.com`, then the ajax request is made to, literally, `https://awebsite.com/sservice`. The string literal 'localhost' does not appear anywhere in the test suite. It only appears in one place in the site code, and that is in the ALLOWED_HOSTS list - and it is only there because Django forced me to put it there. –  May 08 '20 at 19:17
  • no, you can put the name of the hosts on which you are, well hosting your site. But it looks like you are hosting your site locally. Is the `https://a.awebsite.com/` *your* site, or a site where you make requests to (for example an Amazon API)? – Willem Van Onsem May 08 '20 at 19:19
  • `https://a.website.com/` is the DNS name for the server that the Django website is running on. The client is separate desktop machine in a completely different domain, in another building, actually also in another country. If it the client got much farther from the server it would get closer going the other direction. –  May 08 '20 at 19:22

1 Answers1

1

The solution was to add this line into the proxy pass config of nginx:

proxy_set_header Host $http_host;

The location block now looks like this:

 location / {
        proxy_pass http://localhost:8001/;
        proxy_set_header Host $http_host;     
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "Upgrade";
    }

After adding proxy_set_header the get_current_site and all its variations now work correctly.

Note also these: Why does Nginx keep redirecting me to localhost?
How can I get the domain name of my site within a Django template?