配套后端(Node.js + Express + SQLite)

配套后端(Node.js + Express + SQLite) ,实现完整的:

  • 👤 用户表(users)
  • 🧩 角色表(roles)
  • 🔐 权限点表(permissions)
  • 🔗 角色权限关联表(role_permissions)
  • 🔗 用户角色关联表(user_roles)

并提供标准 REST 接口供前端(Naive Admin)调用。


📁 项目结构

markdown 复制代码
backend/
  server.js
  db.js
  routes/
    users.js
    roles.js
    permissions.js
  schema.sql

📁 db.js --- SQLite 初始化

sql 复制代码
import sqlite3 from "sqlite3";
import { open } from "sqlite";

export async function initDB() {
  const db = await open({
    filename: "./data.db",
    driver: sqlite3.Database
  });

  await db.exec(`
    CREATE TABLE IF NOT EXISTS users (
      id INTEGER PRIMARY KEY AUTOINCREMENT,
      nickname TEXT,
      phone TEXT
    );

    CREATE TABLE IF NOT EXISTS roles (
      id INTEGER PRIMARY KEY AUTOINCREMENT,
      name TEXT,
      description TEXT
    );

    CREATE TABLE IF NOT EXISTS permissions (
      id INTEGER PRIMARY KEY AUTOINCREMENT,
      key TEXT,
      label TEXT
    );

    CREATE TABLE IF NOT EXISTS user_roles (
      user_id INTEGER,
      role_id INTEGER,
      PRIMARY KEY (user_id, role_id)
    );

    CREATE TABLE IF NOT EXISTS role_permissions (
      role_id INTEGER,
      permission_id INTEGER,
      PRIMARY KEY (role_id, permission_id)
    );
  `);

  return db;
}

📁 routes/users.js

vbnet 复制代码
import express from "express";
export default function (db) {
  const router = express.Router();

  // 查询所有用户及其角色
  router.get("/", async (req, res) => {
    const users = await db.all(`
      SELECT u.id, u.nickname, u.phone,
             group_concat(r.name) as roleNames,
             group_concat(r.id) as roleIds
      FROM users u
      LEFT JOIN user_roles ur ON u.id = ur.user_id
      LEFT JOIN roles r ON ur.role_id = r.id
      GROUP BY u.id
    `);
    res.json(users);
  });

  router.post("/", async (req, res) => {
    const { nickname, phone, roleIds = [] } = req.body;
    const result = await db.run("INSERT INTO users (nickname, phone) VALUES (?,?)", [nickname, phone]);
    const userId = result.lastID;
    for (const r of roleIds) {
      await db.run("INSERT INTO user_roles (user_id, role_id) VALUES (?,?)", [userId, r]);
    }
    res.sendStatus(201);
  });

  router.put("/:id", async (req, res) => {
    const { nickname, phone, roleIds = [] } = req.body;
    await db.run("UPDATE users SET nickname=?, phone=? WHERE id=?", [nickname, phone, req.params.id]);
    await db.run("DELETE FROM user_roles WHERE user_id=?", [req.params.id]);
    for (const r of roleIds) {
      await db.run("INSERT INTO user_roles (user_id, role_id) VALUES (?,?)", [req.params.id, r]);
    }
    res.sendStatus(200);
  });

  router.delete("/:id", async (req, res) => {
    await db.run("DELETE FROM users WHERE id=?", [req.params.id]);
    await db.run("DELETE FROM user_roles WHERE user_id=?", [req.params.id]);
    res.sendStatus(200);
  });

  return router;
}

📁 routes/roles.js

csharp 复制代码
import express from "express";

export default function (db) {
  const router = express.Router();

  router.get("/", async (req, res) => {
    const roles = await db.all("SELECT * FROM roles");
    res.json(roles);
  });

  router.post("/", async (req, res) => {
    const { name, description } = req.body;
    await db.run("INSERT INTO roles (name, description) VALUES (?,?)", [name, description]);
    res.sendStatus(201);
  });

  router.put("/:id", async (req, res) => {
    const { name, description } = req.body;
    await db.run("UPDATE roles SET name=?, description=? WHERE id=?", [name, description, req.params.id]);
    res.sendStatus(200);
  });

  router.delete("/:id", async (req, res) => {
    await db.run("DELETE FROM roles WHERE id=?", [req.params.id]);
    await db.run("DELETE FROM role_permissions WHERE role_id=?", [req.params.id]);
    res.sendStatus(200);
  });

  // 更新角色的权限
  router.post("/:id/permissions", async (req, res) => {
    const { permIds = [] } = req.body;
    await db.run("DELETE FROM role_permissions WHERE role_id=?", [req.params.id]);
    for (const p of permIds) {
      await db.run("INSERT INTO role_permissions (role_id, permission_id) VALUES (?,?)", [req.params.id, p]);
    }
    res.sendStatus(200);
  });

  return router;
}

📁 routes/permissions.js

dart 复制代码
import express from "express";

export default function (db) {
  const router = express.Router();

  router.get("/", async (req, res) => {
    const perms = await db.all("SELECT id as key, label FROM permissions");
    res.json(perms);
  });

  router.post("/", async (req, res) => {
    const { key, label } = req.body;
    await db.run("INSERT INTO permissions (key, label) VALUES (?,?)", [key, label]);
    res.sendStatus(201);
  });

  router.delete("/:id", async (req, res) => {
    await db.run("DELETE FROM permissions WHERE id=?", [req.params.id]);
    await db.run("DELETE FROM role_permissions WHERE permission_id=?", [req.params.id]);
    res.sendStatus(200);
  });

  return router;
}

📁 server.js

javascript 复制代码
import express from "express";
import cors from "cors";
import { initDB } from "./db.js";
import usersRouter from "./routes/users.js";
import rolesRouter from "./routes/roles.js";
import permsRouter from "./routes/permissions.js";

const app = express();
app.use(cors());
app.use(express.json());

const db = await initDB();

app.use("/api/users", usersRouter(db));
app.use("/api/roles", rolesRouter(db));
app.use("/api/permissions", permsRouter(db));

app.listen(3001, () => {
  console.log("✅ 后端服务已启动:http://localhost:3001");
});

📌 功能总结

  • 用户表:users(id、nickname、phone)

  • 角色表:roles(id、name、description)

  • 权限点表:permissions(id、key、label)

  • 关联:

    • user_roles(多对多)
    • role_permissions(多对多)
  • 支持接口:

    • GET/POST/PUT/DELETE 用户
    • GET/POST/PUT/DELETE 角色 + 分配权限
    • GET/POST/DELETE 权限点

与前端 Naive Admin 模板完全匹配。


✅ 使用方式

vbscript 复制代码
npm install express sqlite3 sqlite cors
node server.js
  • 前端调用 http://localhost:3001/api/... 接口
  • 即可实现 用户列表 + 角色分配 + 权限点管理

相关推荐
古城小栈5 小时前
Tokio:Rust 异步界的 “霸主”
开发语言·后端·rust
进击的丸子5 小时前
基于虹软Linux Pro SDK的多路RTSP流并发接入、解码与帧级处理实践
java·后端·github
techdashen5 小时前
Go 1.18+ slice 扩容机制详解
开发语言·后端·golang
浙江巨川-吉鹏5 小时前
【城市地表水位连续监测自动化系统】沃思智能
java·后端·struts·城市地表水位连续监测自动化系统·地表水位监测系统
fliter5 小时前
Go 1.18+ slice 扩容机制详解
后端
A黑桃5 小时前
Paimon Action Jar 实现机制分析
大数据·后端
代码笔耕5 小时前
写了几年 Java,我发现很多人其实一直在用“高级 C 语言”写代码
java·后端·架构
@我们的天空5 小时前
【FastAPI 完整版】路由与请求参数详解(query、path、params、body、form 完整梳理)- 基于 FastAPI 完整版
后端·python·pycharm·fastapi·后端开发·路由与请求
武子康5 小时前
大数据-211 逻辑回归的 Scikit-Learn 实现:max_iter、分类方式与多元回归的优化方法
大数据·后端·机器学习
一路向北North6 小时前
springboot基础(85): validator验证器
java·spring boot·后端