PHPackages                             soderlind/custom-document-folder - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Utility &amp; Helpers](/categories/utility)
4. /
5. soderlind/custom-document-folder

ActiveWordpress-plugin[Utility &amp; Helpers](/categories/utility)

soderlind/custom-document-folder
================================

WordPress plugin that organizes document uploads by file type

1.1.1(5mo ago)3447↑50%[1 PRs](https://github.com/soderlind/custom-document-folder/pulls)GPL-2.0-or-laterPHPPHP &gt;=8.3CI passing

Since Nov 24Pushed 3mo agoCompare

[ Source](https://github.com/soderlind/custom-document-folder)[ Packagist](https://packagist.org/packages/soderlind/custom-document-folder)[ Fund](https://paypal.me/PerSoderlind)[ RSS](/packages/soderlind-custom-document-folder/feed)WikiDiscussions main Synced 1mo ago

READMEChangelog (4)Dependencies (4)Versions (8)Used By (0)

Custom Document Folder
======================

[](#custom-document-folder)

Organize document uploads by automatically directing specific file types to custom folders based on their extensions.

Description
-----------

[](#description)

Custom Document Folder automatically organizes your WordPress media uploads by directing specific document types to dedicated folders. Instead of having all files mixed together in date-based folders, you can configure which file extensions should be uploaded to their own organized folders.

Features
--------

[](#features)

- ✨ **Modern Settings Interface** - Beautiful grid-based UI with search functionality
- 📁 **Category Organization** - Extensions grouped by type (Documents, Images, Video, Audio, Archives, etc.)
- 🔍 **Live Search** - Filter extensions and categories in real-time
- ⚡ **Bulk Actions** - Select/deselect all visible extensions at once
- 🎯 **Collapsible Categories** - Media categories (Audio, Images, Video, Other) hidden by default
- 🔢 **Live Counter** - See how many extensions are selected
- 📂 **Custom Folder Routing** - Each extension gets its own folder (e.g., `/pdf/`, `/docx/`, `/xlsx/`)
- 🔒 **Security Focused** - Input sanitization with `sanitize_text_field()`
- ✅ **MIME Type Validation** - Only allows file types that WordPress already permits
- 🔄 **Backward Compatible** - Existing files remain in their original locations
- 📄 **PDF Default** - Comes pre-configured with PDF support
- 🗑️ **Non-unique Filename Handling** - Automatically removes old attachments when re-uploading

Installation
------------

[](#installation)

- **Quick Install**

    - Download [`custom-document-folder.zip`](https://github.com/soderlind/custom-document-folder/releases/latest/download/custom-document-folder.zip)
    - Upload via Plugins &gt; Add New &gt; Upload Plugin
    - Activate the plugin.
    - Go to **Settings &gt; Document Folder** to configure
- **Composer Install**

    ```
    composer require soderlind/custom-document-folder
    ```
- **Updates**

    - Plugin [updates are handled automatically](https://github.com/soderlind/wordpress-plugin-github-updater#readme) via GitHub. No need to manually download and install updates.

Usage
-----

[](#usage)

1. Navigate to **Settings &gt; Document Folder**
2. Check the extensions you want to organize (PDF is pre-selected)
3. Use the search box to quickly find specific extensions
4. Click **"Show More Categories"** to see audio, image, and video extensions
5. Click **"Select All"** or **"Deselect All"** for bulk actions
6. Save your settings
7. New uploads of selected types will automatically go to their designated folders

### Example

[](#example)

If you select `pdf` and `docx` extensions:

- PDF files upload to → `/wp-content/uploads/pdf/`
- DOCX files upload to → `/wp-content/uploads/docx/`
- Other files continue uploading to standard date-based folders

Requirements
------------

[](#requirements)

- **WordPress:** 6.7 or higher
- **PHP:** 8.3 or higher
- **PHP Extensions:** None required beyond standard WordPress requirements

Frequently Asked Questions
--------------------------

[](#frequently-asked-questions)

### What happens to files uploaded before activating the plugin?

[](#what-happens-to-files-uploaded-before-activating-the-plugin)

They remain in their original locations. This plugin only affects new uploads after you configure and save your settings.

### Can I select multiple file extensions?

[](#can-i-select-multiple-file-extensions)

Yes! Select as many extensions as you need. The counter shows how many are currently selected.

### Will this break my existing media library?

[](#will-this-break-my-existing-media-library)

No. Existing files stay where they are. Only new uploads of selected extensions are redirected to custom folders.

### Does this work with multisite?

[](#does-this-work-with-multisite)

Yes. Each site in a multisite installation can configure its own extensions independently.

### Can I organize images and videos too?

[](#can-i-organize-images-and-videos-too)

Yes! Click "Show More Categories" to reveal and select image, video, and audio extensions. However, some themes and plugins expect images in date-based folders.

Development
-----------

[](#development)

### Architecture

[](#architecture)

```
custom-document-folder/
├── custom-document-folder.php  # Main plugin file
├── tests/
│   ├── TestCase.php           # Base test class
│   ├── SettingsTest.php       # Settings tests
│   ├── UploadTest.php         # Upload tests
│   ├── cdf-filter-test.php    # WP-CLI filter test
│   └── TEST-RESULTS.md        # Test documentation
├── composer.json              # Composer configuration
├── phpunit.xml.dist          # PHPUnit configuration
├── CHANGELOG.md              # Version history
└── README.md                 # This file

```

### WordPress Hooks

[](#wordpress-hooks)

The plugin uses these WordPress hooks:

- `upload_dir` (priority 20) - Modifies upload directory path
- `wp_handle_upload_prefilter` - Captures file extension early
- `wp_check_filetype_and_ext` - Validates file types
- `wp_handle_upload_overrides` - Handles non-unique filenames
- `sanitize_file_name` - Removes old attachments

### Code Standards

[](#code-standards)

- PHP 8.3 with strict types and namespaces
- WordPress Coding Standards compliant
- PHPUnit test coverage
- Brain Monkey for WordPress function mocking
- Namespace: `Soderlind\DocumentFolder`

### Testing

[](#testing)

#### Run PHPUnit Tests

[](#run-phpunit-tests)

```
# Install dependencies
composer install

# Run tests
composer test

# Run with coverage
composer test:coverage
```

#### Run WP-CLI Filter Tests

[](#run-wp-cli-filter-tests)

```
wp eval-file wp-content/plugins/custom-document-folder/tests/cdf-filter-test.php
```

#### Test Results

[](#test-results)

```
PHPUnit 9.6.29
OK (7 tests, 21 assertions)

```

All core functionality verified:

- ✅ Settings sanitization
- ✅ Invalid input handling
- ✅ XSS protection
- ✅ PDF upload path modification
- ✅ Non-selected files use default path
- ✅ Multiple extension handling
- ✅ File type validation

Contributing
------------

[](#contributing)

Contributions are welcome! Please follow these guidelines:

1. Fork the repository
2. Create a feature branch (`git checkout -b feature/amazing-feature`)
3. Commit your changes (`git commit -m 'Add amazing feature'`)
4. Push to the branch (`git push origin feature/amazing-feature`)
5. Open a Pull Request

### Development Setup

[](#development-setup)

```
# Clone repository
git clone https://github.com/soderlind/custom-document-folder.git
cd custom-document-folder

# Install dependencies
composer install

# Run tests
composer test
```

Changelog
---------

[](#changelog)

See [CHANGELOG.md](CHANGELOG.md) for version history.

Support
-------

[](#support)

- **GitHub Issues:** [Report bugs or request features](https://github.com/soderlind/custom-document-folder/issues)
- **WordPress Support:** [Plugin support forum](https://wordpress.org/support/plugin/custom-document-folder/)

License
-------

[](#license)

This plugin is licensed under the GPL v2 or later.

```
Copyright (C) 2025 Per Soderlind

This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

```

Author
------

[](#author)

**Per Soderlind**

- Website: [soderlind.no](https://soderlind.no)
- GitHub: [@soderlind](https://github.com/soderlind)
- Twitter: [@soderlind](https://twitter.com/soderlind)

Credits
-------

[](#credits)

Built with:

- [WordPress Settings API](https://developer.wordpress.org/plugins/settings/)
- [PHPUnit](https://phpunit.de/)
- [Brain Monkey](https://brain-wp.github.io/BrainMonkey/)
- [Composer](https://getcomposer.org/)

---

Made with ❤️ for the WordPress community

###  Health Score

42

—

FairBetter than 90% of packages

Maintenance75

Regular maintenance activity

Popularity19

Limited adoption so far

Community6

Small or concentrated contributor base

Maturity55

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~0 days

Total

4

Last Release

173d ago

### Community

Maintainers

![](https://avatars.githubusercontent.com/u/1649452?v=4)[Per Søderlind](/maintainers/soderlind)[@soderlind](https://github.com/soderlind)

---

Top Contributors

[![soderlind](https://avatars.githubusercontent.com/u/1649452?v=4)](https://github.com/soderlind "soderlind (10 commits)")

---

Tags

uploadswordpress-plugin

###  Code Quality

TestsPHPUnit

### Embed Badge

![Health badge](/badges/soderlind-custom-document-folder/health.svg)

```
[![Health](https://phpackages.com/badges/soderlind-custom-document-folder/health.svg)](https://phpackages.com/packages/soderlind-custom-document-folder)
```

###  Alternatives

[10up/10up-experience

The 10up Experience plugin configures WordPress to better protect and inform clients, aligned to 10up's best practices

139477.6k](/packages/10up-10up-experience)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
