import type { QueueItem } from './queue'; import { buildCsrfHeaders } from '../lib/csrf'; export async function createUpload( url: string, it: QueueItem, deviceId: string, onProgress?: (percent: number) => void ): Promise> { return new Promise((resolve, reject) => { const xhr = new XMLHttpRequest(); xhr.open('POST', url, true); const headers = buildCsrfHeaders(deviceId); Object.entries(headers).forEach(([key, value]) => { xhr.setRequestHeader(key, value); }); const form = new FormData(); form.append('photo', it.blob, it.fileName); if (it.emotion_id) form.append('emotion_id', String(it.emotion_id)); if (it.task_id) form.append('task_id', String(it.task_id)); if (typeof it.live_show_opt_in === 'boolean') { form.append('live_show_opt_in', it.live_show_opt_in ? '1' : '0'); } xhr.upload.onprogress = (ev) => { if (onProgress && ev.lengthComputable) { const pct = Math.min(100, Math.round((ev.loaded / ev.total) * 100)); onProgress(pct); } }; xhr.onload = () => { if (xhr.status >= 200 && xhr.status < 300) { try { resolve(JSON.parse(xhr.responseText)); } catch (error) { console.warn('Upload response parse failed', error); resolve({}); } } else { reject(new Error('upload failed')); } }; xhr.onerror = () => reject(new Error('network error')); xhr.send(form); }); }