log
码中赤兔

使用位运算实现权限管理

发布于 2024年12月9日
更新于 2025年1月17日
5 分钟阅读
TypeScriptJavaScript

在开发管理类应用时,权限管理是一个不可避免的问题。


通常的做法

一般来说,我们会将用户行为分为【增】、【删】、【改】、【查】四种类型,并定义相应的常量来表示这些行为。例如:

const READ = 1;
const WRITE = 2;
const UPDATE = 3;
const DELETE = 4;

如果某个用户拥有【查】、【写】、【改】三种权限,我们可能会这样表示:

const permission = [READ, WRITE, UPDATE];

这种方式虽然直观,但并非最佳选择,因为它存在两个问题:

  1. 资源开销增加:在数据库存储或网络传输时,数组形式的数据会占用更多资源。
  2. 判断逻辑冗长:例如判断用户是否有【写】权限时,需使用 permission.includes(WRITE)。虽然这种写法没有问题,但如果代码中频繁出现类似逻辑,会显得繁琐。

推荐的做法

为了解决上述问题,我们可以使用二进制表示法结合位运算,既节省资源,又简化逻辑。


二进制表示权限

我们仍然用常量来表示【增】、【删】、【改】、【查】四种行为,但使用二进制数表示权限:

const READ = 0b1;      // 二进制:0001,对应十进制:1
const WRITE = 0b10;    // 二进制:0010,对应十进制:2
const UPDATE = 0b100;  // 二进制:0100,对应十进制:4
const DELETE = 0b1000; // 二进制:1000,对应十进制:8

在这种表示方式下:

  • 二进制的第1位为 1 表示拥有【查】权限。
  • 第2位为 1 表示拥有【写】权限,以此类推。

常见操作

1. 生成权限

假设需要为用户赋予【查】、【写】、【改】权限,可以通过位运算 | (按位或)生成权限:

const permission = READ | WRITE | UPDATE; // 二进制:0111,十进制:7
console.log(permission); // 输出:7

2. 判断权限

检查用户是否拥有某种权限时,可以使用 &(按位与)运算:

if (permission & WRITE) {
    console.log("用户拥有写权限");
} else {
    console.log("用户没有写权限");
}

3. 添加或移除权限

使用 ^(按位异或)运算可以灵活地为用户添加或移除某个权限:

// 如果权限中没有 DELETE,会添加 DELETE;如果已有 DELETE,会移除 DELETE
const newPermission = permission ^ DELETE;
console.log(newPermission);

优势分析

通过这种方式:

  • 在数据库存储或网络传输时,只需处理一个数字,大幅降低资源开销。
  • 权限判断、添加和移除逻辑更简洁,不再依赖数组操作。

例如:

  • 一个权限值为 7 的用户,其二进制表示为 0111,即拥有【查】、【写】、【改】三种权限。
  • 检查是否拥有【写】权限仅需一行代码:permission & WRITE

总结

二进制表示法结合位运算,是一种高效管理权限的方式。它不仅能优化资源利用,还能使代码逻辑更清晰简洁,非常适合在管理类应用中使用。

关于

分享技术见解、经验和思考的个人博客

联系方式

  • Email: hushukang_blog@proton.me
  • GitHub

© 2025 码中赤兔. 版权所有