@sparkvault/sdk 1.10.0 → 1.10.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -7049,12 +7049,20 @@ class UploadModalContainer {
7049
7049
  this.elements.modal.classList.add('svu-with-sidebar');
7050
7050
  this.elements.modal.appendChild(sidebar);
7051
7051
  this.elements.sidebar = sidebar;
7052
+ // Hide header when sidebar is shown (sidebar has its own logo)
7053
+ if (this.headerElement) {
7054
+ this.headerElement.style.display = 'none';
7055
+ }
7052
7056
  }
7053
7057
  else if (!show && this.elements.sidebar) {
7054
7058
  // Remove sidebar
7055
7059
  this.elements.modal.classList.remove('svu-with-sidebar');
7056
7060
  this.elements.sidebar.remove();
7057
7061
  this.elements.sidebar = null;
7062
+ // Show header again when sidebar is hidden
7063
+ if (this.headerElement) {
7064
+ this.headerElement.style.display = '';
7065
+ }
7058
7066
  }
7059
7067
  }
7060
7068
  createSecuritySidebar() {
@@ -8180,48 +8188,66 @@ class UploadRenderer {
8180
8188
  }
8181
8189
  // Build full upload URL
8182
8190
  const uploadUrl = location.startsWith('http') ? location : `${url.origin}${location}`;
8183
- // Step 2: Upload file in chunks
8191
+ // Step 2: Upload file in chunks with progress tracking
8184
8192
  let offset = 0;
8185
8193
  const totalSize = file.size;
8186
8194
  while (offset < totalSize) {
8187
- const end = Math.min(offset + chunkSize, totalSize);
8188
- const chunk = file.slice(offset, end);
8189
- // Upload chunk
8190
- const patchResponse = await fetch(uploadUrl, {
8191
- method: 'PATCH',
8192
- headers: {
8193
- 'Tus-Resumable': TUS_VERSION,
8194
- 'Upload-Offset': String(offset),
8195
- 'Content-Type': 'application/offset+octet-stream',
8196
- },
8197
- body: chunk,
8198
- });
8199
- if (!patchResponse.ok) {
8200
- const errorText = await patchResponse.text();
8201
- throw new Error(`Chunk upload failed: ${patchResponse.status} ${errorText}`);
8202
- }
8203
- // Update offset from server response
8204
- const newOffsetHeader = patchResponse.headers.get('Upload-Offset');
8205
- const newOffset = newOffsetHeader ? parseInt(newOffsetHeader, 10) : end;
8195
+ const chunkStart = offset;
8196
+ const chunkEnd = Math.min(offset + chunkSize, totalSize);
8197
+ const chunk = file.slice(chunkStart, chunkEnd);
8198
+ // Upload chunk with XHR for progress events
8199
+ const newOffset = await this.uploadChunkWithProgress(uploadUrl, chunk, chunkStart, totalSize, TUS_VERSION, file, ingotId, requestId);
8206
8200
  offset = newOffset;
8207
- // Update progress
8208
- const progress = Math.round((offset / totalSize) * 100);
8209
- this.setState({
8210
- view: 'uploading',
8211
- file,
8212
- ingotId,
8213
- requestId,
8214
- progress,
8215
- bytesUploaded: offset,
8216
- });
8217
- this.callbacks.onProgress?.({
8218
- bytesUploaded: offset,
8219
- bytesTotal: totalSize,
8220
- percentage: progress,
8221
- phase: 'uploading',
8222
- });
8223
8201
  }
8224
8202
  }
8203
+ /**
8204
+ * Upload a single chunk using XMLHttpRequest for progress tracking
8205
+ */
8206
+ uploadChunkWithProgress(uploadUrl, chunk, chunkStart, totalSize, tusVersion, file, ingotId, requestId) {
8207
+ return new Promise((resolve, reject) => {
8208
+ const xhr = new XMLHttpRequest();
8209
+ // Track progress within this chunk
8210
+ xhr.upload.onprogress = (e) => {
8211
+ if (e.lengthComputable) {
8212
+ // Calculate total progress: completed chunks + progress within current chunk
8213
+ const totalUploaded = chunkStart + e.loaded;
8214
+ const progress = Math.round((totalUploaded / totalSize) * 100);
8215
+ this.setState({
8216
+ view: 'uploading',
8217
+ file,
8218
+ ingotId,
8219
+ requestId,
8220
+ progress,
8221
+ bytesUploaded: totalUploaded,
8222
+ });
8223
+ this.callbacks.onProgress?.({
8224
+ bytesUploaded: totalUploaded,
8225
+ bytesTotal: totalSize,
8226
+ percentage: progress,
8227
+ phase: 'uploading',
8228
+ });
8229
+ }
8230
+ };
8231
+ xhr.onload = () => {
8232
+ if (xhr.status >= 200 && xhr.status < 300) {
8233
+ // Get new offset from server response
8234
+ const newOffsetHeader = xhr.getResponseHeader('Upload-Offset');
8235
+ const newOffset = newOffsetHeader ? parseInt(newOffsetHeader, 10) : chunkStart + chunk.size;
8236
+ resolve(newOffset);
8237
+ }
8238
+ else {
8239
+ reject(new Error(`Chunk upload failed with status ${xhr.status}`));
8240
+ }
8241
+ };
8242
+ xhr.onerror = () => reject(new Error('Chunk upload failed'));
8243
+ xhr.ontimeout = () => reject(new Error('Chunk upload timed out'));
8244
+ xhr.open('PATCH', uploadUrl);
8245
+ xhr.setRequestHeader('Tus-Resumable', tusVersion);
8246
+ xhr.setRequestHeader('Upload-Offset', String(chunkStart));
8247
+ xhr.setRequestHeader('Content-Type', 'application/offset+octet-stream');
8248
+ xhr.send(chunk);
8249
+ });
8250
+ }
8225
8251
  async runCeremony(file, ingotId, requestId) {
8226
8252
  for (let i = 0; i < CEREMONY_STEPS.length; i++) {
8227
8253
  this.setState({