Django使用中遇到的问题

情景再现1

创建一个项目名叫TestDemo,然后创建两个程序叫做t1和t2,并且把app注册到settings里面,然后在APP目录下面创建urls.py

注意:我是使用的命令行去创建的,而不是使用pycharm去创建的,所以我的应用并没有默认templates文件夹

image-20240229133328392

image-20240229131106969

使用include来管理路由分发,总路由urls.py

image-20240229131510959

定义app下的urls

image-20240229131958685

视图函数viesw

image-20240229132312686

启动Django项目,分别查看结果

image-20240229132409621

image-20240229132441527

情景再现2

两个app的路由层urls.py不做修改,分别在两个app目录下建立两个一样的templates目录,然后都建立一个register.html

注意:由于我是使用的命令行去创建的,所以根目录下并没有templates文件夹,将templates文件夹以及static文件夹单独存放各自的app单独管理也是一个更好的习惯。

image-20240229134443837

image-20240229133819418

启动Django查看结果

image-20240229133939286

image-20240229134015616

情景再现3

我们在两个app下面分别建立两个static静态目录文件夹,然后在里面都新建一个img的文件夹,将两张不同的图片,都导入进img文件夹,把文件的名称都修改成一样的

image-20240229140139479

image-20240229140228596

修改两个app的register.html代码,其它不做修改

image-20240229140604116

运行Django,浏览器分别查看效果

image-20240229140702865

image-20240229140731800

很明显,这不是我们需要的结果

原因:由于name是没有作用域的,Django在反向解析URL时,会在项目全局顺序搜素,当查找到第一个name指向的URL时,便立即返回。所以,上面访问不同URL,反向解析得到相同的path。

名称空间

使用namespace命名空间,给name设置一个作用域,用include 来管理Test项目URL,并进行namespace(命名空间)。

概念:命名空间(namespace):用来表示标识符的作用范围

一个标识符可以在多个命名空间中定义,它在不同命名空间中的含义是互不相干的。这样,在一个新的命名空间中可定义任何标识符,它们不会与任何已有的标识符发生冲突。

当一个项目中包含多个app,每个app中都有命名相同的标识符时,为了能够使每次访问都能得到想要的结果(访问指定变量),就需要使用namespace。

注意如果设置了名称空间namespace,就需要指定app_name,不然会报错。

  1. 名称空间设置再总的urls.py,即项目名称下面的urls.py
  2. app_name的名称应该与namespace的名称保持一致,设置在app的路由urls.py下
# include使用方法
# 导入 from django.urls import include
# 也可以从 from django.conf.urls import include  都是同一个
from django.urls import path, include

urlpatterns = [
    # include参数直接传递一个元组,元组的第一个参数是urls文件,第二个参数是namespace,相当于我们给目录起的别名
    path('appname/', include('appname.urls', namespace='appname'))
]

# 使用可以通过namespace:name去使用
# 比如 t1: register

问题解决

方案1

第一步

总urls.py设置如下,导入include模块,然后参考下面去写

# 总的urls.py
from django.contrib import admin
from django.urls import path, include

urlpatterns = [
    path('admin/', admin.site.urls),
    path('t1/', include('t1.urls', namespace='t1')),
    path('t2/', include('t2.urls', namespace='t2'))
]

app的路由可以参考下面去写,记得设置好app_name

# t1/url.py
from django.urls import path
from . import views

app_name = 't1'

urlpatterns = [
    # 这里的name='register'中的register 就是别名
    path('register/', views.register, name='register')
]
# t2.urls.py
from django.urls import path
from . import views

app_name = "t2"

urlpatterns = [
    path('register/', views.register, name='register')
]

第二步

在每一个app的templates文件夹下,都建立一个和app名称一样的文件夹,然后再static下面也建立一个和app名称一样的文件夹,html文件和图片文件都移动到刚刚新建的对应的文件下面

image-20240229151803915

两个视图层以及register.html的代码如下

image-20240229152209078

回到浏览器查看效果

image-20240229145623938

image-20240229145711916

方案2

不用设置名称空间,在方案1的基础上,对总路由urls.py做如下修改也可以达到效果

from django.contrib import admin
from django.urls import path, include

urlpatterns = [
    path('admin/', admin.site.urls),
    # 由于不需要声明名称空间, Include必须包含一个元组,所以这里使用逗号隔开就可以了
    path('t1/', include('t1.urls',)),
    path('t2/', include('t2.urls',))
]

参考博文

https://blog.csdn.net/Vincent_Zhang233/article/details/127057383

https://blog.csdn.net/J_wb49/article/details/103055521

posted @ 2024-03-23 00:49  小满三岁啦  阅读(3)  评论(0编辑  收藏  举报