/ concept-collection / trystero-messaging-demo
Sign in
concept-collection / trystero-messaging-demo
trystero-messaging-demo / src / util.ts
41 lines · 1.4 KBBlameHistoryRaw
1// Shorten a long Trystero/Nostr peer id for display.
2export const shortId = (id: string): string => id.slice(0, 8)
4// Human-readable byte sizes.
5export const formatBytes = (n: number): string => {
6 if (n < 1024) return `${n} B`
7 const units = ['KB', 'MB', 'GB']
8 let v = n / 1024
9 let i = 0
10 while (v >= 1024 && i < units.length - 1) {
11 v /= 1024
12 i++
13 }
14 return `${v.toFixed(v < 10 ? 2 : 1)} ${units[i]}`
17// A short random id for transfers / log keys.
18export const uid = (): string => Math.random().toString(36).slice(2, 10)
20// SHA-256 of a buffer, hex-encoded. Used to prove that what arrived on the
21// other side is byte-for-byte identical to what was sent.
22export const sha256Hex = async (
23 data: Uint8Array<ArrayBuffer> | ArrayBuffer
24): Promise<string> => {
25 const digest = await crypto.subtle.digest('SHA-256', data)
26 return [...new Uint8Array(digest)]
27 .map(b => b.toString(16).padStart(2, '0'))
28 .join('')
31// Generate `size` bytes of random data, to demo sending large binary payloads
32// without needing a file. crypto.getRandomValues caps at 65536 bytes per call,
33// so we fill in chunks.
34export const randomBytes = (size: number): Uint8Array<ArrayBuffer> => {
35 const out = new Uint8Array(size)
36 const chunk = 65536
37 for (let offset = 0; offset < size; offset += chunk) {
38 crypto.getRandomValues(out.subarray(offset, Math.min(offset + chunk, size)))
39 }
40 return out
moveopenescclose