后端开发基础
什么是后端开发?
后端开发是指服务器端的开发工作,负责处理业务逻辑、数据存储、用户认证等核心功能,为前端提供数据和服务支持。
后端开发核心概念
客户端-服务器架构
mermaid
graph LR
A[客户端/浏览器] -->|HTTP请求| B[服务器]
B -->|HTTP响应| A
B -->|查询/更新| C[数据库]
C -->|返回数据| BHTTP 协议
HTTP(HyperText Transfer Protocol)是前后端通信的基础协议。
常见HTTP方法
| 方法 | 作用 | 示例 |
|---|---|---|
| GET | 获取资源 | 获取用户列表 |
| POST | 创建资源 | 创建新用户 |
| PUT | 更新资源(完整) | 更新用户信息 |
| PATCH | 更新资源(部分) | 修改用户邮箱 |
| DELETE | 删除资源 | 删除用户 |
HTTP状态码
javascript
// 2xx 成功
200 OK // 请求成功
201 Created // 创建成功
204 No Content // 成功但无返回内容
// 3xx 重定向
301 Moved Permanently // 永久重定向
302 Found // 临时重定向
// 4xx 客户端错误
400 Bad Request // 请求参数错误
401 Unauthorized // 未授权
403 Forbidden // 禁止访问
404 Not Found // 资源不存在
// 5xx 服务器错误
500 Internal Server Error // 服务器内部错误
502 Bad Gateway // 网关错误
503 Service Unavailable // 服务不可用Node.js 后端开发
Express 框架
javascript
// app.js
const express = require('express');
const app = express();
// 中间件
app.use(express.json());
app.use(express.urlencoded({ extended: true }));
// 路由
app.get('/', (req, res) => {
res.json({ message: '欢迎使用API' });
});
// 获取用户列表
app.get('/api/users', (req, res) => {
const users = [
{ id: 1, name: '张三', email: 'zhangsan@example.com' },
{ id: 2, name: '李四', email: 'lisi@example.com' }
];
res.json(users);
});
// 获取单个用户
app.get('/api/users/:id', (req, res) => {
const userId = parseInt(req.params.id);
// 这里应该从数据库查询
const user = { id: userId, name: '张三', email: 'zhangsan@example.com' };
res.json(user);
});
// 创建用户
app.post('/api/users', (req, res) => {
const { name, email } = req.body;
if (!name || !email) {
return res.status(400).json({ error: '缺少必要参数' });
}
// 这里应该保存到数据库
const newUser = { id: 3, name, email };
res.status(201).json(newUser);
});
// 更新用户
app.put('/api/users/:id', (req, res) => {
const userId = parseInt(req.params.id);
const { name, email } = req.body;
// 这里应该更新数据库
const updatedUser = { id: userId, name, email };
res.json(updatedUser);
});
// 删除用户
app.delete('/api/users/:id', (req, res) => {
const userId = parseInt(req.params.id);
// 这里应该从数据库删除
res.status(204).send();
});
// 错误处理中间件
app.use((err, req, res, next) => {
console.error(err.stack);
res.status(500).json({ error: '服务器错误' });
});
// 启动服务器
const PORT = 3000;
app.listen(PORT, () => {
console.log(`服务器运行在 http://localhost:${PORT}`);
});RESTful API 设计
javascript
// routes/users.js
const express = require('express');
const router = express.Router();
// RESTful 路由设计
router.get('/users', getAllUsers); // GET /api/users
router.get('/users/:id', getUserById); // GET /api/users/1
router.post('/users', createUser); // POST /api/users
router.put('/users/:id', updateUser); // PUT /api/users/1
router.delete('/users/:id', deleteUser); // DELETE /api/users/1
// 处理函数
async function getAllUsers(req, res) {
try {
// 分页参数
const page = parseInt(req.query.page) || 1;
const limit = parseInt(req.query.limit) || 10;
const skip = (page - 1) * limit;
// 从数据库查询
const users = await User.find().skip(skip).limit(limit);
const total = await User.countDocuments();
res.json({
data: users,
pagination: {
page,
limit,
total,
pages: Math.ceil(total / limit)
}
});
} catch (error) {
res.status(500).json({ error: error.message });
}
}
module.exports = router;数据库操作
MongoDB(NoSQL)
javascript
// 连接数据库
const mongoose = require('mongoose');
mongoose.connect('mongodb://localhost:27017/myapp', {
useNewUrlParser: true,
useUnifiedTopology: true
});
// 定义模型
const userSchema = new mongoose.Schema({
name: { type: String, required: true },
email: { type: String, required: true, unique: true },
password: { type: String, required: true },
role: { type: String, enum: ['user', 'admin'], default: 'user' },
createdAt: { type: Date, default: Date.now }
});
const User = mongoose.model('User', userSchema);
// CRUD 操作
async function databaseOperations() {
// 创建
const newUser = await User.create({
name: '张三',
email: 'zhangsan@example.com',
password: 'hashed_password'
});
// 查询
const users = await User.find({ role: 'user' });
const oneUser = await User.findById(userId);
const emailUser = await User.findOne({ email: 'zhangsan@example.com' });
// 更新
await User.findByIdAndUpdate(userId, { name: '张三三' });
await User.updateOne({ email: 'zhangsan@example.com' }, { role: 'admin' });
// 删除
await User.findByIdAndDelete(userId);
await User.deleteMany({ role: 'user' });
}MySQL(关系型数据库)
javascript
// 使用 mysql2
const mysql = require('mysql2/promise');
// 创建连接池
const pool = mysql.createPool({
host: 'localhost',
user: 'root',
password: 'password',
database: 'myapp',
waitForConnections: true,
connectionLimit: 10
});
// 数据库操作
async function mysqlOperations() {
try {
// 查询
const [rows] = await pool.query('SELECT * FROM users WHERE role = ?', ['user']);
// 插入
const [result] = await pool.query(
'INSERT INTO users (name, email, password) VALUES (?, ?, ?)',
['张三', 'zhangsan@example.com', 'hashed_password']
);
// 更新
await pool.query('UPDATE users SET name = ? WHERE id = ?', ['张三三', 1]);
// 删除
await pool.query('DELETE FROM users WHERE id = ?', [1]);
// 事务
const connection = await pool.getConnection();
await connection.beginTransaction();
try {
await connection.query('INSERT INTO users ...');
await connection.query('INSERT INTO logs ...');
await connection.commit();
} catch (error) {
await connection.rollback();
throw error;
} finally {
connection.release();
}
} catch (error) {
console.error('数据库错误:', error);
}
}用户认证与授权
JWT(JSON Web Token)
javascript
const jwt = require('jsonwebtoken');
const bcrypt = require('bcrypt');
// 注册
app.post('/api/auth/register', async (req, res) => {
try {
const { name, email, password } = req.body;
// 检查用户是否存在
const existingUser = await User.findOne({ email });
if (existingUser) {
return res.status(400).json({ error: '用户已存在' });
}
// 加密密码
const hashedPassword = await bcrypt.hash(password, 10);
// 创建用户
const user = await User.create({
name,
email,
password: hashedPassword
});
res.status(201).json({ message: '注册成功', userId: user._id });
} catch (error) {
res.status(500).json({ error: error.message });
}
});
// 登录
app.post('/api/auth/login', async (req, res) => {
try {
const { email, password } = req.body;
// 查找用户
const user = await User.findOne({ email });
if (!user) {
return res.status(401).json({ error: '用户名或密码错误' });
}
// 验证密码
const isValidPassword = await bcrypt.compare(password, user.password);
if (!isValidPassword) {
return res.status(401).json({ error: '用户名或密码错误' });
}
// 生成 JWT
const token = jwt.sign(
{ userId: user._id, email: user.email, role: user.role },
'your-secret-key',
{ expiresIn: '24h' }
);
res.json({ token, user: { id: user._id, name: user.name, email: user.email } });
} catch (error) {
res.status(500).json({ error: error.message });
}
});
// 认证中间件
function authenticateToken(req, res, next) {
const authHeader = req.headers['authorization'];
const token = authHeader && authHeader.split(' ')[1];
if (!token) {
return res.status(401).json({ error: '未提供认证令牌' });
}
jwt.verify(token, 'your-secret-key', (err, user) => {
if (err) {
return res.status(403).json({ error: '令牌无效' });
}
req.user = user;
next();
});
}
// 需要认证的路由
app.get('/api/profile', authenticateToken, async (req, res) => {
try {
const user = await User.findById(req.user.userId).select('-password');
res.json(user);
} catch (error) {
res.status(500).json({ error: error.message });
}
});
// 角色权限检查
function requireAdmin(req, res, next) {
if (req.user.role !== 'admin') {
return res.status(403).json({ error: '需要管理员权限' });
}
next();
}
app.delete('/api/users/:id', authenticateToken, requireAdmin, async (req, res) => {
// 只有管理员可以删除用户
// ...
});Python 后端开发(Flask)
python
from flask import Flask, jsonify, request
from flask_sqlalchemy import SQLAlchemy
from werkzeug.security import generate_password_hash, check_password_hash
import jwt
from datetime import datetime, timedelta
app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///myapp.db'
app.config['SECRET_KEY'] = 'your-secret-key'
db = SQLAlchemy(app)
# 数据模型
class User(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(100), nullable=False)
email = db.Column(db.String(120), unique=True, nullable=False)
password = db.Column(db.String(200), nullable=False)
role = db.Column(db.String(20), default='user')
created_at = db.Column(db.DateTime, default=datetime.utcnow)
def to_dict(self):
return {
'id': self.id,
'name': self.name,
'email': self.email,
'role': self.role,
'created_at': self.created_at.isoformat()
}
# 路由
@app.route('/')
def index():
return jsonify({'message': '欢迎使用API'})
@app.route('/api/users', methods=['GET'])
def get_users():
users = User.query.all()
return jsonify([user.to_dict() for user in users])
@app.route('/api/users/<int:user_id>', methods=['GET'])
def get_user(user_id):
user = User.query.get_or_404(user_id)
return jsonify(user.to_dict())
@app.route('/api/users', methods=['POST'])
def create_user():
data = request.get_json()
if not data.get('name') or not data.get('email') or not data.get('password'):
return jsonify({'error': '缺少必要参数'}), 400
hashed_password = generate_password_hash(data['password'])
user = User(
name=data['name'],
email=data['email'],
password=hashed_password
)
db.session.add(user)
db.session.commit()
return jsonify(user.to_dict()), 201
@app.route('/api/auth/login', methods=['POST'])
def login():
data = request.get_json()
user = User.query.filter_by(email=data.get('email')).first()
if not user or not check_password_hash(user.password, data.get('password')):
return jsonify({'error': '用户名或密码错误'}), 401
token = jwt.encode({
'user_id': user.id,
'exp': datetime.utcnow() + timedelta(hours=24)
}, app.config['SECRET_KEY'], algorithm='HS256')
return jsonify({'token': token, 'user': user.to_dict()})
if __name__ == '__main__':
with app.app_context():
db.create_all()
app.run(debug=True, port=3000)API 文档与测试
Swagger/OpenAPI
javascript
const swaggerJsdoc = require('swagger-jsdoc');
const swaggerUi = require('swagger-ui-express');
const swaggerOptions = {
definition: {
openapi: '3.0.0',
info: {
title: 'API 文档',
version: '1.0.0',
description: '我的应用API文档'
},
servers: [
{
url: 'http://localhost:3000',
description: '开发环境'
}
]
},
apis: ['./routes/*.js']
};
const swaggerSpec = swaggerJsdoc(swaggerOptions);
app.use('/api-docs', swaggerUi.serve, swaggerUi.setup(swaggerSpec));
/**
* @swagger
* /api/users:
* get:
* summary: 获取用户列表
* tags: [Users]
* parameters:
* - in: query
* name: page
* schema:
* type: integer
* description: 页码
* responses:
* 200:
* description: 成功返回用户列表
*/最佳实践
1. 项目结构
backend/
├── src/
│ ├── controllers/ # 控制器
│ ├── models/ # 数据模型
│ ├── routes/ # 路由
│ ├── middlewares/ # 中间件
│ ├── services/ # 业务逻辑
│ ├── utils/ # 工具函数
│ └── config/ # 配置文件
├── tests/ # 测试文件
├── .env # 环境变量
├── .gitignore
└── package.json2. 环境变量
bash
# .env
NODE_ENV=development
PORT=3000
DATABASE_URL=mongodb://localhost:27017/myapp
JWT_SECRET=your-secret-key-herejavascript
// config.js
require('dotenv').config();
module.exports = {
env: process.env.NODE_ENV || 'development',
port: process.env.PORT || 3000,
databaseUrl: process.env.DATABASE_URL,
jwtSecret: process.env.JWT_SECRET
};3. 错误处理
javascript
// middlewares/errorHandler.js
class AppError extends Error {
constructor(message, statusCode) {
super(message);
this.statusCode = statusCode;
this.isOperational = true;
}
}
function errorHandler(err, req, res, next) {
err.statusCode = err.statusCode || 500;
err.status = err.status || 'error';
if (process.env.NODE_ENV === 'development') {
res.status(err.statusCode).json({
status: err.status,
error: err,
message: err.message,
stack: err.stack
});
} else {
// 生产环境
if (err.isOperational) {
res.status(err.statusCode).json({
status: err.status,
message: err.message
});
} else {
console.error('ERROR 💥', err);
res.status(500).json({
status: 'error',
message: '服务器错误'
});
}
}
}
module.exports = { AppError, errorHandler };4. 输入验证
javascript
const { body, validationResult } = require('express-validator');
app.post('/api/users',
// 验证规则
body('name').trim().notEmpty().withMessage('姓名不能为空'),
body('email').isEmail().withMessage('邮箱格式不正确'),
body('password').isLength({ min: 6 }).withMessage('密码至少6位'),
// 处理验证结果
(req, res) => {
const errors = validationResult(req);
if (!errors.isEmpty()) {
return res.status(400).json({ errors: errors.array() });
}
// 继续处理...
}
);学习资源
下一步
学习完后端基础后,可以继续学习:
- 前端开发基础
- 微服务架构
- Docker 容器化
- 云服务部署(AWS、阿里云、腾讯云)
- GraphQL
- WebSocket 实时通信