Skip to content

⚡ Bolt: Optimize exportIconsForYAML by replacing sequential await loop with concurrent Promise.all#509

Closed
aafre wants to merge 1 commit into
mainfrom
bolt-concurrent-icon-export-17027412782608959801
Closed

⚡ Bolt: Optimize exportIconsForYAML by replacing sequential await loop with concurrent Promise.all#509
aafre wants to merge 1 commit into
mainfrom
bolt-concurrent-icon-export-17027412782608959801

Conversation

@aafre
Copy link
Copy Markdown
Owner

@aafre aafre commented May 4, 2026

What

Refactored the sequential for loop in exportIconsForYAML to use Promise.all for concurrent execution of asynchronous FileReader conversions.

Why

The previous implementation awaited the fileToBase64 conversion sequentially for each icon file, needlessly blocking execution and slowing down the export process, especially when multiple icons are present.

Impact

Significantly reduces the total time required to export icons by processing all FileReader operations in parallel.

Measurement

Verify the improvement by profiling the execution time of exportIconsForYAML when multiple icon files are registered. The parallel implementation handles the I/O conversions concurrently, reducing overall wait time.


PR created automatically by Jules for task 17027412782608959801 started by @aafre

Co-authored-by: aafre <8656674+aafre@users.noreply.github.com>
@google-labs-jules
Copy link
Copy Markdown
Contributor

👋 Jules, reporting for duty! I'm here to lend a hand with this pull request.

When you start a review, I'll add a 👀 emoji to each comment to let you know I've read it. I'll focus on feedback directed at me and will do my best to stay out of conversations between you and other bots or reviewers to keep the noise down.

I'll push a commit with your requested changes shortly after. Please note there might be a delay between these steps, but rest assured I'm on the job!

For more direct control, you can switch me to Reactive Mode. When this mode is on, I will only act on comments where you specifically mention me with @jules. You can find this option in the Pull Request section of your global Jules UI settings. You can always switch back!

New to Jules? Learn more at jules.google/docs.


For security, I will only act on instructions from the user who triggered this task.

Copy link
Copy Markdown
Contributor

@gemini-code-assist gemini-code-assist Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request optimizes the icon export process by refactoring sequential file conversion loops into concurrent operations using Promise.all. The feedback suggests adopting a more functional approach using Object.fromEntries to avoid mutating a shared object and recommends deduplicating the input filenames to prevent redundant processing.

Comment on lines +173 to +190
await Promise.all(
targetFilenames.map(async (filename) => {
const entry = registry[filename];
if (entry) {
try {
const base64Data = await fileToBase64(entry.file);
exportData[filename] = {
data: base64Data,
type: entry.file.type,
size: entry.file.size,
uploadedAt: entry.uploadedAt.toISOString(),
};
} catch (error) {
console.warn(`Failed to export icon ${filename}:`, error);
}
}
}
}
})
);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

While the current implementation correctly parallelizes the asynchronous operations, it relies on mutating the exportData object from within the Promise.all callbacks. A more functional approach using Object.fromEntries would avoid side effects on a shared object and improve code clarity. Additionally, if filenames is provided as an argument, it may contain duplicates, leading to redundant processing. Consider deduplicating the input array.

    const results = await Promise.all(
      [...new Set(targetFilenames)].map(async (filename) => {
        const entry = registry[filename];
        if (!entry) return null;

        try {
          const base64Data = await fileToBase64(entry.file);
          return [
            filename,
            {
              data: base64Data,
              type: entry.file.type,
              size: entry.file.size,
              uploadedAt: entry.uploadedAt.toISOString(),
            },
          ];
        } catch (error) {
          console.warn(`Failed to export icon ${filename}:`, error);
          return null;
        }
      })
    );

    const exportData: IconExportData = Object.fromEntries(
      results.filter((result): result is [string, any] => result !== null)
    );

@aafre
Copy link
Copy Markdown
Owner Author

aafre commented May 25, 2026

Closing duplicate — the most recent version of this change is PR #535.

@aafre aafre closed this May 25, 2026
@google-labs-jules
Copy link
Copy Markdown
Contributor

Closing duplicate — the most recent version of this change is PR #535.

Understood. Acknowledging that this work is a duplicate and stopping work on this task.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant