import * as plugins from '../../plugins.js'; import type { ICertificateData } from './certificate-manager.js'; export class CertStore { constructor(private certDir: string) {} public async initialize(): Promise { await plugins.smartfile.fs.ensureDirSync(this.certDir); } public async getCertificate(routeName: string): Promise { const certPath = this.getCertPath(routeName); const metaPath = `${certPath}/meta.json`; if (!await plugins.smartfile.fs.fileExistsSync(metaPath)) { return null; } try { const metaFile = await plugins.smartfile.SmartFile.fromFilePath(metaPath); const meta = JSON.parse(metaFile.contents.toString()); const certFile = await plugins.smartfile.SmartFile.fromFilePath(`${certPath}/cert.pem`); const cert = certFile.contents.toString(); const keyFile = await plugins.smartfile.SmartFile.fromFilePath(`${certPath}/key.pem`); const key = keyFile.contents.toString(); let ca: string | undefined; const caPath = `${certPath}/ca.pem`; if (await plugins.smartfile.fs.fileExistsSync(caPath)) { const caFile = await plugins.smartfile.SmartFile.fromFilePath(caPath); ca = caFile.contents.toString(); } return { cert, key, ca, expiryDate: new Date(meta.expiryDate), issueDate: new Date(meta.issueDate) }; } catch (error) { console.error(`Failed to load certificate for ${routeName}: ${error}`); return null; } } public async saveCertificate( routeName: string, certData: ICertificateData ): Promise { const certPath = this.getCertPath(routeName); await plugins.smartfile.fs.ensureDirSync(certPath); // Save certificate files await plugins.smartfile.memory.toFs(certData.cert, `${certPath}/cert.pem`); await plugins.smartfile.memory.toFs(certData.key, `${certPath}/key.pem`); if (certData.ca) { await plugins.smartfile.memory.toFs(certData.ca, `${certPath}/ca.pem`); } // Save metadata const meta = { expiryDate: certData.expiryDate.toISOString(), issueDate: certData.issueDate.toISOString(), savedAt: new Date().toISOString() }; await plugins.smartfile.memory.toFs(JSON.stringify(meta, null, 2), `${certPath}/meta.json`); } public async deleteCertificate(routeName: string): Promise { const certPath = this.getCertPath(routeName); if (await plugins.smartfile.fs.fileExistsSync(certPath)) { await plugins.smartfile.fs.removeManySync([certPath]); } } private getCertPath(routeName: string): string { // Sanitize route name for filesystem const safeName = routeName.replace(/[^a-zA-Z0-9-_]/g, '_'); return `${this.certDir}/${safeName}`; } }