Skip to content

feat: show bulk library progress stats in free settings#66

Open
bfintal wants to merge 13 commits into
developfrom
feat/bulk-progress-stats-upsell
Open

feat: show bulk library progress stats in free settings#66
bfintal wants to merge 13 commits into
developfrom
feat/bulk-progress-stats-upsell

Conversation

@bfintal

@bfintal bfintal commented Jul 17, 2026

Copy link
Copy Markdown
Contributor

Summary

  • Move Media Library attachment listing into free (Cimo_Bulk_Library + GET /cimo/v1/attachments) so free can read bulk progress without Premium.
  • Add shared bulk progress helpers and UI (bulk-stats.js, BulkOptimizerStats) and show real “X of Y optimized” in the free Bulk Optimization upsell (non-working controls).
  • Use the same mime inclusion rules as Premium for stats counting (extension fallback, HEIC, video/audio bulk formats + browser play check).

Test plan

  • Free settings: Bulk Optimization section shows loading then “X of Y optimized” matching a Premium install on the same library
  • Free CTA links to pricing; View Files stays disabled
  • Free build still works without Premium files present
  • Attachment REST endpoint requires upload/edit capabilities

Made with Cursor

Summary by CodeRabbit

  • New Features
    • Added Bulk Optimization progress for free users, including optimized/unoptimized counters and skipped-files handling, plus an upsell panel.
    • Added a premium savings estimate link based on current optimization progress.
  • Improvements
    • Optimization statistics now update immediately after uploads for more accurate tracking.
    • Enhanced the admin rating notice with improved snooze/dismiss behavior and updated presentation.
  • Style
    • Refreshed bulk-optimization UI ordering and upsell visuals, including updated button/link styling.

Move attachment listing and shared progress counting into free so the Bulk Optimization upsell can display real "X of Y optimized" numbers.

Co-authored-by: Cursor <cursoragent@cursor.com>
@cursor

cursor Bot commented Jul 17, 2026

Copy link
Copy Markdown

Bugbot is not enabled for your account, so this pull request was not reviewed.

Enable Bugbot in the Cursor dashboard to get automatic reviews on future PRs.

@coderabbitai

coderabbitai Bot commented Jul 17, 2026

Copy link
Copy Markdown

Review Change Stack

Warning

Review limit reached

@bfintal, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 8 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: f06d9f24-98c9-4cda-927d-b97f05c0b8d1

📥 Commits

Reviewing files that changed from the base of the PR and between 8baefa5 and 76a844c.

📒 Files selected for processing (5)
  • src/admin/class-admin-notices.php
  • src/admin/class-bulk-library.php
  • src/admin/class-stats.php
  • src/admin/js/bulk-optimizer/use-bulk-progress-stats.js
  • src/shared/estimate-additional-savings.js
📝 Walkthrough

Walkthrough

Adds a permission-gated attachment REST endpoint, shared bulk progress and savings calculations, free-tier progress and upsell UI, incremental upload statistics, updated rating notice controls, and packaging failure handling.

Changes

Bulk optimization progress

Layer / File(s) Summary
Attachment progress API
cimo.php, src/admin/class-bulk-library.php
Loads the bulk library and registers GET /cimo/v1/attachments, returning filtered attachment metadata and server-side progress helpers.
Shared progress calculation
src/shared/bulk-stats.js
Adds MIME eligibility, attachment status mapping, and aggregate progress counts.
Savings estimate data
src/admin/class-stats.php, src/admin/class-metadata.php, src/shared/estimate-additional-savings.js
Adds raw statistics, incremental upload updates, savings calculations, and byte formatting helpers.
Progress and upsell UI
src/admin/js/bulk-optimizer/*, src/admin/js/page/premium-savings-estimate.js
Fetches attachment progress and renders progress, pricing, and estimated-savings links.
Admin bulk integration and styling
src/admin/js/page/admin-settings.js, src/admin/css/admin-page.css
Wires free-tier progress and upsell content into settings and updates related styles.

Rating notice controls

Layer / File(s) Summary
Rating notice lifecycle
src/admin/class-admin-notices.php, src/admin/class-admin.php, src/admin/js/page/admin-settings.js, src/admin/css/admin-page.css
Adds gated display, nonce-protected snooze and dismissal AJAX handlers, removes localized dismissal state and related UI logic, and removes obsolete rating styles.
Premium notice savings copy
src/admin/class-admin-notices.php
Selects library premium notice text based on the additional-savings estimate.

Project and packaging support

Layer / File(s) Summary
Repository guidance and packaging status
.cursor/rules/cimo-project-repos.mdc, scripts/package.js
Documents repository layout and ensures packaging failures return exit code 1.

Estimated code review effort: 4 (Complex) | ~60 minutes

Sequence Diagram(s)

sequenceDiagram
  participant AdminSettings
  participant BulkProgressStatsProvider
  participant CimoREST
  participant BulkStats
  participant BulkOptimizationUpsell
  AdminSettings->>BulkProgressStatsProvider: Render free-tier bulk settings
  BulkProgressStatsProvider->>CimoREST: GET /cimo/v1/attachments
  CimoREST-->>BulkProgressStatsProvider: Normalized attachment records
  BulkProgressStatsProvider->>BulkStats: Count attachment progress
  BulkStats-->>BulkProgressStatsProvider: Optimized, unoptimized, skipped, total
  BulkOptimizationUpsell->>BulkProgressStatsProvider: Read shared progress
  BulkOptimizationUpsell-->>AdminSettings: Render progress and pricing actions
Loading

Possibly related PRs

  • gambitph/Cimo#34: Adds related bulk-stat tracking foundations extended by this change.

Suggested reviewers: arukuen

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly matches the main change: adding bulk library progress stats to the free settings UI.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/bulk-progress-stats-upsell

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 5

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/admin/class-bulk-library.php`:
- Around line 47-52: Update get_all_attachments() to avoid querying and
returning the entire Media Library in one request. Add server-side pagination
with bounded query limits and an offset/page parameter, returning only the
requested attachment details while preserving the existing response contract; if
aggregate counts are needed, provide them separately rather than materializing
every attachment.
- Around line 61-65: Update the MIME-type filter in the bulk library query to
also allow attachments with an empty stored post_mime_type, so they reach
resolveAttachmentMimeType() for extension-based resolution. Preserve the
existing image/, video/, and audio/ MIME matches.

In `@src/admin/js/bulk-optimizer/bulk-optimization-upsell.js`:
- Around line 19-29: Update the attachment-loading effect around apiFetch and
the bulk optimization stats UI to track request failures separately from valid
statistics. In the catch handler, set an error state rather than resetting stats
to zero, and render a “progress unavailable” message when that state is present
while preserving normal stats rendering for successful requests and the existing
loading completion behavior.

In `@src/admin/js/bulk-optimizer/bulk-optimizer-stats.js`:
- Around line 52-65: Update the skipped-results control around onSkippedClick so
it only exposes button semantics and keyboard focusability when a handler
exists. When onSkippedClick is absent, render the skipped label as
non-interactive plain text without click or keydown behavior; preserve the
existing interactive behavior when the callback is provided.

In `@src/shared/bulk-stats.js`:
- Around line 39-41: Add descriptive text to each of the seven `@return`
annotations in the documented functions of bulk-stats.js, including the
locations listed in the comment, while preserving their existing boolean or
other return types so jsdoc/require-returns-description passes.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 20c68216-e2ab-43cf-8713-7cf149f8d064

📥 Commits

Reviewing files that changed from the base of the PR and between 996ac95 and 28dff2a.

📒 Files selected for processing (7)
  • cimo.php
  • src/admin/class-bulk-library.php
  • src/admin/css/admin-page.css
  • src/admin/js/bulk-optimizer/bulk-optimization-upsell.js
  • src/admin/js/bulk-optimizer/bulk-optimizer-stats.js
  • src/admin/js/page/admin-settings.js
  • src/shared/bulk-stats.js

Comment on lines +47 to +52
public static function get_all_attachments() {
global $wpdb;

// phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching
$attachments = $wpdb->get_results(
$wpdb->prepare(

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🚀 Performance & Scalability | 🟠 Major | 🏗️ Heavy lift

Avoid loading the entire Media Library into one REST response.

get_all_attachments() performs an unbounded query, materializes metadata for every result, and sends the full dataset to the browser. Large libraries can exceed PHP memory/request limits or freeze the settings page. Add pagination, or expose server-side aggregate statistics and paginate file details separately.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/admin/class-bulk-library.php` around lines 47 - 52, Update
get_all_attachments() to avoid querying and returning the entire Media Library
in one request. Add server-side pagination with bounded query limits and an
offset/page parameter, returning only the requested attachment details while
preserving the existing response contract; if aggregate counts are needed,
provide them separately rather than materializing every attachment.

Comment on lines +61 to +65
AND (
p.post_mime_type LIKE %s
OR p.post_mime_type LIKE %s
OR p.post_mime_type LIKE %s
)

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

Include attachments with an empty stored MIME so extension fallback can run.

The SQL excludes rows without an image/, video/, or audio/ MIME before resolveAttachmentMimeType() sees them. Consequently, the promised extension fallback cannot recover attachments whose post_mime_type is empty.

Proposed fix
 					AND (
 						p.post_mime_type LIKE %s
 						OR p.post_mime_type LIKE %s
 						OR p.post_mime_type LIKE %s
+						OR p.post_mime_type = ''
+						OR p.post_mime_type IS NULL
 					)
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
AND (
p.post_mime_type LIKE %s
OR p.post_mime_type LIKE %s
OR p.post_mime_type LIKE %s
)
AND (
p.post_mime_type LIKE %s
OR p.post_mime_type LIKE %s
OR p.post_mime_type LIKE %s
OR p.post_mime_type = ''
OR p.post_mime_type IS NULL
)
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/admin/class-bulk-library.php` around lines 61 - 65, Update the MIME-type
filter in the bulk library query to also allow attachments with an empty stored
post_mime_type, so they reach resolveAttachmentMimeType() for extension-based
resolution. Preserve the existing image/, video/, and audio/ MIME matches.

Comment thread src/admin/js/bulk-optimizer/bulk-optimization-upsell.js Outdated
Comment on lines +52 to +65
{ !! skipped && (
<div
role="button"
tabIndex={ 0 }
className="cimo-bulk-optimizer-skipped-label"
onClick={ onSkippedClick }
onKeyDown={ e => {
if ( e.key === 'Enter' || e.key === ' ' ) {
e.preventDefault()
onSkippedClick?.()
}
} }
title={ __( 'View skipped files', 'cimo-image-optimizer' ) }
>

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

Do not expose button semantics when onSkippedClick is absent.

The free upsell omits this callback, but skipped results still render a focusable “View skipped files” button that does nothing. Render plain text unless a handler exists, or disable the control explicitly.

Proposed approach
-				<div
-					role="button"
-					tabIndex={ 0 }
+				<div
+					role={ onSkippedClick ? 'button' : undefined }
+					tabIndex={ onSkippedClick ? 0 : undefined }
 					className="cimo-bulk-optimizer-skipped-label"
 					onClick={ onSkippedClick }
 					onKeyDown={ e => {
+						if ( ! onSkippedClick ) {
+							return
+						}
 						if ( e.key === 'Enter' || e.key === ' ' ) {
 							e.preventDefault()
-							onSkippedClick?.()
+							onSkippedClick()
 						}
 					} }
-					title={ __( 'View skipped files', 'cimo-image-optimizer' ) }
+					title={ onSkippedClick ? __( 'View skipped files', 'cimo-image-optimizer' ) : undefined }
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
{ !! skipped && (
<div
role="button"
tabIndex={ 0 }
className="cimo-bulk-optimizer-skipped-label"
onClick={ onSkippedClick }
onKeyDown={ e => {
if ( e.key === 'Enter' || e.key === ' ' ) {
e.preventDefault()
onSkippedClick?.()
}
} }
title={ __( 'View skipped files', 'cimo-image-optimizer' ) }
>
{ !! skipped && (
<div
role={ onSkippedClick ? 'button' : undefined }
tabIndex={ onSkippedClick ? 0 : undefined }
className="cimo-bulk-optimizer-skipped-label"
onClick={ onSkippedClick }
onKeyDown={ e => {
if ( ! onSkippedClick ) {
return
}
if ( e.key === 'Enter' || e.key === ' ' ) {
e.preventDefault()
onSkippedClick()
}
} }
title={ onSkippedClick ? __( 'View skipped files', 'cimo-image-optimizer' ) : undefined }
>
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/admin/js/bulk-optimizer/bulk-optimizer-stats.js` around lines 52 - 65,
Update the skipped-results control around onSkippedClick so it only exposes
button semantics and keyboard focusability when a handler exists. When
onSkippedClick is absent, render the skipped label as non-interactive plain text
without click or keydown behavior; preserve the existing interactive behavior
when the callback is provided.

Comment thread src/shared/bulk-stats.js Outdated

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 5

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/admin/class-admin-notices.php`:
- Around line 302-317: Update the notice heading around
Cimo_Stats::get_additional_savings_estimate_label() so it does not claim
unoptimized images exist when the savings label is empty. Reuse the existing
$savings_label condition to show generic copy for an empty estimate, while
preserving the current unoptimized-image heading when a savings estimate is
available.

In `@src/admin/class-stats.php`:
- Around line 220-222: Align both savings estimators to the same
attachment-based unit model: update src/admin/class-stats.php lines 220-222 and
src/shared/estimate-additional-savings.js lines 33-35 to calculate savings from
unoptimized bytes or an attachment-based unoptimized count, preserving identical
results between the PHP and JavaScript implementations.
- Around line 253-274: Update update_stats_upload_optimized to make
per-attachment accounting idempotent or otherwise synchronize the option
read-modify-write so overlapping uploads cannot lose totals. Establish
last_processed_post_id from the existing scan baseline before allowing this
method to advance it, and only advance the cursor when doing so cannot skip
older unscanned metadata. Preserve totals and cursor updates across concurrent
and initially missing-option updates.

In `@src/admin/css/admin-page.css`:
- Line 96: Update the default link color declaration in the admin page
stylesheet from `#3c83f6` to the existing darker focus color or another shade that
provides at least 4.5:1 contrast against white for 13px text.

In `@src/admin/js/bulk-optimizer/use-bulk-progress-stats.js`:
- Line 18: Add descriptive return text to the JSDoc annotations for both
affected hooks, including the one near the `80` reference, while preserving
their existing return types and documenting the returned progress statistics
object.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 436dd4b2-4596-4368-8fe4-6f28f8cec20d

📥 Commits

Reviewing files that changed from the base of the PR and between 28dff2a and d3b0c16.

📒 Files selected for processing (11)
  • src/admin/class-admin-notices.php
  • src/admin/class-admin.php
  • src/admin/class-bulk-library.php
  • src/admin/class-metadata.php
  • src/admin/class-stats.php
  • src/admin/css/admin-page.css
  • src/admin/js/bulk-optimizer/bulk-optimization-upsell.js
  • src/admin/js/bulk-optimizer/use-bulk-progress-stats.js
  • src/admin/js/page/admin-settings.js
  • src/admin/js/page/premium-savings-estimate.js
  • src/shared/estimate-additional-savings.js
💤 Files with no reviewable changes (1)
  • src/admin/class-admin.php

Comment thread src/admin/class-admin-notices.php
Comment thread src/admin/class-stats.php Outdated
Comment on lines +220 to +222
$avg_original_kb = $original_kb / $optimized;
$unoptimized_original_kb = $avg_original_kb * $unoptimized;
$savings_kb = $unoptimized_original_kb * ( $reduction / 100 );

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🎯 Functional Correctness | 🟠 Major | 🏗️ Heavy lift

Align the unit basis of both savings estimators.

Bulk progress counts each full file and generated image size, while stored upload statistics primarily count and size attachments. Applying the attachment-sized average to the larger per-size count inflates the upsell estimate.

  • src/admin/class-stats.php#L220-L222: derive savings from unoptimized bytes or an attachment-based unoptimized count.
  • src/shared/estimate-additional-savings.js#L33-L35: apply the same corrected unit model so PHP and JavaScript remain consistent.
📍 Affects 2 files
  • src/admin/class-stats.php#L220-L222 (this comment)
  • src/shared/estimate-additional-savings.js#L33-L35
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/admin/class-stats.php` around lines 220 - 222, Align both savings
estimators to the same attachment-based unit model: update
src/admin/class-stats.php lines 220-222 and
src/shared/estimate-additional-savings.js lines 33-35 to calculate savings from
unoptimized bytes or an attachment-based unoptimized count, preserving identical
results between the PHP and JavaScript implementations.

Comment thread src/admin/class-stats.php
Comment on lines +253 to +274
public static function update_stats_upload_optimized( $attachment_id, $original_size, $optimized_size ) {
$stats = get_option( self::OPTION_KEY );
if ( ! is_array( $stats ) ) {
$stats = [
'last_processed_post_id' => 0,
'media_optimized_num' => 0,
'total_original_size' => 0,
'total_optimized_size' => 0,
];
}

$stats['media_optimized_num'] = (int) ( $stats['media_optimized_num'] ?? 0 ) + 1;
$stats['total_original_size'] = (float) ( $stats['total_original_size'] ?? 0 ) + ( (int) $original_size / 1024 );
$stats['total_optimized_size'] = (float) ( $stats['total_optimized_size'] ?? 0 ) + ( (int) $optimized_size / 1024 );

// Advance the cursor so a later incremental scan does not double-count this file.
$attachment_id = (int) $attachment_id;
if ( $attachment_id > (int) ( $stats['last_processed_post_id'] ?? 0 ) ) {
$stats['last_processed_post_id'] = $attachment_id;
}

update_option( self::OPTION_KEY, $stats, false );

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🗄️ Data Integrity & Integration | 🟠 Major | 🏗️ Heavy lift

Make upload-stat updates atomic and cursor advancement lossless.

Overlapping uploads can read the same option and overwrite each other, losing totals. The winning write may then advance last_processed_post_id beyond lost or previously unscanned records, preventing later scans from recovering them. Initializing the option from one new upload similarly skips older Cimo metadata.

Use idempotent per-attachment accounting or synchronize updates and establish the scan baseline before advancing the cursor.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/admin/class-stats.php` around lines 253 - 274, Update
update_stats_upload_optimized to make per-attachment accounting idempotent or
otherwise synchronize the option read-modify-write so overlapping uploads cannot
lose totals. Establish last_processed_post_id from the existing scan baseline
before allowing this method to advance it, and only advance the cursor when
doing so cannot skip older unscanned metadata. Preserve totals and cursor
updates across concurrent and initially missing-option updates.

font-size: 13px;
font-weight: 600;
line-height: 1.3;
color: #3c83f6;

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Use a darker default link color.

#3c83f6 on white is approximately 3.6:1, below the 4.5:1 requirement for 13px text. Use the existing darker focus color or another compliant shade.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/admin/css/admin-page.css` at line 96, Update the default link color
declaration in the admin page stylesheet from `#3c83f6` to the existing darker
focus color or another shade that provides at least 4.5:1 contrast against white
for 13px text.

Comment thread src/admin/js/bulk-optimizer/use-bulk-progress-stats.js Outdated
@bfintal bfintal self-assigned this Jul 17, 2026
@bfintal
bfintal requested a review from Arukuen July 17, 2026 13:50
@github-actions

github-actions Bot commented Jul 17, 2026

Copy link
Copy Markdown

🤖 Pull request artifacts

file commit
pr66-cimo-66-merge.zip 76a844c

github-actions Bot added a commit that referenced this pull request Jul 17, 2026
So CI fails at the package step instead of continuing and failing later when dist/ is missing.

Co-authored-by: Cursor <cursoragent@cursor.com>
github-actions Bot added a commit that referenced this pull request Jul 18, 2026
github-actions Bot added a commit that referenced this pull request Jul 18, 2026
github-actions Bot added a commit that referenced this pull request Jul 18, 2026
github-actions Bot added a commit that referenced this pull request Jul 18, 2026
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