2015-02-10 17 views
3

我已经设置了一个Django项目,它使用django-rest-framework来提供一些ReST功能。网站和其他功能都工作正常。API端点的Django子域配置

但是有一个小问题:我需要我的API端点指向不同的子域

例如,当用户访问该网站,他/她可以正常地按照我的urls.py浏览各地:

http://example.com/control_panel 

到目前为止好。 但是,当使用API​​时,我想将其更改为更合适的内容。所以,而不是http://example.com/api/tasks我需要这成为:

http://api.example.com/tasks 

我应该怎么做?

在此先感谢。

P.S. 该网站将在Gunicorn上运行,并将nginx作为反向代理。

+0

你有没有得到这个工作?我不能相信我没有在我的搜索中找到这个,但我实际上写了一个重复:http://stackoverflow.com/questions/29807091/deploy-django-rest-api-to-api-example-com-apache -2-2-mod-wsgi-mod-rewrite这里提供的中间件方法是否适合你? – nicorellius 2015-04-23 22:28:06

+0

@nicorellius我设法通过使用Django-hosts包来实现它。在pypi上查看它,但是请注意,它目前仅适用于Django 1.7.x.我希望我能帮上忙。 – kstratis 2015-04-23 22:38:56

+0

@ Konos5 - 非常感谢小费!我正在努力整合这一点。确切地说,我正在寻找...嘿,有一点难以配置它,你遇到的任何提示或技巧或陷阱?例如,你是如何在API URLConf中处理你的'include(router.urls)'的? – nicorellius 2015-04-23 23:19:39

回答

1

我有一个类似的问题,基于Django的API。我发现编写一个自定义中间件类并使用它来控制哪些URL在哪个子域上提供服务很有用。

Django在提供URL时并不关心子域,所以假设您的DNS设置为api.example.com指向您的Django项目,那么api.example.com/tasks/将调用预期的API视图。

问题是www.example.com/tasks/也会调用API视图,并且api.example.com将在浏览器中提供主页。

所以有点中间件可以检查子域匹配了网址,并提高响应404如果合适的话:

## settings.py 

MIDDLEWARE_CLASSES += (
    'project.middleware.SubdomainMiddleware', 
) 


## middleware.py 

api_urls = ['tasks'] # the URLs you want to serve on your api subdomain 

class SubdomainMiddleware: 
    def process_request(self, request): 
     """ 
     Checks subdomain against requested URL. 

     Raises 404 or returns None 
     """ 
     path = request.get_full_path() # i.e. /tasks/ 
     root_url = path.split('/')[1] # i.e. tasks 
     domain_parts = request.get_host().split('.') 

     if (len(domain_parts) > 2): 
      subdomain = domain_parts[0] 
      if (subdomain.lower() == 'www'): 
       subdomain = None 
      domain = '.'.join(domain_parts[1:]) 
     else: 
      subdomain = None 
      domain = request.get_host() 

     request.subdomain = subdomain # i.e. 'api' 
     request.domain = domain # i.e. 'example.com' 

     # Loosen restrictions when developing locally or running test suite 
     if not request.domain in ['localhost:8000', 'testserver']: 
      return # allow request 

     if request.subdomain == "api" and root_url not in api_urls: 
      raise Http404() # API subdomain, don't want to serve regular URLs 
     elif not subdomain and root_url in api_urls: 
      raise Http404() # No subdomain or www, don't want to serve API URLs 
     else: 
      raise Http404() # Unexpected subdomain 
     return # allow request 
+0

我想你的意思是:'如果request.domain在['localhost:8000','testserver']:'('不'不应该在那里)。 – jeffjv 2015-05-14 02:16:00