Tender Library self-updates
Library plugin for wordpress
Install
No release zip yet. The repository archive installs, but the folder name will carry the branch suffix and updates will not flow:
wp plugin install https://github.com/lopandpe/tender-a-library/archive/refs/heads/main.zipShips its own WordPress updater (Update URI header), so new versions show up under Dashboard → Updates.
Private WordPress plugin for small local libraries. It provides book/event custom post types, Carbon Fields metadata, lending and reservation workflows, user/profile pages, search blocks, event feeds, email reminders, and CSV migration tools.
This plugin is not distributed through WordPress.org. The first install is done manually from a ZIP file. Future releases are delivered through a private update metadata endpoint and can be installed from the WordPress dashboard.
Requirements
- WordPress 6.4 or newer
- PHP 8.1 or newer
- Composer for PHP dependency installation during release builds
- Node/npm for asset builds during development/release
Important Slug Details
The distributed plugin slug is:
tender-library
The distributed main plugin file is:
tender-library.php
Release ZIPs must contain this top-level folder:
tender-library/
The plugin header includes Update URI: https://example.com/tender-library. This prevents WordPress from matching this private plugin with any WordPress.org plugin that might use the same slug.
Local Development
Install PHP dependencies:
composer install
Install JS dependencies and build assets:
npm install
npm run build
Useful asset commands:
npm run build
npm run build:blocks
npm run webpack
npm run start:blocks
npm run webpack:watch
Private Update Configuration
The private update metadata URL is defined in tender-library.php:
define('TENDER_LIBRARY_UPDATE_METADATA_URL', 'https://example.com/tender-library/update.json');
It can be changed without editing plugin files:
add_filter('tender_library_update_metadata_url', function () {
return 'https://your-domain.example/tender-library/update.json';
});
The default placeholder must be replaced before production distribution.
update.json Format
A minimal metadata file looks like this:
{
"name": "Tender Library",
"slug": "tender-library",
"version": "1.0.1",
"download_url": "https://example.com/tender-library/releases/tender-library-1.0.1.zip",
"requires": "6.4",
"tested": "6.6",
"requires_php": "8.1",
"last_updated": "2026-06-02",
"homepage": "https://example.com/tender-library",
"author": "Luis Gómez",
"sections": {
"description": "Private library/tender management plugin.",
"changelog": "<h4>1.0.1</h4><ul><li>Describe changes here.</li></ul>"
}
}
An example lives in update.example.json.
Creating a Production ZIP
- Update the plugin version in
tender-library.php:- plugin header
Version TENDER_LIBRARY_VERSION
- plugin header
- Update
CHANGELOG.md. - Install production PHP dependencies:
composer install --no-dev --optimize-autoloader
- Build final assets:
npm ci
npm run build
- Build the release ZIP:
./build-release.sh 1.0.0
The script creates:
tender-library-1.0.0.zip
The ZIP contains a top-level tender-library/ folder and excludes development files such as .git, node_modules, src, SCSS sources, test/config files, temp files, documentation, and release scripts.
Publishing a New Version
Example for 1.0.1:
- Update
VersionandTENDER_LIBRARY_VERSIONto1.0.1intender-library.php. - Update
CHANGELOG.md. - Run:
composer install --no-dev --optimize-autoloader
npm ci
npm run build
./build-release.sh 1.0.1
- Upload the ZIP to:
https://example.com/tender-library/releases/tender-library-1.0.1.zip
- Update and upload
update.jsonto:
https://example.com/tender-library/update.json
- In a WordPress installation with the plugin already installed, go to:
WordPress Admin > Dashboard > Updates
or:
WordPress Admin > Plugins
- Confirm that Tender Library shows the update and install it from the dashboard.
First Manual Installation
- Build
tender-library-1.0.0.zip. - In WordPress Admin, go to
Plugins > Add New > Upload Plugin. - Upload the ZIP.
- Activate Tender Library.
- Go to
Settings > Permalinksand clickSave Changesonce. - Confirm the plugin creates its library pages/tables and the admin menu appears for allowed roles.
How Dashboard Updates Work
The plugin registers a private updater class in includes/class-tender-library-updater.php.
It:
- Fetches update metadata with
wp_remote_get(). - Caches valid metadata in a site transient.
- Validates and sanitizes remote fields before use.
- Compares remote and installed versions with
version_compare(). - Injects update data into WordPress' plugin update transient.
- Supports the plugin details modal through the
plugins_apifilter. - Fails silently if the update server is unreachable or returns invalid JSON.
Version Storage and Migrations
The source of truth for runtime code is:
define('TENDER_LIBRARY_VERSION', '1.0.0');
The plugin stores the installed version in:
tender_library_version
Current migration logic only records the installed version. Add version-gated migrations there when schema/data changes are needed.
Manual Test Checklist
See docs/release-checklist.md.
Notes
- Do not commit real license keys, tokens, server credentials, or private endpoint secrets.
- Replace
https://example.com/tender-librarybefore distributing production builds. - Keep the ZIP folder name, plugin slug, and update metadata slug as
tender-library.