Attachments
Where files are saved, what types are allowed, the size and count limits, what customers can and can’t upload, and how the plugin keeps uploads safe on disk.
Where do attachments live on disk?
All uploads go to wp-content/uploads/order-updates-for-woo/ on your own server. The folder is created on the first upload. Inside, each file is saved with a random filename (the original name is kept only in the database, never on disk), and the folder includes an .htaccess file plus an empty index.html to stop the contents being listed publicly.
The details for each file — original name, MIME type, size, who uploaded it, which update and note it belongs to — live in the {prefix}order_updates_for_woo_attachments table. The disk file holds the actual content; the database row links it to your data.
Which file types can be uploaded?
By default: PNG, JPG, GIF, WebP, PDF, plain text, CSV, ZIP, and a few common Office formats (DOCX, XLSX). The full default list is on Settings — Attachments.
You can change which types are allowed under Settings → Attachments → Allowed file types. Pick from the dropdown of every type the plugin knows about, or add custom MIME types with the order_updates_for_woo_default_mime_types filter (for add-ons that need to allow site-specific formats).
How big can a file be, and how many per note?
Two limits, both editable under Settings → Attachments:
- Max file size per upload — default 10 MB. Setting this higher than your PHP
upload_max_filesizeor your web server’s body-size limit won’t help — the upload will fail at the host level before the plugin sees it. - Max files per note — default 5. Both staff and customers share this limit. The upload area blocks adding a sixth file before you post.
If you raise the file size limit, also raise your hosting’s PHP and Nginx/Apache limits to match. Otherwise the form will accept the file in the browser and then fail on the server, which is a confusing error for users.
Can customers upload files too?
Yes. If attachments are turned on, the customer’s reply box in the portal has the same drag-and-drop upload area your team gets. The same allowed-types list, max size, and max files apply to both staff and customers — there’s no separate “customer files” setting.
Customers can drop, drag, or paste images directly into the reply box (paste-from-clipboard works for screenshots). Each file is checked for double-extension tricks (e.g. invoice.pdf.exe) and rejected before upload if the type doesn’t match what the file claims.
Can someone guess the file URL and download it?
No — or at least, guessing isn’t the way in. The file’s name on disk is a random 32-character string, so a guessed URL won’t match anything. But the bigger point is that direct disk URLs aren’t the way files are served at all: every download goes through the /wp-json/order-updates-for-woo/v1/attachment/{id} REST endpoint, which checks the user’s permission to see the parent update before sending the file back.
Staff need the order capability; customers need to be logged in as the order owner or have a valid order_key. Either way, the permission check happens before any file content leaves your server.
What happens to attachments when I delete an update?
Both the database rows and the files on disk are removed in the same step. Deleting an update goes through every note on the update, finds every attachment row for those notes, deletes the row, and removes the file from disk. After it’s done, nothing about that update is left — in the database or on the filesystem.
The same happens when you delete a single note: every attachment that belongs to that note is removed cleanly. No leftover files to worry about.
What if I find empty folders left over from old updates?
The plugin runs a cleanup task once a day that removes any per-update folder with no files inside. So even if a deletion left an empty folder behind in an older version, the cleanup will catch up within 24 hours.
If you want to clean up right away, deactivate and reactivate the plugin — activation runs the same cleanup at the start, so empty folders are gone on the next request.
How do staff or customers delete a file?
Hover the attachment in the note bubble and click the small trash icon. A confirm dialog shows up before the file is actually deleted — once you confirm, both the database row and the disk file are removed and the note redraws without that attachment.
Staff can delete any attachment on any update they have access to. Customers can only delete attachments they uploaded themselves, and only on customer notes they wrote.
Should I include the attachments folder in my site backups?
Yes — treat it the same way you treat wp-content/uploads/ in general. The folder holds the actual files for every customer screenshot, PDF, and document attached to an update. Without it, restoring a backup would leave you with a database that points to missing files.
Most well-known WordPress backup plugins include all of wp-content/uploads/ by default, so unless you’ve added an exclude rule, you’re already covered.
How does the “safe file check” work?
On every upload, before the file is moved into the attachments folder, the plugin runs WordPress’s wp_check_filetype_and_ext — the same check WordPress uses for Media Library uploads. It looks at the file’s actual MIME type (by reading the first few bytes) and makes sure it matches what the file extension claims. If they don’t match, the upload is rejected.
It also blocks files with double extensions (image.gif.php, doc.pdf.exe) and files whose extension isn’t in your allowed list. The goal isn’t to be a full virus scanner — if you need that, run one at the host level — but to make the common attacker tricks fail on their own.
Can I disable attachments entirely?
Yes — set Max files per note to 0 under Settings → Attachments. The upload area is hidden from every reply box (staff and customer), the REST upload endpoint rejects all calls, and existing attachments stay viewable but no new ones can be added.
This is useful for stores on hosting with strict rules where the upload feature is more risk than benefit. Customers can still describe issues in text, and your team can still send screenshots through a separate channel if needed.
What types are blocked even when I add them to “allowed”?
Code-runnable file types are blocked by WordPress itself, no matter what the “allowed file types” setting says: .php, .phtml, .exe, .js (as a hosted file), .sh, and similar. WordPress’s own upload check rejects them, and the plugin doesn’t override that. So even if you somehow get application/x-php into the allowed list, the upload will still be rejected by WordPress.
This is on purpose — letting people upload code into a public uploads folder would be a serious security hole.