feat: finalize mindspace service extraction phase a
This commit is contained in:
@@ -0,0 +1,40 @@
|
||||
import crypto from 'node:crypto';
|
||||
|
||||
function normalizeSecret(secret) {
|
||||
return String(secret ?? '');
|
||||
}
|
||||
|
||||
export function publicAssetToken(assetId, secret) {
|
||||
const normalizedAssetId = String(assetId ?? '').trim();
|
||||
if (!normalizedAssetId) return '';
|
||||
return crypto
|
||||
.createHmac('sha256', normalizeSecret(secret))
|
||||
.update(`mindspace-public-asset:v1:${normalizedAssetId}`)
|
||||
.digest('base64url');
|
||||
}
|
||||
|
||||
export function verifyPublicAssetToken(assetId, token, secret) {
|
||||
const value = Array.isArray(token) ? token[0] : token;
|
||||
const provided = String(value ?? '').trim();
|
||||
if (!provided) return false;
|
||||
const expected = publicAssetToken(assetId, secret);
|
||||
const providedBuffer = Buffer.from(provided);
|
||||
const expectedBuffer = Buffer.from(expected);
|
||||
return (
|
||||
providedBuffer.length === expectedBuffer.length &&
|
||||
crypto.timingSafeEqual(providedBuffer, expectedBuffer)
|
||||
);
|
||||
}
|
||||
|
||||
export function appendPublicAssetTokens(html, secret) {
|
||||
const source = String(html ?? '');
|
||||
if (!source || !source.includes('/api/mindspace/v1/assets/')) return source;
|
||||
return source.replace(
|
||||
/((?:https?:\/\/[^"'<>\\\s]+)?\/api\/mindspace\/v1\/assets\/([a-z0-9-]+)\/download)(\?[^"'<>\\\s)]*)?/gi,
|
||||
(value, base, assetId, query = '') => {
|
||||
if (/(?:\?|&|&)public_token=/.test(query)) return value;
|
||||
const separator = query ? (query.includes('&') ? '&' : '&') : '?';
|
||||
return `${base}${query}${separator}public_token=${publicAssetToken(assetId, secret)}`;
|
||||
},
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user