Explorar el Código

feat: 更新许可证管理功能,使用AES-256-CBC加密和解密,增加生成许可证密钥的API

chengchongzhen hace 1 año
padre
commit
7525b07d5b
Se han modificado 2 ficheros con 97 adiciones y 6 borrados
  1. 38 6
      license_manager.py
  2. 59 0
      server/server.js

+ 38 - 6
license_manager.py

@@ -5,7 +5,8 @@ import platform
 import uuid
 import uuid
 import hashlib
 import hashlib
 from datetime import datetime
 from datetime import datetime
-from cryptography.fernet import Fernet
+from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
+from cryptography.hazmat.backends import default_backend
 import base64
 import base64
 
 
 
 
@@ -21,7 +22,38 @@ class LicenseManager:
             "https://your-activation-server.com/verify"  # 替换为您的验证服务器地址
             "https://your-activation-server.com/verify"  # 替换为您的验证服务器地址
         )
         )
         self.key = b"Kj8nP9x2Qs5mY7vR4wL1hC3fA6tD0iB8"
         self.key = b"Kj8nP9x2Qs5mY7vR4wL1hC3fA6tD0iB8"
-        self.fernet = Fernet(base64.b64encode(self.key))
+
+    def encrypt(self, text):
+        """使用AES-256-CBC加密"""
+        cipher = Cipher(
+            algorithms.AES(self.key),
+            modes.CBC(self.key[:16]),
+            backend=default_backend(),
+        )
+        encryptor = cipher.encryptor()
+
+        # 添加PKCS7填充
+        length = 16 - (len(text) % 16)
+        text += bytes([length]) * length
+
+        encrypted = encryptor.update(text) + encryptor.finalize()
+        return base64.b64encode(encrypted).decode("utf-8")
+
+    def decrypt(self, encrypted_text):
+        """使用AES-256-CBC解密"""
+        encrypted = base64.b64decode(encrypted_text)
+        cipher = Cipher(
+            algorithms.AES(self.key),
+            modes.CBC(self.key[:16]),
+            backend=default_backend(),
+        )
+        decryptor = cipher.decryptor()
+
+        decrypted = decryptor.update(encrypted) + decryptor.finalize()
+
+        # 移除PKCS7填充
+        padding_length = decrypted[-1]
+        return decrypted[:-padding_length]
 
 
     def get_hardware_info(self):
     def get_hardware_info(self):
         """获取硬件信息作为机器码"""
         """获取硬件信息作为机器码"""
@@ -127,8 +159,8 @@ class LicenseManager:
         """加密保存许可证数据"""
         """加密保存许可证数据"""
         try:
         try:
             os.makedirs(os.path.dirname(self.license_file), exist_ok=True)
             os.makedirs(os.path.dirname(self.license_file), exist_ok=True)
-            encrypted_data = self.fernet.encrypt(json.dumps(license_data).encode())
-            with open(self.license_file, "wb") as f:
+            encrypted_data = self.encrypt(json.dumps(license_data).encode())
+            with open(self.license_file, "w") as f:
                 f.write(encrypted_data)
                 f.write(encrypted_data)
         except Exception as e:
         except Exception as e:
             print(f"保存许可证出错: {e}")
             print(f"保存许可证出错: {e}")
@@ -136,9 +168,9 @@ class LicenseManager:
     def _load_license(self):
     def _load_license(self):
         """加密读取许可证数据"""
         """加密读取许可证数据"""
         try:
         try:
-            with open(self.license_file, "rb") as f:
+            with open(self.license_file, "r") as f:
                 encrypted_data = f.read()
                 encrypted_data = f.read()
-            decrypted_data = self.fernet.decrypt(encrypted_data)
+            decrypted_data = self.decrypt(encrypted_data)
             return json.loads(decrypted_data)
             return json.loads(decrypted_data)
         except Exception as e:
         except Exception as e:
             print(f"读取许可证出错: {e}")
             print(f"读取许可证出错: {e}")

+ 59 - 0
server/server.js

@@ -12,11 +12,50 @@ const app = express();
 app.use(cors());
 app.use(cors());
 app.use(express.json());
 app.use(express.json());
 
 
+// Encryption functions
+function encryptLicenseKey(text) {
+    const cipher = crypto.createCipher('aes-256-cbc', process.env.ENCRYPTION_KEY);
+    let encrypted = cipher.update(text, 'utf8', 'hex');
+    encrypted += cipher.final('hex');
+    return encrypted;
+}
+
+function decryptLicenseKey(encrypted) {
+    const decipher = crypto.createDecipher('aes-256-cbc', process.env.ENCRYPTION_KEY);
+    let decrypted = decipher.update(encrypted, 'hex', 'utf8');
+    decrypted += decipher.final('utf8');
+    return decrypted;
+}
+
+function generateLicenseKey() {
+    const randomBytes = crypto.randomBytes(16);
+    const timestamp = Date.now().toString();
+    const combined = randomBytes.toString('hex') + timestamp;
+    return encryptLicenseKey(combined).substring(0, 32); // 生成32位的许可证密钥
+}
+
 // Connect to MongoDB
 // Connect to MongoDB
 mongoose.connect(process.env.MONGODB_URI)
 mongoose.connect(process.env.MONGODB_URI)
     .then(() => console.log('Connected to MongoDB'))
     .then(() => console.log('Connected to MongoDB'))
     .catch(err => console.error('MongoDB connection error:', err));
     .catch(err => console.error('MongoDB connection error:', err));
 
 
+// Generate license key endpoint
+app.post('/generate', async (req, res) => {
+    try {
+        const licenseKey = generateLicenseKey();
+        return res.json({
+            success: true,
+            license_key: licenseKey
+        });
+    } catch (error) {
+        console.error('生成许可证错误:', error);
+        return res.status(500).json({
+            success: false,
+            message: '服务器错误'
+        });
+    }
+});
+
 // Activation endpoint
 // Activation endpoint
 app.post('/activate', async (req, res) => {
 app.post('/activate', async (req, res) => {
     try {
     try {
@@ -30,6 +69,16 @@ app.post('/activate', async (req, res) => {
             });
             });
         }
         }
 
 
+        // Validate license key format
+        try {
+            decryptLicenseKey(license_key);
+        } catch (error) {
+            return res.status(400).json({
+                success: false,
+                message: '无效的许可证密钥'
+            });
+        }
+
         // Check if license already exists
         // Check if license already exists
         const existingLicense = await License.findOne({ licenseKey: license_key });
         const existingLicense = await License.findOne({ licenseKey: license_key });
         if (existingLicense) {
         if (existingLicense) {
@@ -90,6 +139,16 @@ app.post('/verify', async (req, res) => {
             });
             });
         }
         }
 
 
+        // Validate license key format
+        try {
+            decryptLicenseKey(license_key);
+        } catch (error) {
+            return res.status(400).json({
+                success: false,
+                message: '无效的许可证密钥'
+            });
+        }
+
         // Find license
         // Find license
         const license = await License.findOne({ licenseKey: license_key });
         const license = await License.findOne({ licenseKey: license_key });