# 学生信息管理系统
**Repository Path**: wdl1999/student
## Basic Information
- **Project Name**: 学生信息管理系统
- **Description**: No description available
- **Primary Language**: Unknown
- **License**: Not specified
- **Default Branch**: master
- **Homepage**: None
- **GVP Project**: No
## Statistics
- **Stars**: 0
- **Forks**: 0
- **Created**: 2020-09-21
- **Last Updated**: 2020-12-19
## Categories & Tags
**Categories**: Uncategorized
**Tags**: None
## README
# 学生信息管理系统
## 介绍
* 学生信息管理系统,涵盖了学生基础信息,增加了可视化界面,极大的提升了管理员的体验度
## 技术支持
1. 前端库:jQuery;
2. UI库:bootstrap;
3. 后端语言:nodejs;
4. 数据库:Mysql;
5. 第三方模块-1:express;
6. 第三方模块-2:express-static;
7. 第三方模块-3:mysql;
8. 内置模块-1:fs;
9. 内置模块-2:url;
## 技术点
1. 省市区三级联动:
* 获取国家所有省市县的详细json文件
* 将json文件转换为js文件,声明一个变量将其存起来
* 在页面刚加载完的时候初始化城市,select有一个特殊的事件叫onchange,select下拉菜单有一个特殊的属性叫selectedIndex,指的是被选中的option标签的下标。
```javascript
let prov = $("#prov");
let areas = $("#area");
let malls = $("#mall");
//重置city
let ast;
let mst;
citys.forEach(item => {
let op = $(``)
prov.append(op);
})
prov.change(function() {
areas.empty();
malls.empty();
ast = this.selectedIndex;
let cityList = citys[ast].mallCityList;
cityList.forEach(item => {
let op = $(``);
areas.append(op);
})
cityList[0].mallAreaList.forEach(item => {
let op = $(``);
malls.append(op);
})
})
areas.change(function() {
malls.empty();
mst = this.selectedIndex;
let list = citys[ast].mallCityList[mst].mallAreaList;
list.forEach(item => {
let op = $(``);
malls.append(op);
})
})
```
2. 数据请求方式
* 前端请求方式:ajax;
* 后端返回方式:正常返回;
## 管理系统主页接口介绍
1. 学生详细信息接口:"/sel"
* 前端无传参,会接取后端返回的一段含有学生详细信息的JSON,包含学生ID(id),学生姓名(name),年龄(age),所在城市(city),性别(sex接收到的性别是1或0,1代表男,0代表女,在根据数据生成可视化界面的时候需经过二次处理);
* 后端无需要接取的参数,收到前端发送的请求时查询数据库的学生信息表(`select * from student order by id`),然后如果查库成功则返回一个包含所有信息的数组,因为在网络环境中只允许传输string和buffer,所以需要将数组反解析(JSON.stringify())成字符串。
2. 删除学生信息:"/del"
* 前端向后端传要被删除学生的id(必传),后端给前端返回一个状态码"success",表示删除成功,如数据库操作失败则收到一个代表失败的状态码;
* 后端接受到前端发送的参数id,将之解析出来之后用sql语句对数据库进行删除(`delete * from student where id=${id}`),操作成功后给前端返回一个代表操作成功的字符串类型的状态码"success",失败返回一i个字符串的"err";
3. 添加学生信息:"/add"
* 前端需要像后端传name(姓名),sex(性别),age(年龄),city(所在城市),后端给前端返回操作的状态码:成功返回"success",操作失败返回"err"
* 后端接取前端传的name,sex,age,city,将之用sql插入到数据库中(`insert into student (name,age,sex,city) values ("${name}","${age}","${sex}","${city}")`),操作成功返回"success",操作失败返回"err"
4. 修改学生信息:"/upt"
* 前端需要先将点击的那一行的name属性值,age属性值,sex属性,city属性值先填入到弹出框中每个框里与三级联动的select中;
* 后端接取前端传的name,sex,age,city,将之用sql从数据库中修改(`update students set name="${name}",sex="${sex}",age="${age}",city="${city}" where id=${id}`),后端给前端返回操作的状态码:成功返回"success",操作失败返回"err"
#### sex的选中问题可以用两种方式解决:
1. 转node节点改变checked属性
```javascript
$(this).closest("tr").find(".sex").html() === "男" ? $("#boy")[0].checked = "checked" : $("#girl")[0].checked = "checked";
```
2. 使用prop方法改变checked属性
```javascript
$(this).closest("tr").find(".sex").html() === "男" ? $("#boy").prop("checked",true) : $("#girl").prop("checked",true);
```
#### 所在城市的三级联动即时填入select框:
1. 先将地址字符串的省市区三级拆分开(函数):
```javascript
function chai(str) {
let prev;
let areas;
let cs = [];
if(str.indexOf("省") !== -1) {
prev = str.slice(0, str.indexOf("省") + 1);
} else {
if(str.indexOf("自治区") !== -1) {
prev = str.slice(0, str.indexOf("自治区") + 3);
} else {
prev = str.slice(0, str.indexOf("市") + 1);
}
}
str = str.replace(prev, "");
if(str.indexOf("辖县") !== -1) {
areas = str.slice(0, str.indexOf("辖县") + 2);
} else {
if(str.indexOf("单位") !== -1) {
areas = str.slice(0, str.indexOf("单位") + 2);
} else {
if(str.indexOf("盟") !== -1) {
areas = str.slice(0, str.indexOf("盟") + 1);
} else {
if(str.indexOf("州") !== -1) {
areas = str.slice(0, str.indexOf("州") + 1);
} else {
if(str.indexOf("地区") !== -1) {
areas = str.slice(0, str.indexOf("地区") + 2);
} else {
areas = str.slice(0, str.indexOf("市") + 1);
}
}
}
}
}
str = str.replace(areas, "");
cs.push(prev);
cs.push(areas);
cs.push(str);
return cs;
}
```
2. 更新至select下拉菜单中:
```javascript
let cit = chai($(this).closest("tr").find(".city").html());
let provo = $("#prov option");
for (let i = 0; i < provo.length; i++) {
if (provo.eq(i).html() === cit[0]) {
prov[0].selectedIndex = i;
ast = i;
break;
}
}
areas.empty();
citys[ast].mallCityList.forEach(item => {
let op = $(``)
areas.append(op);
})
let areao = $("#area option");
for (let i = 0; i < areao.length; i++) {
if (areao.eq(i).html() === cit[1]) {
areas[0].selectedIndex = i;
mst = i;
break;
}
}
malls.empty();
citys[ast].mallCityList[mst].mallAreaList.forEach(item => {
let op = $(``)
malls.append(op);
})
let mallo = $("#mall option");
for (let i = 0; i < mallo.length; i++) {
if (mallo.eq(i).html() === cit[2]) {
malls[0].selectedIndex = i;
break;
}
}
```
##登录注册页面接口介绍
1. 注册接口:"/addun"
* 前端传两个参数:uname(*用户名),pwd(*用户密码);
* 后端接受两个参数:uname,pwd;返回两种状态码:success代表注册成功,already代表已注册;
2. 登录接口:"/selun"
* 前端传两个参数:uname(*用户名),pwd(*用户密码);
* 后端接受两个参数:uname,pwd;返回两种状态码:success代表登录成功,nouser代表无用户名,err代表密码错误;
## 使用说明
1. xxxx
2. xxxx
3. xxxx
## 参与贡献
1. Fork 本仓库
2. 新建 Feat_xxx 分支
3. 提交代码
4. 新建 Pull Request