【Django入门】——从模型类关联关系的一对多到自关联

文章目录

  • 一、创建自关联数据表
    • 1. 创建模型类
    • 2. 迁移生成表
    • 3. 插入示例数据
  • 二、定义视图函数
  • 三、创建模板文件
  • 四、配置URL路由
    • 1. 配置项目`urls.py`文件
    • 2. 配置应用`urls.py`文件

在文章MySQL数据库入门(4)——自关联中,我们初步接触了自关联,而在【Django入门】——模型类的关联关系简介中我们知道数据表之间的关系中有一种是一对多。

实际上,自关联就是一种特殊的一对多关系。本文就将通过Django框架,通过自关联实现这样一个需求:

  • 通过模型类创建一个具有自关联特性的全国省、市、县(区)行政区域信息表;
  • 在浏览器输入127.0.0.1:8000/areas时显示合肥市的上级地区和下级地区,如下所示:

当前地区

合肥市

父级地区

安徽省

子级地区

  • 市辖区
  • 长丰县
  • 肥东县
  • 肥西县
  • 庐江县
  • 巢湖市

为简便起见,此处依然使用【Django入门】——通过模型类查询MySQL数据库基本操作中用到的test3项目和MySQL数据库db4_test3

一、创建自关联数据表

1. 创建模型类

为生成与MySQL数据库入门(4)——自关联中的案例相同结构的数据表,可以首先定义一个模型类AreaInfo

# models.py

......

class AreaInfo(models.Model):
    """地区模型类"""
    # 地区名称
    area_title = models.CharField(max_length=20)
    # 关系属性,当前地区的父级地区
    area_parent = models.ForeignKey('self', models.CASCADE, null=True, blank=True)

需要注意的是:

  • 由于自关联是一种特殊的一对多,所以在AreaInfo类中也应该有一个ForeignKey创建的类属性,名为area_parent
  • 由于类属性area_parent对应的关联关系字段和AreaInfo生成的数据表发生关联,则ForeignKey的第一个参数应该为'self'

2. 迁移生成表

迁移生成表的流程在此不做赘述,下面是成功生成数据表后查看的表结构。

mysql> show tables;
+----------------------------+
| Tables_in_db4_test3        |
+----------------------------+
......
| booktest_areainfo          |
| booktest_bookinfo          |
| booktest_heroinfo          |
......
+----------------------------+
13 rows in set (0.00 sec)

mysql> desc booktest_areainfo;
+----------------+-------------+------+-----+---------+----------------+
| Field          | Type        | Null | Key | Default | Extra          |
+----------------+-------------+------+-----+---------+----------------+
| id             | int(11)     | NO   | PRI | NULL    | auto_increment |
| area_title     | varchar(20) | NO   |     | NULL    |                |
| area_parent_id | int(11)     | YES  | MUL | NULL    |                |
+----------------+-------------+------+-----+---------+----------------+
3 rows in set (0.00 sec)

3. 插入示例数据

为了后续演示,需要向上述生成的数据表booktest_areainfo中插入示例数据。

mysql> source areas.sql;

插入数据的语句可从此处获取,且需要注意的是,当使用上述批量插入的文件时,需要保证文件存放的路径和在终端连接MySQL的路径一致。

二、定义视图函数

# views.py
from django.shortcuts import render
from booktest.models import AreaInfo


# Create your views here.
def areas(request):
    """获取合肥市的上下级地区"""
    # 1.获取合肥市的信息
    area = AreaInfo.objects.get(area_title='合肥市')
    # 2.查询合肥市的上级地区
    parent_area = area.area_parent
    # 3.查询合肥市的下级地区
    child_area = area.areainfo_set.all()
    # 4.使用模板
    return render(request=request,
                  template_name='booktest/areas.html',
                  context={
                      'area': area,
                      'parent_area': parent_area,
                      'child_area': child_area
                  })

三、创建模板文件

首先,在和应用booktest同级的路径下新建目录templates,然后在templates下新建目录booktest,最后在booktest下新建areas.html文件。



<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>自关联案例title>
head>
<body>
<h1>当前地区h1>
{{area.area_title}}<br/>
<h1>父级地区h1>
{{parent_area.area_title}}
<h1>子级地区h1>
<ul>
    {%for child in child_area%}
        <li>{{child.area_title}}li>
    {%endfor%}
ul>
body>
html>

需要注意的是,为了让Django框架能在运行时找到templates目录下的模板文件,需要在项目的settings.py文件中作如下修改:

import os

# Build paths inside the project like this: os.path.join(BASE_DIR, ...)
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))

......

TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        'DIRS': [os.path.join(BASE_DIR, 'templates')],  # 设置模板目录,
       ......
    },
]

四、配置URL路由

1. 配置项目urls.py文件

# 项目的urls.py文件
from django.contrib import admin
from django.urls import path
from django.conf.urls import url, include

urlpatterns = [
    path('admin/', admin.site.urls),
    url(r'^', include('booktest.urls')),  # 包含booktest的urls文件
]

2. 配置应用urls.py文件

from django.conf.urls import url
from booktest import views

urlpatterns = [
    url(r'^areas$', views.areas),  # 关联url和视图函数areas
]

至此,需求实现。

你可能感兴趣的:(#,Django框架)