首先来说说我在搭建之前都先了解了什么:npm 包管理器、node模块、包的概念,前后端分离,模板的渲染、mongodb数据库、数据库操作,数据库的链接、用Romogondb工具可视化数据库及连接操作等。
建站目录
本次demo的练习让我理清了node开发的基本流程及前后端逻辑。
在开发之前,建好项目目录我觉得这是最重要的,在建站之前,你必须建立一些需求,我是打算写一个关于图书管理,共四个页面的网站,首页、后台数据录入页、列表数据页(用来获取数据库中的全部数据展现在页面上)、详情页(每一个id对应的数据页),然后链接数据库,实现数据库的添加、查找、修改、删除操作。下面是我的目录:
- db#用来存放启动数据库的数据
- models#用来存放对象在数据库中模型
- node_modules#用来存放项目所需的模板
- public#用来放前端的js、css、images文件
- routes#存放后端路由
- schemas#用来存放对象所需的字节信息
- views#存放视图模板的目录
- app.js#项目的入口文件
- package.json#包管理文件
具体如下:
建站实施
我用的视图模板是html,他没有自动填充后台接口数据的语法,所以我用的是传统的ajax请求实现数据的获取,下面我就直接粘代码了,很多解释我都有代码注释的,在开发中遇到的问题我也会描述的。
- 入口文件:app.js
var express = require('express');
var mongoose=require('mongoose');//引入模块
var path = require('path');
/*var _ = require('underscore');*///新更新的数据替换
var Book = require('./models/book');
var bodyParser = require('body-parser');
var swig = require('swig');
//创建web实例
var app = express();
var admin = require('./routes/admin');
var index = require('./routes/index');
var list = require('./routes/list');
var watch = require('./routes/watch');
//定义模板
app.engine('html', swig.renderFile);
//设置模板目录
app.set('views', './views');
//注册模板
app.set('view engine', 'html');
/*//取消模板缓存
swig.setDefaults({cache:false});*/
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
//express配置静态文件
app.use(express.static(path.join(__dirname, 'public')));
//各路由
app.use('/admin', admin);
app.use('/', index);
app.use('/list', list);
app.use('/watch', watch);
app.listen(3000, function(){
console.log('app is listening at port 3000');
});
//连接数据库
mongoose.connect('mongodb://localhost:27017/book',function(err){
if(err){
console.log('数据库连接错误了哦');
}else{
console.log('数据库连接成功了!你很棒棒哦!');
app.listen();
}
});
module.exports = app;
- 各路由
admin.js
var express = require('express');
//创建路有对象
var router = express.Router();
var Book =require('../models/book');
router.get('/', function(req, res){
res.render('admin/admin');
});
//统一返回格式
var responseData = null;
router.use(function(req,res,next){
responseData={
message:'',
bookInfo: ''
}
next();
});
//后台录入数据
router.post('/bookinfo', function(req, res){
/* var id = req.body.book._id;*/
var bookname = req.body.bookname;
var username = req.body.username;
var publishtime = req.body.publishtime;
var bookinfo = req.body.bookinfo;
var _book;
if(bookname == '' || username == '' || publishtime == '' || bookinfo == ''){
responseData.message = '需要输入全部的数据!';
res.json(responseData);
return;
}
//查看所录入的书本信息是否存在
Book.findOne({
bookname: bookname
}).then(function(bookInfo){
if(bookInfo){
responseData.message = '该书已经存在,可对他进行更新';
res.json(responseData);
_book = new Book({
bookname: bookname,
username: username,
publishtime: publishtime,
bookinfo: bookinfo,
});
return _book.save();
}else{
_book = new Book({
bookname: bookname,
username: username,
publishtime: publishtime,
bookinfo:bookinfo,
});
return _book.save();
}
}).then(function(newBookInfo){
responseData.message='数据录入成功!';
responseData.bookInfo = _book;
res.json(responseData);
//res.redirect('/list.html');
});
});
module.exports = router;
index.js
var express = require('express');
//创建路有对象
var router = express.Router();
var Book = require('../models/book');
router.get('/', function(req, res){
res.render('index');
});
//统一返回格式
var responseData = null;
router.use(function(req,res,next){
responseData={
message:'',
bookInfo: ''
}
next();
});
router.get('/index', function(req, res){
Book.find(function(err, books){
if(err){
console.log(err);
}else{
responseData.message = '所有数据查询成功';
responseData.bookInfo = books;
res.json(responseData);
return;
}
});
});
module.exports = router;
list.js
var express = require('express');
//创建路有对象
var router = express.Router();
var Book =require('../models/book');
//统一返回格式
var responseData = null;
router.use(function(req,res,next){
responseData={
message:'',
bookInfo: ''
}
next();
});
router.get('/', function(req, res){
res.render('admin/list');
});
//数据列表
router.get('/listnew', function(req, res){
Book.find(function(err, books){
if(err){
console.log(err);
}else{
responseData.message = '所有数据查询成功';
responseData.bookInfo = books;
/*responseData.bookInfo.id = books._id;*/
res.json(responseData);
return;
}
});
});
//更新数据
//直接去后台页面
//删除数据
router.delete('/delete', function(req, res){
var id = req.query.id;
if(id){
Book.remove({
_id: id
}, function(err,book){
if(err){
console.log(err);
}
responseData.message = '数据删除成功';
res.json(responseData);
return;
});
}
});
module.exports = router;
watch.js
var express = require('express');
//创建路有对象
var router = express.Router();
var Book =require('../models/book');
router.get('/', function(req, res){
res.render('admin/watch');
});
//统一返回格式
var responseData = null;
router.use(function(req,res,next){
responseData={
message:'',
bookInfo: ''
}
next();
});
//详情页/展示页
router.get('/look', function(req, res) {
var id = req.query.id;
Book.findOne({
_id: id
}).then(function(book){
if(!book){
responseData.message='该id在数据库中不存在!';
res.json(responseData);
return;
}else{
responseData.message='获取当前页面成功!';
responseData.bookInfo = book;
res.json(responseData);
return;
}
});
});
module.exports = router;
上面这些是后台路由的代码,前端的请求脚本代码我不打算放了,相信我这种水平能做的,大家都能实现的,
- 图书数据模式schemas
//book.js
//模式
//这里面放与书相关的信息
var mongoose = require('mongoose');
var Schema = mongoose.Schema;
var BookSchema = new Schema({
bookname: String,
username: String,
publishtime: Number,
bookinfo:String,
meta:{
createAt:{
type: Date,
default: Date.now()
},
updateAt: {
type: Date,
default: Date.now()
}
}
});
//为模式添加方法
//每次保存一个book数据之前都会调用这个方法
BookSchema.pre('save', function(next){
if(this.isNew) {
this.meta.createAt = this.meta.updateAt = Date.now();
}else{
this.meta.updateAt = Date.now();
}
next();
});
//静态方法,通过模型实例化之后才会有效
BookSchema.static = {
//取出目前数据库所有的数据
fetch: function(cb){
return this
.find({})
.sort('meta.updateAt')//通过时间顺序对数据进行排序
.exec(cb);//执行回调方法
},
findById: function(id, cb){
return this
.findOne({_id: id})
.exec(cb);
}
};
module.exports = BookSchema;
- 图书数据模型
//book.js
//模型
//用来初始化一个模式,成为一个有用的数据库对象
var mongoose = require('mongoose');
var BookSchema = require('../schema/book');
var Book = mongoose.model('Book', BookSchema);
module.exports = Book;
- 测试网站效果
- 开启数据库:我是使用最原始的方式,在本地下好的mogondb数据库文件下找到bin目录,打开mogond.exe文件,然后在romogondb工具下建立一个链接name,链接即可开启数据库;或是在bin目录下cmd运行下面命令
mongod --dbpath=(项目放数据库运行数据的文件目录,及这里的db文件夹目录) --port=27017 #这是链接数据库端口号,可以自己设定
- 开启express服务器:在项目目录下运行命令
node app.js
如果显示数据库已经链接好了,便可以在浏览器中查看效果了:
localhost:3000 #首页
localhost:3000/admin #后台管理页
localhost:3000/list #列表页
- 问题
- 查看详情页
我们通过a标签的href属性,查询字符串的形式传给后台相应的id,然后查看该ID的所以信息,在展示到页面上,请求代码如下:
$.ajax({
type: 'GET',
url: 'watch/look?id='+getSearchString('id'),
data: {
// id: getSearchString('id')
},
dataType:'json',
success: function(data){
var data = data.bookInfo;
//展示到页面。。。
},
error: function(){
console.log(err);
}
});
- 网站截图如下
首页
后台管理
列表页
romongodb工具使用
建站总结
学习node已经断断续续已经差不多三个月了,用心的学习效果还是很棒的,这个网站很简单,但是基本的一些功能有实现,所以会在继续添加新的功能,node学习中,我觉得最重要的是把前后端分离,逻辑分清,然后就是异步编程的使用。大概就是这些了,希望这次的练习能让自己得到一些成长,自己也会继续学习提升能力的。