Django 项目中的动态子域和 url 路径
Dynamic subdomains and url paths in django project
我正在尝试在我的 django 项目中实现动态子域和 urls 系统。
一般来说,每个用户都有自己的域,例如。 myusername.example.com
用户可以定义动态 URL,例如:
- myusername.example.com/something1
- myusername.example.com/something2
- myusername2.example.com/something1
- myusername2.example.com/something2
但我在 example.com 上也有我的网站 运行,其中有 urls like example.com/contact、example.com/about-us 等等。
我希望所有这些 URL 都指向我的自定义视图(基于 class),我在其中执行一些数据库查询和 return 动态内容。这个 somethin1/something2 部分是完全动态的,可能有任何东西。由用户定义。
我有这样的东西:
urls.py
from web.views import HomeView, ContactView
urlpatterns = [
path('admin/', admin.site.urls),
path('contact', ContactView.as_view()),
path('', HomeView.as_view()),
re_path('.*', HomeView.as_view())
]
web.views.py
class HomeView(TemplateView):
template_name = 'home.html'
def dispatch(self, request, *args, **kwargs):
SERVICE_DOMAIN = settings.DOMAIN
http_host = str(request.META.get('HTTP_HOST'))
if SERVICE_DOMAIN in http_host:
subdomains = http_host.split(SERVICE_DOMAIN)[0]
subdomain = slugify.slugify(subdomains)
else:
subdomain = False
if subdomain:
print('Our subdomain is {}'.format(subdomain))
kwargs['subdomain'] = subdomain
return CustomUrlView.as_view()(self.request, *args, **kwargs)
if not subdomain:
print('run normally')
return super().dispatch(request, *args, **kwargs)
class CustomUrlView(View):
def dispatch(self, request, *args, **kwargs):
subdomain = kwargs.get('subdomain')
url = request.META.get('PATH_INFO').lower().strip().replace('/', '', 1)
# here I do some queries in DB with my url variable - it has own model etc.
一般来说,几乎所有用户定义的 urls 一切正常...
问题是当访问者打开 myusername.example.com/contact - 它总是匹配 urls.py 中定义的 url 并且它没有被我的 HomeView 捕获。
我该如何解决?当请求来自子域时,我不想使用我在 urls.py 中定义的任何基于 class 的视图的 url。
您需要有两个不同的 urls 文件。一个用于域,第二个用于子域。
- 在两个 url 文件中拆分域和子域视图。如果您有适用于两者的观点,例如登录,创建一个 "common" 文件并包含在两个 url 中。
- 您可以选择要使用的 url,因此创建一个中间件并检查主机
request.META.get('HTTP_HOST')
。如果请求来自子域,则只需加载适当的 urls request.urlconf = 'path.to_subdomain.urls'
注意:
确保 settings.py 中的 ROOT_URLCONF
指向“域” url。此外,在你的中间件中,你应该检查子域是否存在,如果不存在,则 return 404不存在。
我正在尝试在我的 django 项目中实现动态子域和 urls 系统。
一般来说,每个用户都有自己的域,例如。 myusername.example.com 用户可以定义动态 URL,例如:
- myusername.example.com/something1
- myusername.example.com/something2
- myusername2.example.com/something1
- myusername2.example.com/something2
但我在 example.com 上也有我的网站 运行,其中有 urls like example.com/contact、example.com/about-us 等等。
我希望所有这些 URL 都指向我的自定义视图(基于 class),我在其中执行一些数据库查询和 return 动态内容。这个 somethin1/something2 部分是完全动态的,可能有任何东西。由用户定义。
我有这样的东西:
urls.py
from web.views import HomeView, ContactView
urlpatterns = [
path('admin/', admin.site.urls),
path('contact', ContactView.as_view()),
path('', HomeView.as_view()),
re_path('.*', HomeView.as_view())
]
web.views.py
class HomeView(TemplateView):
template_name = 'home.html'
def dispatch(self, request, *args, **kwargs):
SERVICE_DOMAIN = settings.DOMAIN
http_host = str(request.META.get('HTTP_HOST'))
if SERVICE_DOMAIN in http_host:
subdomains = http_host.split(SERVICE_DOMAIN)[0]
subdomain = slugify.slugify(subdomains)
else:
subdomain = False
if subdomain:
print('Our subdomain is {}'.format(subdomain))
kwargs['subdomain'] = subdomain
return CustomUrlView.as_view()(self.request, *args, **kwargs)
if not subdomain:
print('run normally')
return super().dispatch(request, *args, **kwargs)
class CustomUrlView(View):
def dispatch(self, request, *args, **kwargs):
subdomain = kwargs.get('subdomain')
url = request.META.get('PATH_INFO').lower().strip().replace('/', '', 1)
# here I do some queries in DB with my url variable - it has own model etc.
一般来说,几乎所有用户定义的 urls 一切正常... 问题是当访问者打开 myusername.example.com/contact - 它总是匹配 urls.py 中定义的 url 并且它没有被我的 HomeView 捕获。
我该如何解决?当请求来自子域时,我不想使用我在 urls.py 中定义的任何基于 class 的视图的 url。
您需要有两个不同的 urls 文件。一个用于域,第二个用于子域。
- 在两个 url 文件中拆分域和子域视图。如果您有适用于两者的观点,例如登录,创建一个 "common" 文件并包含在两个 url 中。
- 您可以选择要使用的 url,因此创建一个中间件并检查主机
request.META.get('HTTP_HOST')
。如果请求来自子域,则只需加载适当的 urlsrequest.urlconf = 'path.to_subdomain.urls'
注意:
确保 settings.py 中的 ROOT_URLCONF
指向“域” url。此外,在你的中间件中,你应该检查子域是否存在,如果不存在,则 return 404不存在。