Releases: inalto/mm-optimizer
Release list
MM Optimizer 1.1.0
Reliability release: the bulk queue now recovers on its own from a worker that dies mid-batch, and the plugin says clearly when visitors are not being served the converted images.
Restartable bulk queue
On a busy library the queue could stall with no way to restart it. The cause was PHP's time limit. On Linux it counts CPU time, and multithreaded AVIF encoding uses it about five times faster than the wall clock (one 12 MP photo: 1.3 s wall, 7 s CPU). A batch sized to fit in 30 seconds of wall time could run through 50 seconds of CPU and be killed. It then left the lock held for five minutes and its rows blocked for ten.
- The time limit is restarted before every file, so the limit is not reached in the first place.
- When a worker does die, it releases its rows and the lock and starts the next worker. This works even through WordPress's own fatal-error handler, which exits before later shutdown functions get a chance to run.
- Only the file being worked when the worker died counts as a failed attempt. A file that kills the worker three times leaves the queue, and the log names it.
- The lock doubles as a heartbeat: two minutes without one means the worker is dead, whatever the transient says.
- The Bulk tab shows Resume (N queued) for a leftover queue instead of making you rescan the library, and says when the queue has gone idle.
- The browser runner retries failed batches for about three minutes instead of stopping at the first error.
"Image delivery is off" notice
Conversion runs whether or not delivery is on, so it was easy to convert a whole library and never notice visitors were still getting the original JPEGs. A red notice now appears on the MM Optimizer screens, the dashboard and the media library. It gives the number of derivatives that are ready but not being served, and why:
- A conflicting plugin is active. Delivery is held back, and it now switches on by itself once that plugin is deactivated.
- The mode is set to No delivery. This setting stays until you change it.
In 1.0.0, applying the recommended configuration while a conflicting plugin was active saved No delivery. The message said delivery would switch itself back on; it never did. The recommendation now leaves the mode alone and lets conflict detection hold delivery back. If you applied it on 1.0.0, pick a delivery mode by hand; the notice links straight to the setting.
Fixes
- The Bulk tab's Derivatives generated and Space saved counters always read zero on MySQL 8, because
OUTis a reserved word.
Upgrading
Upload over 1.0.0. No schema change. An existing queue is picked up by Resume.
MM Optimizer 1.0.0
First release.
MM Optimizer starts from a question most image plugins skip: what can this
server actually do? It runs a detection pass, shows a capability matrix built
from real encoding tests, and recommends a configuration with the reason next to
every choice.
Original files are never modified.
Highlights
Detection that does not trust declared support. Imagick::queryFormats()
lists WEBP even when the delegate is broken; a cwebp on the PATH is
sometimes a placeholder script. Both report success to a naive check and then
produce corrupted files in silence. For every library and format, MM Optimizer
encodes a known sample, checks the magic bytes, verifies the size is plausible,
and reads the result back. A format that is claimed but not verified stays
disabled, and the diagnostics screen says why.
Engine ranking on the right sample. Verification uses a 64×64 probe;
ranking uses a 512×384 photograph, because the two questions are different. On
the small probe cwebp -m 6 comes out two bytes larger than -m 4; on the
photograph it is 7% smaller. Ranking on the wrong sample picks the wrong engine.
There is no hand-written preference table — whichever engine produces the
smallest file on your server wins.
Recommendations with reasons. Every proposed setting carries the measurement
or condition behind it, including the unwelcome ones: if your host has no
lossless JPEG tool, it says so and names the package to ask for rather than
pretending.
The AVIF MIME-type trap, handled. <source type="image/avif"> is a hint the
browser trusts before fetching. On a server whose MIME list predates AVIF, the
file comes back as application/octet-stream and Firefox and Safari fail with
no fallback to the <img>. The plugin probes this with a real request, writes
an AddType line, and if it cannot, disables AVIF delivery rather than ship
something half your visitors cannot display.
What it does
- Detects GD, Imagick, Gmagick and system binaries (cwebp, avifenc, jpegoptim, jpegtran, optipng, pngquant, gifsicle)
- Generates WebP and AVIF derivatives across four optimization levels
- Delivers responsively with
<picture>and onesrcsetper format, or via.htaccessnegotiation - Stands down when another optimizer is active — conversion keeps running, delivery switches off
- Imports settings and existing files from Converter for Media
- Browser-driven bulk conversion that survives unreliable WordPress cron
Measured results
On a 2048×1367 photograph of 721,366 bytes at the Balanced level:
| Format | Size | Saving |
|---|---|---|
| AVIF | 244,780 B | −66.1% |
| WebP | 380,730 B | −47.2% |
Requirements
WordPress 6.0+, PHP 7.4+, and GD or Imagick with WebP and/or AVIF support. The
plugin tells you what you have and what to request if you have neither.
Installation
Download mm-optimizer.zip below and upload it through Plugins → Add New →
Upload Plugin. See the wiki for
setup, and docs/ for
the technical reference.
Language
Source strings are English; an Italian translation ships in languages/.
Known limitations
- Multisite is untested rather than supported.
- Wrapping images in
<picture>breaks CSS written with direct-child selectors
(.gallery > img). Use the exclusion list or.htaccessmode.