使用Mongoose构建服务
该方式需要在本地安装MongoDB才可以
使用 TypeScript、Express、Mongoose 和 pnpm 可以快速构建后端服务,并实现增删改查以及列表查询的功能。下面是一个简单的示例:
首先,确保已经安装了 Node.js 和 pnpm。
创建项目文件夹,并进入该文件夹:
mkdir backend
cd backend
初始化 npm 项目,并选择 TypeScript 作为开发语言:
pnpm init
安装依赖:
pnpm install express mongoose
pnpm install --save-dev typescript ts-node nodemon @types/express @types/mongoose
创建 TypeScript 配置文件 tsconfig.json
:
{
"compilerOptions": {
"target": "es6",
"module": "commonjs",
"outDir": "dist",
"strict": true,
"esModuleInterop": true
},
"include": ["src"]
}
创建 src
文件夹,并在其中创建以下文件:
app.ts
:Express 应用程序的入口文件。models.ts
:Mongoose 模型定义文件。routes.ts
:Express 路由定义文件。
在 models.ts
文件中定义 Mongoose 模型。例如,我们创建一个 User
模型:
import mongoose from 'mongoose';
const userSchema = new mongoose.Schema({
name: {
type: String,
required: true
},
age: {
type: Number,
required: true
}
});
export default mongoose.model('User', userSchema);
在 routes.ts
文件中定义 Express 路由。例如,我们创建一个处理用户相关操作的路由:
import express, { Request, Response, NextFunction } from 'express';
import User from './models';
const router = express.Router();
// 获取用户列表
router.get('/users', async (req, res) => {
try {
const users = await User.find();
res.json(users);
} catch (error:any) {
res.status(500).json({ message: error.message });
}
});
// 创建用户
router.post('/users', async (req, res) => {
const { name, age } = req.body;
const user = new User({ name, age });
try {
const newUser = await user.save();
res.status(201).json(newUser);
} catch (error:any) {
res.status(400).json({ message: error.message });
}
});
// 获取单个用户
router.get('/users/:id', getUser, (req, res:any) => {
res.json(res.user);
});
// 更新用户
router.patch('/users/:id', getUser, async (req, res:any) => {
const { name, age } = req.body;
if (name) {
res.user.name = name;
}
if (age) {
res.user.age = age;
}
try {
const updatedUser = await res.user.save();
res.json(updatedUser);
} catch (error:any) {
res.status(400).json({ message: error.message });
}
});
// 删除用户
router.delete('/users/:id', getUser, async (req, res:any) => {
try {
await res.user.remove();
res.json({ message: 'User deleted' });
} catch (error:any) {
res.status(500).json({ message: error.message });
}
});
async function getUser(req: Request, res: any, next: NextFunction) {
let user;
try {
user = await User.findById(req.params.id);
if (user == null) {
return res.status(404).json({ message: 'User not found' });
}
} catch (error:any) {
return res.status(500).json({ message: error.message });
}
res.user = user;
next();
}
export default router;
在 app.ts
文件中创建 Express 应用程序,并配置中间件和路由:
import express from 'express';
import mongoose from 'mongoose';
import routes from './routes';
const app = express();
const port = 3000;
app.use(express.json());
app.use(routes);
mongoose.connect('mongodb://localhost:27017/mydatabase', {
useNewUrlParser: true,
useUnifiedTopology: true
}).then(() => {
console.log('Connected to MongoDB');
}).catch((error) => {
console.error('Error connecting to MongoDB:', error.message);
});
app.listen(port, () => {
console.log(`Server running on port ${port}`);
});
在 package.json
文件中添加脚本命令:
{
"scripts": {
"start": "nodemon --exec ts-node src/app.ts"
}
}
启动应用程序:
pnpm start
现在,你的后端服务已经启动,可以使用 Postman 或其他工具测试 API。以下是一些示例请求:
接口测试
- 获取用户列表:GET http://localhost:3000/users
- 创建用户:POST http://localhost:3000/users,请求体为 JSON 格式的用户数据。
- 获取单个用户:GET http://localhost:3000/users/{id}
- 更新用户:PATCH http://localhost:3000/users/{id},请求体为 JSON 格式的更新数据。
- 删除用户:DELETE http://localhost:3000/users/{id}
请注意,这只是一个简单的示例,实际项目中可能需要更多的验证、错误处理和安全性措施。
使用内存数据库SQLite数据库
该方式无需安装数据库SQLite,使用的是内存数据库
以下步骤和之前的一样,不再做过多解释
mkdir backend
cd backend
pnpm init
pnpm install express
pnpm install --save-dev typescript ts-node nodemon @types/express
安装SQLLite数据库
npm install sqlite3 sequelize pnpm install @types/body-parser
models.ts
import { Sequelize, DataTypes, Model } from 'sequelize';
export interface TodoListAttributes {
id?: number;
title: string;
desc: string;
}
export class TodoList extends Model<TodoListAttributes> implements TodoListAttributes {
public id!: number;
public title!: string;
public desc!: string;
public readonly createdAt!: Date;
public readonly updatedAt!: Date;
}
export const sequelize = new Sequelize({
dialect: 'sqlite',
storage: ':memory:'
});
TodoList.init(
{
title: {
type: DataTypes.STRING,
allowNull: false
},
desc: {
type: DataTypes.STRING,
allowNull: false
}
},
{
sequelize,
modelName: 'TodoList'
}
);
controllers.ts
import { Request, Response } from 'express';
import { TodoList } from '../model/models';
export const createTodoList = async (req: Request, res: Response) => {
try {
const { title, desc } = req.body;
const todoList = await TodoList.create({ title, desc });
res.status(201).json(todoList.toJSON());
} catch (error) {
console.error('Error creating todoList:', error);
res.status(500).json({ error: 'Internal server error' });
}
};
export const getTodoList = async (req: Request, res: Response) => {
try {
const todoLists = await TodoList.findAll();
res.json(todoLists.map(todoList => todoList.toJSON()));
} catch (error) {
console.error('Error getting todoLists:', error);
res.status(500).json({ error: 'Internal server error' });
}
};
export const getTodoListById = async (req: Request, res: Response) => {
try {
const { id } = req.params;
const todoList = await TodoList.findByPk(id);
if (todoList) {
res.json(todoList.toJSON());
} else {
res.status(404).json({ error: 'TodoList not found' });
}
} catch (error) {
console.error('Error getting todoList by ID:', error);
res.status(500).json({ error: 'Internal server error' });
}
};
export const updateTodoList = async (req: Request, res: Response) => {
try {
const { id } = req.params;
const { title, desc } = req.body;
const todoList = await TodoList.findByPk(id);
if (todoList) {
await todoList.update({ title, desc });
res.json(todoList.toJSON());
} else {
res.status(404).json({ error: 'TodoList not found' });
}
} catch (error) {
console.error('Error updating todoList:', error);
res.status(500).json({ error: 'Internal server error' });
}
};
export const deleteTodoList = async (req: Request, res: Response) => {
try {
const { id } = req.params;
const todoList = await TodoList.findByPk(id);
if (todoList) {
await todoList.destroy();
res.json({ message: 'TodoList deleted successfully' });
} else {
res.status(404).json({ error: 'TodoList not found' });
}
} catch (error) {
console.error('Error deleting todoList:', error);
res.status(500).json({ error: 'Internal server error' });
}
};
routes.ts
import express from 'express';
import { createTodoList, getTodoList, getTodoListById, updateTodoList, deleteTodoList } from '../utils/controllers';
const router = express.Router();
router.post('/todo-list', createTodoList);
router.get('/todo-list', getTodoList);
router.get('/todo-list/:id', getTodoListById);
router.put('/todo-list/:id', updateTodoList);
router.delete('/todo-list/:id', deleteTodoList);
export default router;
app.ts
import express from 'express';
import bodyParser from 'body-parser';
import { sequelize } from './model/models';
import router from './router/router';
const app = express();
app.use(bodyParser.json());
app.use(router);
const startServer = async () => {
try {
await sequelize.sync();
app.listen(3000, () => {
console.log('Server is running on port 3000');
});
} catch (error) {
console.error('Error starting server:', error);
}
};
startServer();
启动
pnpm start
接口测试
- 获取列表:GET localhost:3000/todo-list
- 创建:POST localhost:3000/todo-list,请求体为 JSON 格式的数据。
- 获取单个数据:GET localhost:3000/todo-list/1
- 更新数据:PUT localhost:3000/todo-list/2,请求体为 JSON 格式的更新数据。
- 删除数据:DELETE localhost:3000/todo-list/2
源码
todo-express.zip
好了,本章节到此告一段落。希望对你有所帮助,祝学习顺利。