如何在Nginx中使用Proxy_Pass时使用Django请求获取真实的域名

mfpqipee  于 2023-11-17  发布在  Nginx
关注(0)|答案(1)|浏览(183)

我使用docker和nginx来运行我的系统,但我现在遇到了一个问题,我想将我的系统的客户端用户自动重定向到一个子域。即类似prod.example.com的东西。这已经在我的nginx配置中工作,以复制对页面的访问,但我想将特定的client URLMap到子域,而不是主域。
通常这在Django中很简单,使用如下代码:

  1. if not 'prod.' in request.get_host():
  2. redirect(f'app.{request.get_host()}')
  3. # example # get_host()=app | get_absolute_ur()=http://app/, meta: app

字符串
但是我的nginx代理传递使用了一个上游变量,看起来这就是上面尝试的变量所传递的全部内容。我如何才能做到这一点?

  1. upstream app {
  2. server web:8000; # appserver_ip:ws_port
  3. }
  4. server {
  5. server_name prod.example.com;
  6. listen 80;
  7. client_max_body_size 250M;
  8. # enforces HSTS or only content from https can be served. We do this in CloudFlare
  9. add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
  10. add_header Permissions-Policy "autoplay=(), encrypted-media=(), fullscreen=(), geolocation=(), microphone=(), browsing-topics=(), midi=()" always;
  11. location / {
  12. proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  13. proxy_pass http://app;
  14. proxy_http_version 1.1;
  15. proxy_set_header Upgrade $http_upgrade;
  16. proxy_set_header Connection "upgrade";
  17. proxy_redirect off;
  18. proxy_headers_hash_max_size 512;
  19. proxy_headers_hash_bucket_size 128;
  20. }
  21. }

gwo2fgha

gwo2fgha1#

Okay@nigel239通过漂亮的文档链接给了我解决方案。总的来说,我的想法是为每个服务器块->位置传递一个X-Forwarded-Host值到我的NGINX配置:

  1. upstream app {
  2. server web:8000; # appserver_ip:ws_port
  3. }
  4. server {
  5. # example.com is main site, prod.example.com is the system
  6. server_name example.com prod.example.com;
  7. listen 80;
  8. client_max_body_size 250M;
  9. # enforces HSTS or only content from https can be served. We do this in CloudFlare
  10. add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
  11. add_header Permissions-Policy "autoplay=(), encrypted-media=(), fullscreen=(), geolocation=(), microphone=(), browsing-topics=(), midi=()" always;
  12. location / {
  13. proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  14. proxy_set_header X-Forwarded-Host $host;
  15. proxy_pass http://app;
  16. proxy_http_version 1.1;
  17. proxy_set_header Upgrade $http_upgrade;
  18. proxy_set_header Connection "upgrade";
  19. proxy_redirect off;
  20. proxy_headers_hash_max_size 512;
  21. proxy_headers_hash_bucket_size 128;
  22. }
  23. }

字符串
然后在settings.py用途:USE_X_FORWARDED_HOST = True
然后在我的中间件中,我可以使用request.META值来获取它:

  1. class RedirectMiddleware(MiddlewareMixin):
  2. def process_request(self, request):
  3. try:
  4. session_key = request.COOKIES.get(settings.SESSION_COOKIE_NAME)
  5. # print('key loaded middleware', session_key)
  6. # print(request.path, resolve(request.path_info).kwargs)
  7. kwargs = resolve(request.path_info).kwargs
  8. if 'client_url' in kwargs:
  9. client = ClientInformation.objects.filter(url_base=kwargs['client_url']).last()
  10. if client:
  11. # using this to ensure clients go to app....
  12. if settings.PROD:
  13. if request.META and request.META.get('HTTP_X_FORWARDED_HOST'):
  14. # we hold this reference
  15. if request.META.get('HTTP_X_FORWARDED_HOST', '') != 'prod.example.com':
  16. # redirect
  17. proto = 'https' # still passed in but we know what it should be
  18. host = 'prod.example.com'
  19. path = request.get_full_path()
  20. url_to_redirect_to = f'{proto}://{host}{path}'
  21. print(url_to_redirect_to)
  22. return redirect(url_to_redirect_to, permanent=True)
  23. else:
  24. pass
  25. # print('client url found')
  26. request.session = self.SessionStore(session_key)
  27. request.client = client

展开查看全部

相关问题