概述
开发采用前后端分离方式:
1、后端采用Django框架开发,根据项目功能模块建立多个应用APP;
2、前端以vue-element-admin为模板开发;
3、部署采用Nginx+Docker方式。
后端
环境准备
已安装python3.6.8环境和django库
1、项目新建
有两种方式:
a、pycharm里直接创建:File-New Project-Django
b、1)命令行创建一个Django项目:django-admin.py startproject 项目名
2)创建一个APP:python manage.py startapp 应用名
如创建多个APP,多次执行以上命令即可
2、创建数据库
a、编写models.py,创建数据模型
from django.db import models
# Create your models here.
# 测试用例基本情况
class Testcase(models.Model):
# 如果没有models.AutoField,默认会创建一个id的自增列
project = models.ForeignKey(to='pro.Project',on_delete=models.CASCADE,) # 外键——所属项目
name = models.CharField("测试用例名称", max_length=100)
version = models.CharField("版本号", max_length=30)
creator = models.CharField("创建者", null=True, max_length=30)
create_time = models.DateTimeField("创建时间", null=True, auto_now_add=True)
update_time = models.DateTimeField("更新时间", null=True, auto_now=True)
注意:关联其他APP中的class为外键时,可用models.ForeignKey(to='pro.Project',on_delete=models.CASCADE,)
b、创建数据库
1、在settings.py文件中配置数据源:
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'tmp_dev',
'USER': '***',
'PASSWORD': '***',
'HOST': '127.0.0.1',
'PORT': '3306',
}
}
2、按顺序执行以下命令:
python manage.py migrate
python manage.py makemigrations
3、编写视图函数
在每个APP的views.py文件里编写视图函数,不同APP里的model可相互引用。举例如下:
# -*- coding: utf-8 -*-
import sys, json, datetime, math
from django.http import JsonResponse
from django.db.models import F,Q
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
from .models import *
import importlib
import logging
logger = logging.getLogger('A')
importlib.reload(sys)
# Create your views here.
# 返回 projects 统计列表,以便渲染到所有项目的 projects 列表展示界面
def get_projects(request):
page = int(request.GET.get('page', 1))
limit = int(request.GET.get('limit', 10))
keyword = request.GET.get('keyword','')
try:
# print(page,limit,keyword)
projects = Project.objects.filter(
Q(name__icontains=keyword) |
Q(status__icontains=keyword) |
Q(project_leader__icontains=keyword)
).order_by('-status', '-update_time')
total = projects.count() # 不能用函数 len(),一旦用了函数 len(),projects_limit就不再是QuerySet数据类型,而是成了list数据类型
if page > math.ceil(total/limit):
page = math.ceil(total/limit)
paginator = Paginator(projects, limit)
projects_limit = paginator.page(page).object_list
projectpage = list(projects_limit.values(
"id",
"name",
"abbr",
"status",
"project_leader",
"product_leader",
))
except PageNotAnInteger:
projectpage=[]
except EmptyPage:
projectpage = []
data = {
"code": 20000,
"data": {
"page": page,
"total": total,
"items": projectpage
}
}
logger.info('url: %s, method: %s, 返回所有项目的信息。' % (request.path, request.method))
return JsonResponse(data, json_dumps_params={'ensure_ascii': False, 'indent': 2})
4、配置路由
在每个APP的urls.py文件里配置路由信息,路由必须与views.py里的函数对应,例如:
from django.conf.urls import url
import pro.views as views
urlpatterns = [
url(r'^get_pro_sel/$', views.get_pro_sel),
url(r'^get_projects/$', views.get_projects),
url(r'^get_project_basicinfo/$', views.get_project_basicinfo),
url(r'^create/$', views.pro_create, name='pro_create'),
url(r'^update/$', views.pro_update, name='pro_update'),
url(r'^delete/$', views.pro_delete, name='pro_delete'),
]
并在项目根目录下的urls.py里加入各APP模块里的url配置,例如:
from django.contrib import admin
from django.urls import path, include
urlpatterns = [
path('admin/', admin.site.urls),
path('tmp/pro/', include(('pro.urls','pro'),namespace='pro')),
path('tmp/rep/', include(('rep.urls', 'rep'), namespace='rep')),
path('tmp/tc/', include(('tc.urls','tc'),namespace='tc')),
path('tmp/cod/', include(('cod.urls', 'cod'), namespace='cod')),
path('tmp/bug/', include(('bug.urls', 'bug'), namespace='bug')),
path('tmp/rbac/', include(('rbac.urls','rbac'),namespace='rbac')),
]
5、启动服务器
项目目录下运行命令:python manage.py runserver 127.0.0.1:8081
前端
vue-element-admin是一个后台前端解决方案,它基于vue和 element-ui实现。vue-admin-template是一个基础模板。本项目是在vue-admin-template的基础上进行了二次开发。
环境准备
1、安装Vue环境,参考Vue官网:https://cn.vuejs.org/v2/guide/
2、element组件库:https://element.eleme.cn/#/zh-CN/component/installation
3、分别下载vue-admin-template和vue-element-admin源码。
vue-element-admin文档:https://panjiachen.github.io/vue-element-admin-site/zh/guide/
vue-element-admin源码:https://github.com/PanJiaChen/vue-element-admin
vue-admin-template源码:https://github.com/PanJiaChen/vue-admin-template
1、运行vue-admin-template
cd vue-element-admin
#安装依赖
npm install
#启动项目
npm run dev
2、新增页面
请参考vue-element-admin文档,有详细说明。
3、前后端配置
vue.config.js文件里配置前端访问地址和后端服务地址:
const port = process.env.port || process.env.npm_config_port || 9000 // 9528 // dev port
// All configuration item explanations can be find in https://cli.vuejs.org/config/
module.exports = {
/**
* You will need to set publicPath if you plan to deploy your site under a sub path,
* for example GitHub Pages. If you plan to deploy your site to https://foo.github.io/bar/,
* then publicPath should be set to "/bar/".
* In most cases please use '/' !!!
* Detail: https://cli.vuejs.org/config/#publicpath
*/
publicPath: './',
outputDir: 'dist',
assetsDir: 'static',
lintOnSave: process.env.NODE_ENV === 'development',
productionSourceMap: false,
devServer: {
port: port,
open: true,
overlay: {
warnings: false,
errors: true
},
proxy: {
'/tmp': {
target: 'http://127.0.0.1:8081', //后端服务IP和端口号
changeOrigin: true
// pathRewrite: {
// ['^' + process.env.VUE_APP_BASE_API]: ''
// }
}
},
// before: require('./mock/mock-server.js')
},
后端API配置:
举例:在./src/api目录下创建项目相关的api服务,创建文件project.js,引入项目增删改查接口服务。
import request from '@/utils/request'
export function fetchList(query) {
return request({
url: '/tmp/pro/get_projects/',
method: 'get',
params: query
})
}
export function createProject(data) {
return request({
url: '/tmp/pro/create/',
method: 'post',
data
})
}
export function updateProject(data) {
return request({
url: '/tmp/pro/update/',
method: 'post',
data
})
}
export function deleteProject(data) {
return request({
url: '/tmp/pro/delete/',
method: 'post',
data
})
}
前端调用API:
import {fetchList, createProject, updateProject, deleteProject} from '@/api/project'
getList() {
this.listLoading = true
fetchList(this.listQuery).then(response => {
this.list = response.data.items.map(row => {
return {
...row,
edit_status: false,
unfold_status: false,
interval: [row.start_time, row.plan_end_time]
}
})
this.listQuery.page = response.data.page
this.total = response.data.total
this.listLoading = false
})
},
createData() {
this.$refs['dataForm'].validate((valid) => {
if (valid) {
this.temp.start_time = parseTime(this.temp.interval[0])
this.temp.plan_end_time = parseTime(this.temp.interval[1])
createProject(this.temp).then((response) => {
if (response.code !== 20000) {
return Promise.reject(new Error(response.message || 'Error'))
} else {
// this.list.unshift(this.temp)
this.dialogFormVisible = false
this.$notify({
title: 'Success',
message: '新增成功!',
type: 'success',
duration: 2000
})
this.getList()
}
})
}
})
},
部署
1、Vue工程打包
1)vue.config.js,修改配置publicPath: './'
2).env.production,修改配置VUE_APP_BASE_API = '/'
3)在vue项目根路径下执行 npm run build:prod --report
2、Django项目的Docker镜像部署
1)将Django项目包(tmp文件夹)上传到服务器目录/home/下,在/home/tmp/目录下创建front文件夹,再将打包后的vue代码(dist文件夹)上传到front文件夹下;
2)已有centos7+python3.6.8+django库的基础镜像,使用potainner新建容器,配置如下:
3)新建容器完成,启动容器即可。
3、Nginx配置
1)下载并安装nginx,使用start nginx
命令启动服务,测试nginx是否安装成功;
2)修改nginx.conf配置文件如下:
server {
listen 9001; //前端访问端口
location / {
root /home/tmp/front/dist; //放置打包后的vue工程代码
index index.html index.htm;
autoindex on;
autoindex_exact_size on;
autoindex_localtime on;
}
location ^~ /tmp/ {
proxy_http_version 1.1;
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-Host $http_host;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Accept-Encoding 'gzip';
proxy_set_header Connection "upgrade";
add_header Access-Control-Expose-Headers "token";
proxy_pass http://127.0.0.1:8081/tmp/; //Django服务地址
}
add_header Access-Control-Allow-Origin "*";
default_type 'text/html';
charset utf-8;
}
3)修改配置后重启nginx服务,重启命令nginx -s reload
,访问http://127.0.0.1:9001/。
项目源码
Vue前端工程:https://gitee.com/xingxixi/vue-tm.git
Django后端工程:https://gitee.com/ddlyr/tmp.git
注:该项目未开源,需要源码的同学请注册码云后,联系我申请开通权限。