Tidy Media

Beskriuwing

Tidy Media finds and removes unused images, videos, and other media files cluttering your WordPress Media Library. Files are moved to a quarantine folder before deletion, so you can restore anything that turns out to still be in use.

Page builder support, WooCommerce detection, and custom field scanning are all included with no feature gating.

Quarantine

Files are not deleted directly. They are moved to a quarantine folder where they remain for a configurable retention period (default 30 days). One-click restore brings the file back to its original location with all thumbnails intact. After the retention period files are automatically deleted, or you can clear the quarantine manually at any time.

Scanning

The scanner runs in two phases. First it collects every media reference it can find: post content, featured images, page builder data, WooCommerce products, custom fields, widgets, site options, and theme files. Then it compares every file in the Media Library against that list. Anything not found in any source is flagged as unused.

Scans run in batches with resource monitoring and can pause and resume, so they will not crash your site.

Page Builders

Elementor, Divi, Beaver Builder, WPBakery, and Bricks. Detects images used in widgets, modules, backgrounds, templates, and saved layouts. Builders that are not installed appear greyed out in the scan sources list.

WooCommerce

Product featured images, gallery images, variation images, category and tag thumbnails, and downloadable files.

Custom Fields

ACF, Meta Box, Pods, JetEngine, and Toolset Types. Image, file, gallery, and media fields in post meta, term meta, user meta, and option pages. Repeaters, groups, and flexible content layouts are walked.

Other

Filter results by file type, sort by size or upload date, and set a minimum file size for scans. Bulk actions for cleanup. CSV export of unused file lists. Detection of unregistered files (files in uploads/ without a Media Library entry, often left behind by backup or image optimization plugins).

100% Free

No pro version, no upsells. Every feature is included.

Skermôfbyldings

Ynstallaasje

  1. Upload the tidy-media folder to /wp-content/plugins/
  2. Activate the plugin through the Plugins menu in WordPress
  3. Go to Media > Tidy Media to start scanning
  4. Review the results and move unused files to quarantine
  5. Files in quarantine are automatically deleted after 30 days (configurable)

FAQ

Is it safe to delete unused media?

Yes. Tidy Media never deletes files directly from scan results. Files are first moved to a quarantine folder where they remain for 30 days (configurable). During this time, if you notice any missing images on your site, you can restore them with one click. Only after the retention period expires are files automatically deleted, or you can delete them manually from the Quarantine tab. All permanent delete actions require explicit confirmation.

How does the scanner decide what is “unused”?

The scanner works in two phases. First, it collects every media reference it can find across your site: post content, featured images, page builder data, WooCommerce products, custom fields, widgets, site options, and theme files. Then it compares every file in your Media Library against that list. If a file was not found in any scanned location, it is flagged as unused. See the “How It Works” tab in the plugin for full details.

Will this work with my page builder?

Tidy Media supports all major page builders: Elementor, Divi, Beaver Builder, WPBakery, and Bricks. The scanner detects images used in widgets, modules, backgrounds, templates, and saved layouts. Page builders that are not installed appear greyed out in the scan sources list so you can see what is supported.

Does it work with WooCommerce?

Yes. Tidy Media detects images used in WooCommerce product galleries, variation images, category thumbnails, downloadable product files, attribute images, brand images, and placeholder images.

Does it detect images in custom fields (ACF, Meta Box, Pods)?

Yes. Tidy Media supports five custom field plugins: ACF (Advanced Custom Fields), Meta Box, Pods, JetEngine, and Toolset Types. It scans image, file, gallery, and media fields in post meta, term meta, user meta, and ACF option pages. It also handles repeaters, groups, and flexible content layouts.

What if I accidentally delete an important image?

As long as the file is still in quarantine (within the retention period), you can restore it with one click. The file and all its thumbnails are moved back to their original location. If the WordPress attachment post was deleted while the file was in quarantine, a new one is automatically created with the original metadata.

What are “unregistered files”?

Unregistered files are files that exist in your wp-content/uploads/ directory but have no corresponding entry in the WordPress Media Library database. They are invisible to WordPress. Common sources include backup plugins (UpdraftPlus, BackWPup), image optimization backups (ShortPixel, Smush), cache files, and files left behind by uninstalled plugins. You can enable the “Scan for unregistered files” option to find and clean these up.

How long does scanning take?

It depends on the size of your Media Library and the number of posts on your site. A site with 1,000 media files typically takes 1-3 minutes. Large sites with 10,000+ files may take 10-30 minutes. The scan runs in batches and monitors server resources, so it will not crash your site. You can pause and resume at any time.

Does it handle WordPress-generated thumbnails?

When you upload an image, WordPress generates multiple sizes (thumbnail, medium, large, etc.). Tidy Media tracks the original file — if the original is used, all its thumbnails are automatically considered used too. When a file is quarantined or restored, all thumbnails are moved together. You can enable “Skip WordPress-generated thumbnails” in Settings to exclude auto-generated sizes from the results.

What happens if I deactivate the plugin?

Quarantined files remain safely on disk in wp-content/uploads/tidy-media-quarantine/. They are not deleted when the plugin is deactivated. If you uninstall (delete) the plugin and have “Delete all data” enabled in Settings, quarantined files and all plugin data will be permanently removed.

Will scanning affect my site performance?

No. The scan runs in small batches and monitors server resources (memory and execution time). It automatically pauses if resources are low and resumes after a brief cooldown. Your site remains fully operational during scanning.

Are there any limitations?

The scanner cannot detect images referenced only in custom plugin code (only theme files are scanned), external CSS/JS files, images loaded via custom PHP or AJAX, or media used only in email templates. This is why quarantine exists — always quarantine first and verify your site before permanently deleting.

Does it work on multisite?

The plugin scans the current site only. On multisite installations, activate it per-site and run scans on each site individually.

Resinsjes

D’r binne gjin resinsjes foar dizze plugin.

Meiwurkers & amp; Untwikkelders

“Tidy Media” is iepen boarne software. De folgjende minsken hawwe bydroegen oan dizze plugin.

Meiwurkers

Oersette “Tidy Media” yn jo taal.

Ynteressearre yn ûntwikkeling?

Blêdzje troch de koade , besjoch de SVN-repository , of abonnearje op it ûntwikkelingslogboek troch RSS .

Feroaringslog

1.0.13 – 2026-08-09

  • Fixed: Filesystem scan no longer flags the pristine originals of large images as unregistered files. WordPress keeps the untouched original next to the “-scaled” version it actually attaches (and keeps the original .heic for HEIC uploads, which convert to .jpg as of WordPress 7.0); these originals are now recognized so they can’t be quarantined by mistake.
  • Fixed: On sites that don’t organize uploads into month folders, generated thumbnails stored in the uploads root were wrongly flagged as unregistered files.
  • Fixed: Filesystem scan no longer flags the pre-edit originals kept by the WordPress image editor (_wp_attachment_backup_sizes) as unregistered files.
  • Fixed: URL matching now checks the raw filename as well as the size-stripped variant, so uploads with names like “logo-300×100.png” are no longer falsely flagged as unused.
  • Fixed: “Move All to Quarantine”, “Restore All”, “Delete All”, and “Empty Quarantine” no longer report a false “Could not process any files” error after completing successfully, and the list now refreshes.
  • Fixed: Quarantining a file whose quarantine slot is already occupied by an earlier quarantined file now stores the new file under a unique name instead of silently overwriting the old one.
  • Fixed: Raising the Quarantine Retention setting now extends the expiry of files already in quarantine; lowering it never shortens existing expiries.
  • Fixed: The Scanner tab “Deep scan” checkbox now reflects the saved setting instead of always being checked.
  • Fixed: Untranslated strings after refreshing dashboard stats and in the filtered-results empty state (localization key mismatches).
  • Fixed: Overlapping scan requests (a second admin tab, or a browser retry while the server was still working) can no longer corrupt scan progress or collected reference data — scan batches are now serialized with a lock.
  • Fixed: The options-table scan now processes all matching rows in batches instead of stopping after the first 500, so media referenced only in plugin or theme options (sliders, theme settings) is no longer flagged as unused on plugin-heavy sites.
  • Fixed: Media referenced only in protected (underscore-prefixed) custom fields — such as Yoast SEO Open Graph and Twitter images — is now detected by the deep scan instead of being flagged as unused.
  • Fixed: The unregistered-files scan no longer skips the rest of a folder when a batch ends mid-folder; large uploads folders are now scanned completely.
  • Fixed: On low-memory servers the scanner no longer hangs forever in a “Cooling down…” loop — it continues with the smallest batch size and shows a one-time warning instead.
  • Fixed: Restoring from quarantine now works after a site migration or uploads-directory move; the original location is stored relative to the uploads folder (older quarantined files keep their previous behavior).
  • Fixed: Quarantine expiry is now tracked in UTC everywhere, so auto-cleanup no longer deletes files hours before the shown expiry time on timezones ahead of UTC.
  • Fixed: URL matching now also resolves “-scaled” attachments referenced through sized URLs (photo-300×200.jpg photo-scaled.jpg), so large originals are no longer falsely flagged as unused.
  • Fixed: Same-named thumbnails from different attachments no longer overwrite each other in quarantine — colliding thumbnails get a unique stored name and are restored under their original name.
  • Fixed: If recording a quarantined file in the database fails, the file and its thumbnails are moved back instead of being stranded invisibly in the quarantine folder.
  • Fixed: Bulk actions that fail on every file (e.g. permission problems) now show the error reason instead of a “0 files” success toast.
  • Fixed: Reference collection pages the database deterministically, so posts published while a scan is running can no longer cause other references to be skipped.
  • Fixed: The “Skip WordPress-generated thumbnails” setting is now actually applied — when enabled, files that look like generated image sizes are excluded from unregistered-file results.
  • Fixed: All confirmation-dialog titles, buttons, and warnings are now translatable, and the delete dialogs no longer repeat the same warning twice.
  • New: “Empty Quarantine” button on the Quarantine tab — permanently deletes everything in quarantine regardless of the active search or filter, with a count-and-confirm dialog.
  • Security: The quarantine folder’s .htaccess now includes Apache 2.4 syntax (“Require all denied”) alongside the legacy 2.2 rules, and the protection files are re-created on every quarantine operation and on activation.
  • Security: Restoring from quarantine now validates that the destination resolves inside the uploads directory and refuses to overwrite an existing file at the original location (same for thumbnails).
  • Changed: The thumbnail badge is now an honest heuristic (“Filename matches a generated-thumbnail pattern. Verify before deleting.”) instead of claiming files are safe to delete and regenerable.
  • Changed: Bulk confirmation dialogs now state the exact number of files affected and whether the current search/filter limits the operation; the cancel-scan dialog has clear “Cancel Scan” / “Keep Scanning” buttons.
  • Changed: Clearer wording for the Scan Batch Size help text, the dashboard quarantine size stat, the stats empty state, and the readme feature list.
  • Cleanup: Removed debug HTML comments and console logging from the admin interface.
  • Compatibility: Tested with WordPress 7.0, WooCommerce 11.0 (incl. Action Scheduler 4.0) and PHP 8.5.

1.0.12 – 2026-05-27

  • Compatibility: Tested with WordPress 7.0 and WooCommerce 10.8.

1.0.11 – 2026-05-09

  • New: “More tools by WPCoreTools” tab listing the rest of our free, GPL toolkit (Email Verify, Disposable Email Guard, Speedix). Each entry shows whether it is already active on the site, with one-click activate links and Thickbox modal install for missing plugins.

1.0.10 – 2026-04-29

  • Removed: WP-Cron background scanning (use the in-page scanner with pause/resume)
  • Cleanup: Simplified readme and in-plugin “How It Works” copy

1.0.9 – 2026-04-27

  • Security: Hardened SQL preparation across the scanner, quarantine, and bulk actions
  • Stopped overriding the PHP time limit during scans so host settings are respected

1.0.8 – 2026-04-23

  • Compliance: Renamed internal prefix from tm_ / TM_ to tidymedia_ / TIDYMEDIA_ to satisfy the WordPress.org Plugin Review Team’s 4-character minimum. All AJAX actions, nonces, CSS classes, and HTML IDs updated accordingly. No user-facing behavior changes.

1.0.7 – 2026-04-17

  • Enhancement: Progress modal for Quarantine/Restore/Delete Selected — client-side batching with per-chunk progress instead of a silent spinner
  • Enhancement: Media Library Breakdown now shows size per file type in addition to count
  • Enhancement: Quarantine image preview is served with cleaned output buffers and explicit inline disposition so hosts with gzip handlers no longer return a broken-image icon
  • Performance: Stats refresh walks attachments in keyset-paginated batches of 2,000, keeping memory flat on 50k+ media libraries
  • Security: Hardened clipboard-copy fallback against XSS from unusual filenames
  • Security: Attachment metadata deserialization now blocks object instantiation (allowed_classes => false)

1.0.6 – 2026-04-16

  • Enhancement: Show image thumbnails in the Quarantine list instead of a generic icon (served through a protected preview endpoint)
  • Enhancement: Clear (×) button on all search inputs for quick reset

1.0.5 – 2026-04-16

  • Enhancement: Show original file location (wp-content/uploads/…) for each item in the Quarantine tab
  • Fix: Search by filename in the Quarantine tab now works (dead handler was suppressing the server-side search)

1.0.0 – 2025-04-11

  • Initial release
  • Two-phase scanner (collect references, then compare against Media Library)
  • Quarantine system with configurable retention (1-365 days, default 30)
  • One-click restore from quarantine with full metadata preservation
  • Page builder support: Elementor, Divi, Beaver Builder, WPBakery, Bricks
  • WooCommerce support: galleries, variations, categories, downloadable files
  • Custom field support: ACF, Meta Box, Pods, JetEngine, Toolset Types
  • Theme file scanning for hardcoded image URLs
  • Unregistered file detection with origin tagging
  • Deep scan mode for serialized data in post meta and options
  • Pause and resume support during scans
  • Resource monitoring with auto-pause to prevent server crashes
  • Server-side pagination, filtering, sorting, and search
  • Disk space check before quarantine operations
  • Minimum file size filter
  • CSV export of unused files
  • Visual dashboard with storage statistics