mirror of
https://github.com/NeteaseCloudMusicApiEnhanced/api-enhanced.git
synced 2025-10-22 14:43:10 +00:00

Refactored main.js to optimize module and server loading, improving code clarity and lazy loading. Updated several dependencies in package.json to their latest versions for better security and compatibility. Updated documentation cover page and home page to reflect project branding changes. Co-Authored-By: binaryify <binaryify@gmail.com>
169 lines
4.2 KiB
JavaScript
169 lines
4.2 KiB
JavaScript
const crypto = require("crypto");
|
||
const os = require("os");
|
||
|
||
class AdvancedClientSignGenerator {
|
||
/**
|
||
* 获取本机MAC地址
|
||
*/
|
||
static getRealMacAddress() {
|
||
try {
|
||
const interfaces = os.networkInterfaces();
|
||
for (let interfaceName in interfaces) {
|
||
const interface = interfaces[interfaceName];
|
||
for (let i = 0; i < interface.length; i++) {
|
||
const alias = interface[i];
|
||
// 排除内部地址和无效地址
|
||
if (
|
||
alias.mac &&
|
||
alias.mac !== "00:00:00:00:00:00" &&
|
||
!alias.internal
|
||
) {
|
||
return alias.mac.toUpperCase();
|
||
}
|
||
}
|
||
}
|
||
return null;
|
||
} catch (error) {
|
||
console.warn("获取MAC地址失败:", error.message);
|
||
return null;
|
||
}
|
||
}
|
||
|
||
/**
|
||
* 生成随机MAC地址
|
||
*/
|
||
static generateRandomMac() {
|
||
const chars = "0123456789ABCDEF";
|
||
let mac = "";
|
||
for (let i = 0; i < 6; i++) {
|
||
if (i > 0) mac += ":";
|
||
mac +=
|
||
chars[Math.floor(Math.random() * 16)] +
|
||
chars[Math.floor(Math.random() * 16)];
|
||
}
|
||
// 确保第一个字节是单播地址(最低位为0)
|
||
const firstByte = parseInt(mac.substring(0, 2), 16);
|
||
const unicastFirstByte = (firstByte & 0xfe)
|
||
.toString(16)
|
||
.padStart(2, "0")
|
||
.toUpperCase();
|
||
return unicastFirstByte + mac.substring(2);
|
||
}
|
||
|
||
/**
|
||
* 获取MAC地址(优先真实,否则随机)
|
||
*/
|
||
static getMacAddress() {
|
||
const realMac = this.getRealMacAddress();
|
||
if (realMac) {
|
||
return realMac;
|
||
}
|
||
console.warn("无法获取真实MAC地址,使用随机生成");
|
||
return this.generateRandomMac();
|
||
}
|
||
|
||
/**
|
||
* 字符串转HEX编码
|
||
*/
|
||
static stringToHex(str) {
|
||
return Buffer.from(str, "utf8").toString("hex").toUpperCase();
|
||
}
|
||
|
||
/**
|
||
* SHA-256哈希
|
||
*/
|
||
static sha256(data) {
|
||
return crypto.createHash("sha256").update(data, "utf8").digest("hex");
|
||
}
|
||
|
||
/**
|
||
* 生成随机设备ID
|
||
*/
|
||
static generateRandomDeviceId() {
|
||
const partLengths = [4, 4, 4, 4, 4, 4, 4, 5]; // 各部分长度
|
||
const chars = "0123456789ABCDEF";
|
||
|
||
const parts = partLengths.map((length) => {
|
||
let part = "";
|
||
for (let i = 0; i < length; i++) {
|
||
part += chars[Math.floor(Math.random() * 16)];
|
||
}
|
||
return part;
|
||
});
|
||
|
||
return parts.join("_");
|
||
}
|
||
|
||
/**
|
||
* 生成随机clientSign(优先使用真实MAC,否则随机)
|
||
*/
|
||
static generateRandomClientSign(secretKey = "") {
|
||
// 获取MAC地址(优先真实,否则随机)
|
||
const macAddress = this.getMacAddress();
|
||
|
||
// 生成随机设备ID
|
||
const deviceId = this.generateRandomDeviceId();
|
||
|
||
// 转换设备ID为HEX
|
||
const hexDeviceId = this.stringToHex(deviceId);
|
||
|
||
// 构造签名字符串
|
||
const signString = `${macAddress}@@@${hexDeviceId}`;
|
||
|
||
// 生成哈希
|
||
const hash = this.sha256(signString + secretKey);
|
||
|
||
return `${signString}@@@@@@${hash}`;
|
||
}
|
||
|
||
/**
|
||
* 批量生成多个随机签名
|
||
*/
|
||
static generateMultipleRandomSigns(count, secretKey = "") {
|
||
const signs = [];
|
||
for (let i = 0; i < count; i++) {
|
||
signs.push(this.generateRandomClientSign(secretKey));
|
||
}
|
||
return signs;
|
||
}
|
||
|
||
/**
|
||
* 使用指定参数生成签名
|
||
*/
|
||
static generateWithCustomDeviceId(macAddress, deviceId, secretKey = "") {
|
||
const hexDeviceId = this.stringToHex(deviceId);
|
||
const signString = `${macAddress}@@@${hexDeviceId}`;
|
||
const hash = this.sha256(signString + secretKey);
|
||
return `${signString}@@@@@@${hash}`;
|
||
}
|
||
|
||
/**
|
||
* 验证签名格式是否正确
|
||
*/
|
||
static validateClientSign(clientSign) {
|
||
try {
|
||
const parts = clientSign.split("@@@@@@");
|
||
if (parts.length !== 2) return false;
|
||
|
||
const [infoPart, hash] = parts;
|
||
const infoParts = infoPart.split("@@@");
|
||
if (infoParts.length !== 2) return false;
|
||
|
||
const [mac, hexDeviceId] = infoParts;
|
||
|
||
// 验证MAC地址格式
|
||
const macRegex = /^([0-9A-F]{2}:){5}[0-9A-F]{2}$/;
|
||
if (!macRegex.test(mac)) return false;
|
||
|
||
// 验证哈希格式
|
||
const hashRegex = /^[0-9a-f]{64}$/;
|
||
if (!hashRegex.test(hash)) return false;
|
||
|
||
return true;
|
||
} catch (error) {
|
||
return false;
|
||
}
|
||
}
|
||
}
|
||
|
||
module.exports = AdvancedClientSignGenerator; |