携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第26天,点击查看活动详情
搭建项目
新建 app.js
const Koa = require('koa')
const app = new Koa()
app.use(async (ctx, next) => {
ctx.body = 'hello Koa'
})
app.listen(3000)
地址栏输入 localhost:3000
app.js
const Koa = require('koa')
const Router = require('koa-router')
const app = new Koa()
const router = new Router()
app.use(async (ctx, next) => {
ctx.body = 'hello Koa'
await next()
})
router.get('/test', async (ctx) => {
ctx.body = 'hello koa-router'
})
app.use(router.routes()).use(router.allowedMethods())
app.listen(3000)
访问 localhost:3000/test 就可以看到 hello koa-router
项目不可能所有的接口都放在主文件里面,所以在 routes 新建两个文件夹 user, news,里面新建两个文件 user/admin.js , news/list.js
app.js
const Koa = require('koa')
const Router = require('koa-router')
// 引入两个文件
var admin = require('./routes/user/admin.js')
var newList = require('./routes/news/list.js')
const app = new Koa()
const router = new Router()
router.get('/', (ctx) => {
ctx.body = 'home page'
})
// 配置这两个,当你访问 /admin 这个路由是,会转发的 admin.js 文件下
router.use('/admin', admin.routes())
router.use('/news', newList.routes())
app.use(router.routes()).use(router.allowedMethods())
app.listen(3000)
routes/user/admin.js
const router = require('koa-router')()
router.get('/user', (ctx) => {
ctx.body = 'admin'
})
module.exports = router
localhost:300/admin/user
动态匹配路由
const router = require('koa-router')()
router.get('/user', (ctx) => {
ctx.body = 'admin'
})
router.get('/add/:id/:bid', async (ctx) => {
console.log(ctx.params)
// { id: '112', bid: 'qwe' }
ctx.body = '添加详情'
})
module.exports = router
localhost:3000/add/112/qwe
get 请求之后,就是 post 请求
const Koa = require('koa')
const Router = require('koa-router')
// 引入
var bodyParser = require('koa-bodyparser')
var admin = require('./routes/user/admin.js')
var newList = require('./routes/news/list.js')
const app = new Koa()
const router = new Router()
// 使用
app.use(bodyParser())
router.get('/', (ctx) => {
ctx.body = 'home page'
})
router.use('/admin', admin.routes())
router.use('/news', newList.routes())
app.use(router.routes()).use(router.allowedMethods())
app.listen(3000)
routes/news/list.js
const router = require('koa-router')()
router.get('/list', (ctx) => {
ctx.body = 'list'
})
router.post('/postRoute', async (ctx, next) => {
const rb = ctx.request.body
console.log(rb);
ctx.response.body = 'success'
})
module.exports = router
post 在浏览器的地址栏里面直接输入是不可以的,可以使用 postman 来进行测试。
{ user: 'mjhgf', age: '111', sex: '0' }
操作数据库
npm install mongodb --save
根目录下新建一个utils文件夹, 里面放上 config.js, db.js。
config.js
const app = {
dbUrl: 'mongodb://localhost:27017',
dbName: 'koa'
}
module.exports = app
db.js(对MongoDB的封装)
const MongoClient = require('mongodb').MongoClient
const ObjectID = require('mongodb').ObjectID
const Config = require('./config.js')
class Db {
// 单例模式
static getInstance() {
if (!Db.instance) {
Db.instance = new Db()
}
return Db.instance
}
constructor() {
this.dbClient = ''
this.connect()
}
connect() {
return new Promise((resolve, reject) => {
if (!this.dbClient) {
MongoClient.connect(Config.dbUrl, { useUnifiedTopology: true }, (err, client) => {
if (err) {
reject(err)
} else {
const db = client.db(Config.dbName)
this.dbClient = db
resolve(this.dbClient)
}
})
} else {
resolve(this.dbClient)
}
})
}
find(collectionName, json) {
return new Promise((resolve, reject) => {
this.connect().then(function (db) {
const result = db.collection(collectionName).find(json)
result.toArray(function (err, docs) {
if (err) {
reject(err)
return
} else {
resolve(docs)
}
})
})
})
}
update(collectionName, json1, json2) {
return new Promise((resolve, reject) => {
this.connect().then((db) => {
db.collection(collectionName).updateOne(json1, {
$set: json2
}, (err, result) => {
if (err) {
reject(err)
return
} else {
resolve(result)
}
})
})
})
}
insert(collectionName, json) {
return new Promise((resolve, reject) => {
this.connect().then((db) => {
db.collection(collectionName).insertOne(json, function (err, result) {
if (err) {
reject(err)
return
} else {
resolve(result)
}
})
})
})
}
remove(collectionName, json) {
return new Promise((resolve, reject) => {
this.connect().then((db) => {
db.collection(collectionName).removeOne(json, function (err, result) {
if (err) {
reject(err)
return
} else {
resolve(result)
}
})
})
})
}
// 查询 _id
getObjectID(id) {
return new ObjectID(id)
}
}
module.exports = Db.getInstance()
routes/user/admin.js
(连接自己的数据库,在数据库中新建一个 koa 数据库,新建一个user表)
const router = require('koa-router')()
const DB = require('../../utils/db.js')
router.get('/user', async (ctx) => {
var result = await DB.find('user', {})
ctx.body = result
})
module.exports = router
这样就可以使用 koa 操作数据库了。
数据库增删改查
routes/user/admin.js
const router = require('koa-router')()
const DB = require('../../utils/db.js')
router.get('/add/:id/:bid', async (ctx) => {
// http://localhost:3000/add/112/qwe
console.log(ctx.params)
// { id: '112', bid: 'qwe' }
ctx.body = '添加详情'
})
// 查询
router.get('/list', async (ctx) => {
var result = await DB.find('user', {})
ctx.body = result
})
// 插入
router.post('/doAdd', async (ctx) => {
let data = await DB.insert('user', ctx.request.body)
ctx.body = data
try {
if (data.result.ok) {
console.log(ctx.body)
}
} catch (error) {
console.log(err)
ctx.redirect('/')
}
})
// 删除
router.get('/remove', async (ctx) => {
// let user = ctx.query.user
let user = ctx.request.body.user
console.log(user)
var data = await DB.remove('user', {'user': user})
try {
if (data.result.ok) {
// ctx.redirect('/')
ctx.body = data
}
} catch (error) {
console.log(err)
}
})
// 更新
router.get('/update', async (ctx) => {
var id = ctx.query.id
var user = ctx.query.user
var age = ctx.query.age
var sex = ctx.query.sex
console.log(DB.getObjectID(id), user, age, sex)
let data = await DB.update('user', {'_id': DB.getObjectID(id)}, {
age,
sex
})
try {
if (data.result.ok) {
ctx.body = data
}
} catch (error) {
console.log(err)
ctx.redirect('/add')
}
})
module.exports = router
登录和注册功能
新建 login.js
const router = require('koa-router')()
const DB = require('../../utils/db.js')
router.post('/register', async (ctx) => {
let data = await DB.insert('author', ctx.request.body)
console.log(data)
ctx.body = data
try {
if (data.result.ok) {
ctx.redirect('/login/getInfo')
}
} catch (error) {
console.log(error)
// ctx.redirect('/')
}
})
router.post('/login', async (ctx) => {
let name = ctx.request.body.name
let email = ctx.request.body.email
let pwd = ctx.request.body.pwd
console.log(name, email, pwd)
var result = await DB.find('author',
{'name': name, 'email': email, 'pwd': pwd})
console.log(result)
try {
if (result.length > 0) {
ctx.body = '登录成功'
ctx.redirect('/')
}
} catch (error) {
console.log(error)
// ctx.redirect('/')
}
})
router.get('/getInfo', async (ctx) => {
var result = await DB.find('author', {})
ctx.body = result
})
module.exports = router
利用 JWT 设置 Token
const Koa = require('koa')
const Router = require('koa-router')
const bodyParser = require('koa-bodyparser')
const jwt = require('jsonwebtoken')
const jwtKoa = require('koa-jwt')
var admin = require('./routes/user/admin.js')
var newList = require('./routes/news/list.js')
var login = require('./routes/user/login.js')
const DB = require('./utils/db.js')
const keys = require('./utils/config')
const app = new Koa()
const router = new Router()
const secret = 'secret'
app.use(jwtKoa({secret}).unless({
path: [/\/register/, /\/login/]
}))
app.use(bodyParser())
app.use(async (ctx, next) => {
console.log(ctx)
let params = Object.assign({}, ctx.request.query, ctx.request.body);
ctx.request.header = {'authorization': "Bearer " + (params.token || '')}
await next();
})
router.get('/', async (ctx) => {
ctx.body = 'home'
})
router.post('/register', async (ctx) => {
console.log(ctx.request.body.email)
let email = ctx.request.body.email
const findResult = await DB.find('author', {
'email': email
})
console.log(findResult)
if (findResult.length > 0) {
ctx.status = 506
ctx.body = { email: '邮箱已被占用 ' }
} else {
let data = await DB.insert('author', ctx.request.body)
console.log(data)
ctx.body = data
try {
if (data.result.ok) {
ctx.body = {
mssage: '注册成功'
}
}
} catch (error) {
console.log(error)
// ctx.redirect('/')
}
}
})
router.post('/login', async (ctx, next) => {
let name = ctx.request.body.name
let email = ctx.request.body.email
let pwd = ctx.request.body.pwd
console.log(name, email, pwd)
var result = await DB.find('author',
{'name': name, 'email': email})
console.log(result)
if (result.length === 0) {
ctx.status = 404
ctx.body = { email: '用户不存在!' }
} else {
var result = await DB.find('author',{'pwd': pwd})
if (result) {
// 返回token
const payload = { pwd: pwd, name: name}
const token = jwt.sign(payload, keys.secretOrkey, { expiresIn: 3600 })
ctx.status = 200
ctx.body = { success: true, token: 'Bearer ' + token }
} else {
ctx.status = 400
ctx.body = { password: '密码错误!' }
}
}
})
router.use('/admin', admin.routes())
router.use('/news', newList.routes())
router.use('/login', login.routes())
app.use(router.routes()).use(router.allowedMethods())
app.listen(3000)
之后,项目需要什么接口,就向 routes 中添加对应的接口。