Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 | 1x 7x 28x 7x 6x 5x 4x 3x 3x 2x 2x 1x 1x 1x 7x 6x 6x 6x 6x 3x 1x 2x 2x 2x 9x 3x 3x 2x 1x 2x 2x 2x 1x 1x 1x 2x 2x 261x 2x 1x 2x 2x 2x 2x 1x 2x | import { Injectable } from '@angular/core';
@Injectable({ providedIn: 'root' })
export class ContentPreviewService {
detectContentType(data: Uint8Array): string {
// Check for common file signatures
if (data.length >= 4) {
const header = Array.from(data.slice(0, 4)).map(b => b.toString(16).padStart(2, '0')).join('');
// PNG
if (header === '89504e47') return 'image/png';
// JPEG
if (header.startsWith('ffd8ff')) return 'image/jpeg';
// GIF
if (header.startsWith('47494638')) return 'image/gif';
// PDF
if (header === '25504446') return 'application/pdf';
}
// Try to decode as text
try {
const text = new TextDecoder('utf-8', { fatal: true }).decode(data.slice(0, 1000));
// Check if it's JSON
try {
JSON.parse(text);
return 'application/json';
} catch {
// Not JSON, but is text
return 'text/plain';
}
} catch {
// Not valid UTF-8, treat as binary
return 'application/octet-stream';
}
}
formatFileSize(bytes: number): string {
if (bytes === 0) return '0 Bytes';
const k = 1024;
const sizes = ['Bytes', 'KB', 'MB', 'GB'];
const i = Math.floor(Math.log(bytes) / Math.log(k));
return parseFloat((bytes / Math.pow(k, i)).toFixed(2)) + ' ' + sizes[i];
}
formatHashForDisplay(hashValue: string, maxLength = 16): string {
if (hashValue.length <= maxLength) {
return hashValue;
}
const prefixLength = 6;
const suffixLength = 8;
return `${hashValue.substring(0, prefixLength)}...${hashValue.substring(hashValue.length - suffixLength)}`;
}
generatePreview(data: Uint8Array, format: 'text' | 'json' | 'hex' | 'base64', maxSize = 1000): string {
switch (format) {
case 'text':
try {
const text = new TextDecoder('utf-8', { fatal: true }).decode(data);
return text.length > maxSize
? text.substring(0, maxSize) + '...'
: text;
} catch {
return 'Unable to decode as text';
}
case 'json':
try {
const text = new TextDecoder().decode(data);
const json = JSON.parse(text);
const formatted = JSON.stringify(json, null, 2);
return formatted.length > maxSize
? formatted.substring(0, maxSize) + '...'
: formatted;
} catch {
return 'Invalid JSON';
}
case 'hex':
const hexBytes = Math.min(data.length, 256);
let hex = Array.from(data.slice(0, hexBytes))
.map(b => b.toString(16).padStart(2, '0'))
.join(' ')
.toUpperCase();
if (data.length > hexBytes) {
hex += ' ...';
}
return hex;
case 'base64':
const base64Bytes = Math.min(data.length, 1000);
let base64 = btoa(String.fromCharCode(...data.slice(0, base64Bytes)));
if (data.length > base64Bytes) {
base64 += '...';
}
return base64;
default:
return 'Unsupported format';
}
}
} |