unpak.js
Version:
Modern TypeScript library for reading Unreal Engine pak files and assets, inspired by CUE4Parse
119 lines • 4.08 kB
JavaScript
Object.defineProperty(exports, "__esModule", { value: true });
exports.KeyManager = exports.MemoryKeyProvider = void 0;
const CryptoProvider_1 = require("./CryptoProvider");
const Logger_1 = require("../core/logging/Logger");
/**
* Simple in-memory key provider
*/
class MemoryKeyProvider {
keys = new Map();
async getKey(guid) {
return this.keys.get(guid.toLowerCase()) || null;
}
async hasKey(guid) {
return this.keys.has(guid.toLowerCase());
}
async addKey(guid, key) {
try {
const keyBuffer = CryptoProvider_1.KeyUtils.normalizeKey(key);
if (!CryptoProvider_1.KeyUtils.validateKeyLength(keyBuffer)) {
throw new Error(`Invalid key length: ${keyBuffer.length} bytes. Expected 16, 24, or 32 bytes.`);
}
this.keys.set(guid.toLowerCase(), keyBuffer);
Logger_1.logger.debug('Added key to memory provider', {
guid: guid.toLowerCase(),
keyLength: keyBuffer.length,
});
}
catch (error) {
if (error instanceof Error && error.message.includes('hex string')) {
throw new Error(`Invalid key format: ${error.message}`);
}
throw error;
}
}
/**
* Get all stored key GUIDs
*/
getStoredKeys() {
return Array.from(this.keys.keys());
}
/**
* Clear all stored keys
*/
clear() {
this.keys.clear();
}
}
exports.MemoryKeyProvider = MemoryKeyProvider;
/**
* Key manager implementation with caching and multiple providers
*/
class KeyManager {
providers = [];
cache = new Map();
addProvider(provider) {
this.providers.push(provider);
Logger_1.logger.debug('Added key provider', { providerType: provider.constructor.name });
}
async getKey(guid) {
const normalizedGuid = guid.toLowerCase();
// Check cache first
if (this.cache.has(normalizedGuid)) {
return this.cache.get(normalizedGuid) || null;
}
// Try each provider
for (const provider of this.providers) {
try {
const key = await provider.getKey(normalizedGuid);
if (key) {
this.cache.set(normalizedGuid, key);
Logger_1.logger.debug('Found key in provider', {
guid: normalizedGuid,
providerType: provider.constructor.name,
});
return key;
}
}
catch (error) {
Logger_1.logger.warn('Error getting key from provider', {
guid: normalizedGuid,
providerType: provider.constructor.name,
error: error instanceof Error ? error.message : String(error),
});
}
}
// Cache miss result
this.cache.set(normalizedGuid, null);
Logger_1.logger.warn('Key not found in any provider', { guid: normalizedGuid });
return null;
}
async submitKey(guid, key) {
const normalizedGuid = guid.toLowerCase();
const keyBuffer = CryptoProvider_1.KeyUtils.normalizeKey(key);
// Add to the first provider (create memory provider if none exist)
if (this.providers.length === 0) {
this.addProvider(new MemoryKeyProvider());
}
await this.providers[0].addKey(normalizedGuid, keyBuffer);
// Update cache
this.cache.set(normalizedGuid, keyBuffer);
Logger_1.logger.info('Submitted key', { guid: normalizedGuid, keyLength: keyBuffer.length });
}
clearCache() {
this.cache.clear();
Logger_1.logger.debug('Cleared key cache');
}
/**
* Get statistics about cached keys
*/
getStats() {
return {
cachedKeys: this.cache.size,
providers: this.providers.length,
};
}
}
exports.KeyManager = KeyManager;
//# sourceMappingURL=KeyManager.js.map
;