1.创建项目pycharm文件/cmd命令:django-admin startproject +项目名
2.创建子应用/命令:python manage.py startapp +子应用名
3.项目文件下的__init__.py 安装数据库
import pymysql
pymysql.install_as_MySQLdb()
4.项目文件下的settings.py 配置
INSTALLED_APPS = [
'School', # 注册子应用
'corsheaders', # 跨域
'rest_framework', # def框架
]
MIDDLEWARE = [
# 'django.middleware.csrf.CsrfViewMiddleware', # 注释掉 防止跨站伪造
'corsheaders.middleware.CorsMiddleware' # 加入 中间件
]
CORS_ORIGIN_ALLOW_ALL = True # 允许所有的源进行访问
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'HOST':'localhost', # 主机
'PORT':3306, # 端口
'USER':'root', # 账号
'PASSWORD':'123456', # 密码
'NAME':'zx2' # 数据库名
}
}
LANGUAGE_CODE = 'zh-Hans' # 时间
TIME_ZONE = 'Asia/Shanghai' # 地区
5.路由分发
(1)项目文件下的主路由配置
from django.contrib import admin
from django.urls import path,include
from School import urls
urlpatterns = [
path('admin/', admin.site.urls),
path('',include(urls))
]
(2)子应用下的子路由配置
from django.urls import path
urlpatterns = [
]
6.子应用下文件配置,models.py配置模型类
from django.db import models
# Create your models here.
class School(models.Model):
school_name = models.CharField(max_length=20,verbose_name='学校名称')
class Meta:
verbose_name='学校表' # admin中定义的学校表
verbose_name_plural=verbose_name # 复数形式
db_table = 'School' # 数据库表的名字
def __str__(self): # 定义魔法方法
return self.school_name # 指定school_name字段
class Student(models.Model):
stu_name = models.CharField(max_length=20,verbose_name='姓名')
hobby = models.CharField(max_length=20,verbose_name='爱好')
score = models.IntegerField(verbose_name='成绩')
# 外键绑定 to=关联School表 on_delete=级联操作 CASCADE同时删除 verbose_name=外键名字
kind = models.ForeignKey(to=School,on_delete=models.CASCADE,verbose_name='学校名称')
class Meta:
verbose_name='学生表'
verbose_name_plural=verbose_name
db_table = 'Student'
def __str__(self):
return self.stu_name
7.执行数据库迁移操作
迁移: python manage.py makemigrations
执行迁移:python manage.py migrate
8.子应用下文件配置,admin.py创建超级用户,导入模型类
from django.contrib import admin
from School.models import School,Student #导入模型类
# Register your models here.
admin.site.register(Student)
admin.site.register(School)
9.创建超级用户
命令:python manage.py createsuperuser
10.进去django管理添加测试数据
运行项目命令:python manage.py runserver
网址:http://127.0.0.1:8000/admin/
11.子应用下创建 serializers序列化py文件
from rest_framework import serializers #导入serializers
from School.models import School,Student #导入模型类
# 编写序列化器 继承的是serializers中的ModelSerializer
class SchoolSerializers(serializers.ModelSerializer):
class Meta:
# model中School模型
model = School
# 字段映射'__all__'所有字段
fields = '__all__'
class StudentSerializers(serializers.ModelSerializer):
# 增加school_name 字段 用于读取学校名称
# 自定义字段school_name 继承serializers中的SerializerMethodField
# (read_only=True) 只读
school_name = serializers.SerializerMethodField(read_only=True)
# def定义school_name用get获取的方法 obj指具体的某一个对象
# obj 类别组 模型类对象
def get_school_name(self,obj):
# 返回 obj对象中调用外键kind中的school_name字段 (学校表中school_name学校名称)
return obj.kind.school_name
class Meta:
model = Student
fields = '__all__'
12.子应用下文件配置,views.py创建视图
from django.shortcuts import render
from rest_framework.viewsets import ModelViewSet #导入ModelViewSet
from rest_framework.filters import SearchFilter,OrderingFilter #导入过滤和排序
from School.models import School,Student #导入模型类
from School.serializers import SchoolSerializers,StudentSerializers #导入序列化器
# Create your views here.
# 继承ModelViewSet 实现对学校的增删查改
class SchoolView(ModelViewSet):
queryset = School.objects.all()
serializer_class = SchoolSerializers
class StudentView(ModelViewSet):
queryset = Student.objects.all()
serializer_class = StudentSerializers
# 导入过滤,排序功能
filter_backends = [SearchFilter,OrderingFilter]
# 过滤字段 通过过滤出的字段来查询
search_fields = ['stu_name','hobby','kind__id']
# 排序字段
ordering_fields = ['score']
13.配置子路由
from django.urls import path
from rest_framework import routers #导入routers
from School import views # 导入views视图
urlpatterns = [
]
# 用routers生成路由对象 通过routers中的SimpleRouter()
router = routers.SimpleRouter()
# 用router.register生成路由信息
# 'school' 前面是路由,后面是给路由起的名字,中间调用views中SchoolView视图
router.register('school',views.SchoolView,'school')
router.register('stu',views.StudentView,'stu')
# 路由追加,上面urlpatterns += router.urls
urlpatterns += router.urls
14.后端配置完成,页面查看效果
(1)运行项目python manage.py runserver
(2)根据路由对应操作
1.admin/ #django管理路由
2.^school/$ [name='school-list'] # 学校信息路由
# 学校信息动态路由
# 根据编号查询对应的学校信息
# 例:http://127.0.0.1:8000/school/1/
3.^school/(?P<pk>[^/.]+)/$ [name='school-detail']
4.^stu/$ [name='stu-list'] # 学生信息路由
# 学生信息动态路由 可以根据高级功能设定的字段进行过滤查找和排序展示
# 查询学生id为1 :http://127.0.0.1:8000/stu/1/
# 模糊查询学生姓名:http://127.0.0.1:8000/stu/?search=宋
# 查询学生所属学校,年龄降序展示 http://127.0.0.1:8000/stu/?search=1&ordering=-score
5.^stu/(?P<pk>[^/.]+)/$ [name='stu-detail']
15.创建前端code/vue项目
项目命令cmd:vue create +项目名
(1)选3 (2)空格勾选Router 和 Vuex (3)选版本3 (4)输y (5)选1 (6)输n
项目开始创建
15.2 运行项目命令 npm run serve
16.配置跨域/code文件夹全局下创建vue.config.js文件
module.exports={
devServer:{
proxy:'http://127.0.0.1:8000/'
}
}
17.1 安装axios 命令:npm install axios -- save
17.2 src目录下创建工具文件夹utils,在utils文件夹下创建文件request开始封装请求方法
import Axios from "axios"
export function put(url,params){
return Axios.put(url,params)
}
export function del(url,params){
return Axios.delete(url,params)
}
export function post(url,params){
return Axios.post(url,params)
}
export function get(url,params){
return Axios.get(url,params)
}
18.可有可无的操作:
1.路由router下注释不用的两个配置文件
2.视图views下删除多余的两个vue文件
3.导航栏app注释没用的导航标题
19.views文件夹下创建需要的几个视图文件 后缀名为.vue
1.视图vue文件中输入vue回车,模板的快捷方式
20.开始配置router文件中的路由
import School from '../views/School.vue'
import Stu from '../views/Stu.vue'
import Xin from '../views/Xin.vue'
const routes = [
{
path: '/', # 视图的路由
name: 'School', # 视图路由的名字
component: School # 组件
},
{
path: '/stu',
name: 'Stu',
component: Stu
},
{
path: '/xin',
name: 'Xin',
component: Xin
},
]
21.在APP.vue配置导航栏 (可有可无)
<router-link to="/">学校页面</router-link> |
<router-link to="/stu">学生页面</router-link> |
<router-link to="/xin">排序页面</router-link>
22.开始编写views文件中的视图
(1)主表视图
<template>
<p>学校页面</p>
<table border="1" align="center">
<tr>
<th>编号</th>
<th>学校名称</th>
</tr>
<tr v-for="(item,i) in SchList" :key="i">
<td>{{item.id}}</td>
<td>
<router-link :to="{name:'Stu',params:{id:item.id}}">
{{item.school_name}}
</router-link>
</td>
</tr>
</table>
</template>
<script>
import { get } from '@/utils/request'
export default {
data(){
return{
SchList:[],
}
},
mounted(){
this.SchData();
},
methods:{
SchData(){
get('school/')
.then((resp) => {
console.log(resp)
this.SchList = resp.data
}).catch((err) => {
console.log(err)
});
}
}
}
</script>
<style>
</style>
(2)从表视图
<template>
<p>学生页面</p>
<table border="1" align="center">
<tr>
<th>编号</th>
<th>姓名</th>
<th>爱好</th>
<th>成绩</th>
<th>学校名称</th>
<th>操作</th>
</tr>
<tr v-for="(item,i) in StuList" :key="i">
<td>{{item.id}}</td>
<td>{{item.stu_name}}</td>
<td>{{item.hobby}}</td>
<td>{{item.score}}</td>
<td>{{item.school_name}}</td>
<td>
<button @click="upd(i)">修改</button>
<button @click="remove(item.id)">删除</button>
</td>
</tr>
</table>
<p>修改学生信息</p>
编号:<input type="text" v-model="id"><br>
姓名:<input type="text" v-model="stu_name"><br>
爱好:<input type="text" v-model="hobby"><br>
成绩:<input type="text" v-model="score"><br>
学校名称:<select name="aa" v-model="kind">
<option v-for="(item,i) in SchList" :key="i" :value="item.id">{{item.school_name}}</option>
</select>
<button @click="update">确认修改</button>
<p>添加学生信息</p>
姓名:<input type="text" v-model="stu_name2"><br>
爱好:<input type="text" v-model="hobby2"><br>
成绩:<input type="text" v-model="score2"><br>
学校名称:<select name="bb" v-model="kind2">
<option v-for="(item,i) in SchList" :key="i" :value="item.id">{{item.school_name}}</option>
</select>
<button @click="addData">确认添加</button>
<p>根据 学生姓名 和 爱好 搜索学生信息</p>
<input type="text" v-model="soudata">
<button @click="sou">搜索</button>
<p>{{SouList}}</p>
</template>
<script>
import { del, get, post, put } from '@/utils/request'
export default {
data(){
return{
Sch_id : this.$route.params.id,
StuList:[],
SchList:[],
SouList:[],
soudata:'',
id:0,stu_name:'',hobby:'',score:0,kind:0,
stu_name2:'',hobby2:'',score2:0,kind2:0,
}
},
mounted(){
this.StuData();
this.SchData();
},
methods:{
SchData(){
get('school/')
.then((resp) => {
console.log(resp)
this.SchList = resp.data
}).catch((err) => {
console.log(err)
});
},
StuData(){
let url = 'stu/?search=' + this.Sch_id
get(url)
.then((resp) => {
console.log(resp)
this.StuList = resp.data
}).catch((err) => {
console.log(err)
});
},
remove(id){
let url = 'stu/' + id + '/'
del(url)
.then((resp) => {
console.log(resp)
alert('删除成功')
this.StuData()
}).catch((err) => {
console.log(err)
});
},
upd(i){
this.id=this.StuList[i].id
this.stu_name=this.StuList[i].stu_name
this.hobby=this.StuList[i].hobby
this.score=this.StuList[i].score
this.kind=this.Sch_id
},
update(){
let url = 'stu/' + this.id + '/'
let obj = {id:this.id,stu_name:this.stu_name,hobby:this.hobby,score:this.score,kind:this.kind}
put(url,obj)
.then((resp) => {
console.log(resp)
alert('修改成功')
this.StuData()
}).catch((err) => {
console.log(err)
});
},
addData(){
let obj = {stu_name:this.stu_name2,hobby:this.hobby2,score:this.score2,kind:this.kind2}
post('stu/',obj)
.then((resp) => {
console.log(resp)
alert('添加成功')
this.StuData()
}).catch((err) => {
console.log(err)
});
},
sou(){
let url = 'stu/?search=' + this.soudata
get(url)
.then((resp) => {
console.log(resp)
this.SouList = resp.data
}).catch((err) => {
console.log(err)
});
}
}
}
</script>
<style>
</style>
(3)单独一个表,排序展示信息
<template>
<table border="1" align="center">
<tr>
<th>编号</th>
<th>姓名</th>
<th>爱好</th>
<th>成绩</th>
<th>学校名称</th>
</tr>
<tr v-for="(item,i) in StuList" :key="i">
<td>{{item.id}}</td>
<td>{{item.stu_name}}</td>
<td>{{item.hobby}}</td>
<td>{{item.score}}</td>
<td>{{item.school_name}}</td>
</tr>
</table>
</template>
<script>
import { get } from '@/utils/request'
export default {
data(){
return{
StuList:[],
}
},
mounted(){
this.StuData()
},
methods:{
StuData(){
let url = 'stu/?ordering=score'
get(url)
.then((resp) => {
console.log(resp)
this.StuList = resp.data
}).catch((err) => {
console.log(err)
});
},
}
}
</script>
<style>
</style>