Purrfect Match
A WordPress plugin that shows any shelter's adoptable Petfinder pets in a beautiful, filterable grid — "Find your purr-fect match." Originally built for CJ Paws, it ships with generic defaults so any rescue can use it.
by Andrew Mayes · github.com/mayes/wp-purrfect-match · website
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/mayes/wp-purrfect-match/archive/refs/heads/main.zip
A WordPress plugin that shows your shelter's adoptable Petfinder pets in a beautiful, filterable grid.
No API key. No cron. Listings load on demand, with optional shared and local caching.
✨ Features
| 🐾 Live Petfinder listings | Real adoptable pets with photos, names, breed, size, age, and location. |
| 🔎 Instant filtering | Filter by breed, size, and age in the browser, with removable chips. |
| 📖 Pet stories (flip card) | Flip a card to read the pet's description — an accessible disclosure with keyboard focus handling and Escape to close; auto-detected with safe fallback. |
| 🎚️ Card display toggles | Show/hide location, story, breed, and the age/size badge per site. |
| 💌 Apply to adopt | Optional button linking each pet to your application form, prefilled with its name & ID. |
| 🎨 Fully brandable | Your accent color, your copy, 2–4 column layouts. |
| 📱 Responsive | Mobile-first grid that looks great from phone to desktop. |
| ⚡ Fast & respectful | Optional shared cache, no plugin analytics, and no API key to manage. |
| 🔎 SEO & AI ready | Emits Schema.org JSON-LD (AnimalShelter + pet ItemList) for search engines and AI crawlers. |
| ♿ Accessible | Labelled controls, aria-live updates, and reduced-motion support. |
🚀 Quick start
- Copy this folder into
wp-content/plugins/purrfect-match/— or build a ZIP (see below) and upload it via Plugins → Add New → Upload. - Activate Purrfect Match.
- Open Settings → Purrfect Match and set your Petfinder organization ID
(required — e.g.
FL1629), plus any branding/copy you like. - Drop the shortcode on any page or post:
[purrfect_match]
🧩 Shortcode
With per-instance overrides:
[purrfect_match organization="FL1629" type="cat" status="adoptable"
limit="24" columns="3" brand="#e93396" hide_breed="false"
title="Find your purr-fect match"]
For a compact four-card teaser ordered by Petfinder publication time:
[purrfect_match limit="4" per_page="4" columns="4" sort="newest"]
| Attribute | Default | Description |
|---|---|---|
organization |
(none — required) | Petfinder display ID(s) or UUID(s), comma-separated. |
type |
cat |
cat, dog, rabbit, small-furry, bird, horse, barnyard, scales-fins-other. |
status |
adoptable |
adoptable, adopted, found. |
sort |
default |
default preserves the established order; newest requests recently published pets first. |
limit |
0 |
Max pets to load (0 = all; up to 1000). |
per_page |
24 |
Pets revealed in each visible batch (0 = show all). |
columns |
3 |
Desktop columns (2–4). |
hide_breed |
false |
Hide the breed name and the breed filter. |
adoption_form_url |
(empty) | Link each pet to your application form ("Apply to adopt"). |
title |
Find your purr-fect match |
Main heading. |
eyebrow |
Adoptable Pets |
Small label above the heading. |
subtitle |
Filter by breed, size, and age. |
Subheading. |
brand |
#e93396 |
Accent color (hex). |
org_name |
(empty) | Shown in the banner and as a location fallback. |
org_website |
(empty) | "Visit" link in the banner. |
Settings also include toggles for Show pet stories (flip to read), Show
location, Show age & size badge, Show plugin credit, SEO structured
data, and an optional Shared cache. Advanced settings (api_base,
s3_url, petfinder_url) match the public Petfinder widget and rarely need
changing.
Cached results can lag behind Petfinder by the configured cache lifetime. This
also applies to sort="newest"; the plugin orders the available result before
applying limit, but a still-fresh cached result is not refreshed early.
⚙️ How it works
Purrfect Match reproduces the data layer of Petfinder's own public pet-scroller widget, entirely client-side:
- A Petfinder organization display ID (e.g.
FL1629) is resolved to a UUID via theGetOrganizationGraphQL query; configured UUIDs are used directly. - The
SearchAnimalquery returns that organization's animals (name, photo, breed, size, age, location, optional description, and a detail-page link). - Results render into the grid, and the breed / size / age filters run instantly in the browser against the loaded set.
Requests go directly from the visitor's browser to Petfinder's public widget endpoint — so there's no API key to request and no server-side request from your site (an optional shared cache can serve a copy from your own site to cut repeat calls).
🛠 Development
This is a standard WordPress plugin with no build step — edit the PHP, CSS, and JS directly. See CONTRIBUTING.md for details.
📦 Building a release ZIP
bash bin/build.sh
Produces dist/purrfect-match.zip containing only the files that ship —
developer tools, examples, and docs are excluded automatically via
.gitattributes.
📁 Project structure
purrfect-match.php Plugin bootstrap: constants, includes, init.
includes/class-settings.php Options, defaults, and the Settings screen.
includes/class-purrfect-match.php Assets, shortcode, and per-instance config.
includes/class-rest.php Optional shared-cache REST endpoint.
templates/widget.php Front-end markup (one instance per shortcode).
assets/css/purrfect-match.css Namespaced widget styles (brand + columns via CSS vars).
assets/js/purrfect-match.js Client-side GraphQL data layer + filter UI.
uninstall.php Removes saved options and cache on delete.
readme.txt WordPress.org-style readme.
🔒 Privacy & external services
Purrfect Match does not add form, account, or tracking data to Petfinder
requests and includes no plugin analytics. To show pets, listing data and
photos may load in the visitor's browser from Petfinder's public widget
data source (psl.petfinder.com/graphql) and photo CDN. Those services receive
ordinary connection metadata such as IP address, user agent, and request
headers. See the readme "External services" section for details.
[!NOTE] Purrfect Match is not affiliated with, endorsed by, or sponsored by Petfinder. "Petfinder" is a trademark of its respective owner. Your use of Petfinder data is subject to Petfinder's terms and policies.
📄 License
GPL-2.0-or-later. Plugin by Andrew Mayes.