设计一个有效的软件许可证系统需要结合技术验证和法律约束,以下是一个分层次的许可证设计方案,从基础到高级逐步增强保护:
1. 基础许可证设计(简单易行)
核心要素
-
唯一标识符:绑定到用户或设备(如机器码)。
-
有效期:设置许可证过期时间。
-
数字签名:防止篡改(如RSA签名)。
实现步骤
-
生成机器码
基于用户硬件信息(CPU序列号、MAC地址、磁盘ID)生成唯一机器码:import hashlib, subprocess def get_machine_code(): # 获取硬件信息(示例,需根据系统调整命令) cpu = subprocess.check_output("wmic cpu get ProcessorId", shell=True).decode().split("\n")[1].strip() disk = subprocess.check_output("wmic diskdrive get SerialNumber", shell=True).decode().split("\n")[1].strip() mac = subprocess.check_output("getmac", shell=True).decode().split("\n")[3].split()[0] raw_code = f"{cpu}-{disk}-{mac}" return hashlib.sha256(raw_code.encode()).hexdigest()[:16] # 16位机器码
-
生成许可证文件
使用非对称加密签名(如RSA)保护许可证内容:from cryptography.hazmat.primitives import hashes from cryptography.hazmat.primitives.asymmetric import padding, rsa # 生成密钥对(私钥自己保存,公钥嵌入代码) private_key = rsa.generate_private_key(public_exponent=65537, key_size=2048) public_key = private_key.public_key() # 创建许可证内容(JSON格式) license_data = { "machine_code": "用户机器码", "expire_date": "2025-12-31", "features": ["api_access", "premium_support"] } # 签名并保存 signature = private_key.sign( str(license_data).encode(), padding.PSS(mgf=padding.MGF1(hashes.SHA256()), salt_length=padding.PSS.MAX_LENGTH), hashes.SHA256() ) with open("license.lic", "wb") as f: f.write(signature + b"||" + json.dumps(license_data).encode())
-
代码中验证许可证
在FastAPI启动时或关键接口中校验:from fastapi import FastAPI, HTTPException app = FastAPI() def verify_license(): try: with open("/app/license.lic", "rb") as f: signature, data = f.read().split(b"||") # 使用公钥验证签名 public_key.verify( signature, data, padding.PSS(mgf=padding.MGF1(hashes.SHA256()), hashes.SHA256() ) license = json.loads(data.decode()) if license["machine_code"] != get_machine_code(): raise HTTPException(status_code=403, detail="机器码不匹配") if datetime.now() > datetime.strptime(license["expire_date"], "%Y-%m-%d"): raise HTTPException(status_code=403, detail="许可证已过期") except Exception as e: raise HTTPException(status_code=403, detail=f"许可证无效: {str(e)}") @app.get("/api/protected") async def protected_route(): verify_license() return {"status": "success"}
2. 进阶方案(增强安全性)
动态在线验证
- 定期连接许可证服务器:
容器启动后定期向你的服务器发送心跳(携带机器码和许可证哈希),服务器返回是否有效。import requests def online_verify(): try: response = requests.post( "https://your-license-server.com/verify", json={"machine_code": get_machine_code(), "license_hash": license_hash} ) if not response.json()["valid"]: shutdown_app() # 终止服务 except: shutdown_app() # 断网时直接拒绝服务(根据需求调整策略)
硬件绑定增强
-
多因素混合指纹:
组合更多硬件信息(如主板型号、GPU ID、BIOS版本)生成机器码,增加伪造难度。
代码混淆与反调试
-
使用PyArmor加密Python代码:
确保许可证验证逻辑无法被直接逆向分析。 -
检测调试器:
在代码中集成反调试逻辑,发现调试行为时触发异常。
3. 企业级方案(高安全性)
基于TPM的硬件加密
-
依赖可信平台模块(TPM):
将许可证密钥存储在TPM芯片中,确保仅在特定物理设备上可用。 -
实现步骤:
使用tpm2-tools
或python-tpm2-pytss
库与TPM交互。
许可证微服务化
-
关键功能依赖远程API:
将核心业务逻辑(如数据处理)部署在你的服务器,本地容器仅作为代理,通过许可证Token访问。
区块链存证
-
许可证信息上链:
在区块链(如以太坊私有链)记录许可证签发和验证记录,防止抵赖和伪造。
4. 法律与协议设计
- 用户协议约束
在许可证文件中明确条款:-
禁止逆向工程、反编译、多设备复用。
-
明确违反协议的法律责任。
-
-
定期审计
保留许可证验证日志,发现异常时通过法律途径追责。
推荐工具与库
工具/库 | 用途 |
---|---|
cryptography | RSA签名/验证 |
PyArmor | Python代码混淆 |
tpm2-tools | TPM硬件集成 |
Docker Content Trust | 镜像签名防止篡改 |
总结
-
简单场景:机器码绑定 + RSA签名 + 过期时间(适合小型项目)。
-
商业项目:增加在线验证 + 代码混淆 + 多硬件因素绑定。
-
高安全需求:TPM硬件加密 + 核心逻辑云端化。
关键原则:提高攻击成本(技术) + 降低法律风险(协议) + 平衡用户体验(如离线授权机制)。