Skip to content

dknauss/borges-bibliography-builder

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

275 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Borges Bibliography Builder for WordPress

License: GPL v2+ WordPress tested PHP tested CI Runtime matrix CodeQL codecov WordPress Playground WordPress.org

Borges Bibliography Builder is named after Jorge Luis Borges (1899–1986), the Argentine writer, essayist, poet, and librarian whose work imagined infinite libraries, invented books, and self-referential labyrinths.

Borges, the plugin, adds a single bibliography builder block to the WordPress editor. It transforms pasted scholarly references — DOI numbers/URLs, PubMed/PMID identifiers, BibTeX entries, and supported formatted citations — into a semantically rich, auto-sorted bibliography with static saved output. Export your work as CSL-JSON, BibTeX, BibLaTeX, and RIS for Zotero, Mendeley, EndNote, JabRef, BibDesk, and similar tools.

No shortcodes. No database storage. Static HTML output survives plugin deactivation.

Just write out your citations or paste DOIs, PubMed/PMID identifiers, and BibTeX code, up to 50 at a time. Easily build a formatted, auto-sorted bibliography in any supported style.

Try it in WordPress Playground

Install the public release from WordPress.org or launch a disposable WordPress instance with the plugin preinstalled: Try the Borges Bibliography Builder in WordPress Playground. The GitHub-hosted demo Blueprint installs the latest GitHub Release ZIP through the WordPress Playground CORS proxy and explicitly requests PHP intl support because editor-time CSL formatting runs through the plugin's local PHP formatter. The WordPress.org Preview blueprint is separate; WordPress.org installs Borges automatically there, and the blueprint only seeds demo content and auxiliary plugin setup.

Screenshots

Front-end output Editor with citations
The rendered bibliography on the site front end with hanging indents, italic titles, and linked DOIs — all styled by the active theme. The block in editor view showing a formatted bibliography. Hover over any entry to reveal copy, edit, and delete actions.
Block inserter Empty-state form Manual entry
Discover the Bibliography block in the block inserter by searching for "Bibliography." Paste DOIs, PubMed/PMID identifiers, BibTeX entries, or supported citation text into the import form. The sidebar controls citation style, visible heading, and metadata output (JSON-LD, COinS, CSL-JSON). Switch to Manual Entry to build a citation field by field: Publication Type, Author, Title, Container, Publisher, Year, Pages, DOI, and URL. These fields will be automatically populated from DOIs, PubMed/PMID records, and pasted input that can be parsed.

Installation

  1. Upload the plugin files to /wp-content/plugins/borges-bibliography-builder/, or install directly through the WordPress plugin screen.
  2. Activate the plugin through the Plugins screen in WordPress.
  3. Add the Bibliography block to any post or page.
  4. Paste DOI(s), PubMed/PMID identifiers, BibTeX entries, or supported citations.

Compatibility

  • WordPress 6.4+; tested up to WordPress 7.0.
  • PHP 7.4+.
  • Multisite — supported and covered by CI smoke testing.

Developer-facing CI/runtime coverage details are listed in the development section below.

Recent Release Highlights

  • 1.3.3 — Restores DOI imports in WordPress Playground with direct CrossRef CSL transform lookups, serializes DOI requests for CrossRef's public concurrency limit, and adds a PubMed sample to the demo starter content.
  • 1.3.0 — Enforces an explicit 50-citation cap with editor warnings, guards all editor mutation flows against stale async results, removes a redundant formatter call in the manual-entry path, prunes non-runtime vendor dead weight from the release zip, and caches successful PMID responses while deduplicating concurrent DOI requests.
  • 1.2.0 — Adds PubMed/PMID import through an authenticated REST proxy, BibLaTeX export, manual reordering for numeric styles, full-bibliography reformat parity, and compact matrix coverage across all nine styles.
  • ABNT / NBR 6023:2018 — Brazilian bibliography output is available as ABNT (Associação Brasileira de Normas Técnicas) with pt-BR defaults and the Referências heading.
  • 1.1.x accessibility — Adds optional Block Accessibility Checks integration and restores visible keyboard focus on editor row actions.

Features

  • Multiple input paths — Add bare DOIs, DOI URLs, PubMed/PMID records, BibTeX entries, and supported formatted citations.
  • Nine citation styles — Chicago Notes-Bibliography by default, with Chicago Author-Date, APA 7, Harvard, Vancouver, IEEE, MLA 9, OSCOLA, and ABNT (Associação Brasileira de Normas Técnicas / NBR 6023:2018) selectable.
  • Structured editing — Plain-text editing plus per-field editing for heuristic or warning-marked citations.
  • Semantic outputrole="doc-bibliography", <cite> wrappers, lang attributes, and hanging-indent styling without deprecated bibliography-entry ARIA roles.
  • JSON-LD — Schema.org structured data for search engines, AI systems, and semantic consumers (on by default).
  • COinS — Optional OpenURL spans for browser-based citation manager detection, especially Zotero and legacy OpenURL workflows.
  • CSL-JSON output — Optional machine-readable metadata for citation-manager, citeproc, and scholarly-service interoperability.
  • Export — Download the current bibliography as CSL-JSON, UTF-8 BibTeX, BibLaTeX, or RIS; copy individual citations or the full bibliography as plain text.
  • Static save — Bibliography HTML and metadata are baked into post content at save time.
  • Accessible editor UX — Focus management, block-local Gutenberg notices, keyboard escape/cancel flows, and row action controls.
  • Translation-ready interface — strings use the borges-bibliography-builder text domain; WordPress.org publishes language packs as community translations are approved. (See Language Support below.)

Reference Manager Compatibility

Borges is reference-manager-friendly by design. It outputs portable CSL-JSON, BibTeX, BibLaTeX, RIS, DOI links, Schema.org JSON-LD, and optional COinS metadata so your bibliographies can be imported directly into the most widely used bibliography management and academic publishing software.

Tool or workflow How Borges supports it
Zotero Strong compatibility through DOI links, BibTeX, RIS, CSL-JSON, and optional COinS metadata. Tested with the @zotero SaaS, macOS app, and Chrome browser extension from @digitalscholar.
Mendeley Compatible with Elsevier's @Mendeley SaaS, macOS app, and Chrome browser extension through BibTeX/RIS exports; DOI-backed entries are also browser-importer friendly. Use export/copy actions for non-DOI entries rather than relying on extension autodetection.
EndNote Compatible through RIS and BibTeX imports. EndNote XML is deferred as a Borges export format unless user feedback and/or future testing show a practical gap that RIS and BibTeX do not cover.
JabRef, BibDesk, LaTeX Compatible through UTF-8 BibTeX and BibLaTeX exports for BibTeX/Biber and LaTeX-family workflows.
CSL / citeproc tools Compatible through CSL-JSON, which is the plugin's canonical structured data model.

Language Support

WordPress.org language packs are generated from translate.wordpress.org after the Stable translation project reaches the approval threshold for a locale. The live WordPress.org plugin page's Languages list is the canonical list of currently published language packs; English (US) is the source language and is not counted as a translated locale.

This repository/package currently includes seed PO/MO files for translator review and import in fr_FR, de_DE, nl_NL, sv_SE, es_ES, it_IT, pt_PT, pl_PL, ru_RU, ja, zh_CN, ko_KR, sr_RS, hr, pt_BR, hi_IN, bn_BD, ta_IN, and te. These files cover plugin interface strings only, not user-provided citation content. They should not be described as official WordPress.org language-pack availability until the corresponding locale is approved and listed on WordPress.org.

Supported Input

First-Class Inputs

  • Bare DOI10.1000/xyz123
  • DOI URLhttps://doi.org/10.1000/xyz123
  • PubMed/PMIDPMID:26673779 or pmid:26673779, resolved through the authenticated WordPress REST proxy
  • BibTeX@article{key, title={...}, ...}

Supported Formatted Citation Coverage

The free-text parser currently supports a growing set of formatted citations for:

  • books
  • journal articles
  • chapters
  • webpages and social media posts
  • reviews
  • theses and dissertations

Support is heuristic rather than universal. Unsupported inputs fail closed with a block-local inline Gutenberg notice. Manual entry is now available as a fallback for unsupported formats.

REST API

Borges exposes read-only bibliography data routes under /wp-json/bibliography/v1 for published content, integrations, and export workflows.

List bibliographies in a post

GET /wp-json/bibliography/v1/posts/<post_id>/bibliographies

Returns every Borges Bibliography block found in the post, including nested blocks:

{
  "postId": 123,
  "bibliographies": [
    {
      "index": 0,
      "entryCount": 2,
      "citationStyle": "chicago-notes-bibliography",
      "headingText": "References",
      "outputJsonLd": true,
      "outputCoins": false,
      "outputCslJson": false,
      "citations": []
    }
  ]
}

Get one bibliography

GET /wp-json/bibliography/v1/posts/<post_id>/bibliographies/<index>

<index> is zero-based within the post. Supported formats:

  • ?format=json — normalized bibliography block data. This is the default.
  • ?format=text — one visible citation per line, stripped to plain text.
  • ?format=csl-json — CSL-JSON array with application/vnd.citationstyles.csl+json content type.

Permissions and limitations

  • Published, non-password-protected posts are publicly readable.
  • Password-protected, draft, private, or otherwise non-public posts require edit_post permission.
  • Missing posts, forbidden posts, and missing bibliography indexes return explicit REST errors.
  • The public bibliography data routes are read-only. They do not add, update, delete, reorder, or persist citations.

The separate editor-only formatter endpoint accepts POST /wp-json/bibliography/v1/format, requires edit_posts, and returns formatted citation text for submitted CSL-JSON. It does not save changes.

The editor-only PubMed resolver accepts GET /wp-json/bibliography/v1/pmid/<pmid>, requires edit_posts, validates the PMID as numeric input, and returns normalized CSL-JSON from the fixed NCBI/PMC citation exporter endpoint. It is used for pasted PMID: input and does not persist citations by itself.

External Services

This plugin connects to fixed scholarly metadata services only when you explicitly add an identifier in the block editor — no citation data is sent automatically or in the background. No account or API key is required for the supported DOI or PMID lookups.

DOI metadata

DOI input connects to the CrossRef REST API to resolve citation metadata.

PubMed/PMID metadata

PubMed/PMID input connects through the plugin's authenticated WordPress REST proxy to the NCBI/PMC Literature Citation Exporter CSL endpoint. The proxy uses a fixed upstream host and validates the PMID before making the outbound request.

Development

Requires Node.js 18+, npm 9+, and Composer.

npm install                  # Install dependencies
composer install             # Install PHP tooling
npm run build                # Production build
npm run start                # Development mode with file watching
npm run lint:js              # ESLint
npm run lint:css             # Stylelint
npm run lint:php             # WPCS/PHPCS
npm run test                 # Unit tests
npm run test:js:coverage     # JS coverage for Codecov
npm run test:rest:local      # Local REST endpoint smoke test (Studio site)
npm run test:e2e             # Playwright smoke suite against local site
npm run test:e2e:playground  # Playground-based Playwright smoke suite
npm run test:e2e:lifecycle   # Plugin lifecycle e2e tests (activate/deactivate/delete)
npm run test:runtime:local   # Docker-based runtime smoke environment
npm run test:interop:zotero  # Zotero + citation format interoperability checks
composer test:php            # PHPUnit REST and bootstrap tests
composer test:php:coverage   # PHP coverage for Codecov
composer analyze:php         # Psalm static analysis

GitHub Actions currently runs:

  • Node quality/build checks
  • PHPUnit and PHPCS on PHP 8.3
  • Psalm static analysis
  • CodeQL for JavaScript and PHP
  • Codecov uploads from JS + PHP coverage
  • Playwright smoke and lifecycle tests against WordPress Playground

The GitHub Actions runtime matrix currently covers:

  • Apache + PHP 7.4 + WordPress 6.4
  • Apache + PHP 8.1 + WordPress 6.4
  • Apache + PHP 8.1 + WordPress 6.7
  • Apache + PHP 8.2 + latest WordPress
  • Apache + PHP 8.3 + latest WordPress
  • Apache + PHP 8.4 + latest WordPress
  • Apache + PHP 8.3 + latest WordPress + Multisite
  • Nginx + PHP 8.1 + WordPress 6.7
  • Nginx + PHP 8.2 + latest WordPress
  • Nginx + PHP 8.3 + latest WordPress

Each runtime smoke job uploads artifacts, including Docker logs, service status, HTTP responses, and environment summaries under output/runtime-matrix/<matrix-name>.

Multisite runtime smoke coverage is included in CI. SQLite is not currently part of the GitHub runtime matrix; add it when a compatibility risk justifies the extra lane.

Project Documentation and Operational Files

WordPress.org branding assets live in .wordpress-org, editable source files live in .wordpress-org/source, and maintainer-facing deploy notes live in docs/wporg-svn-checklist.md.

Playground Blueprint maintenance

The Playground demo and WordPress.org Preview both rely on the PHP formatter used by the editor REST endpoint. That formatter uses citeproc-php, which requires PHP intl. Keep both Blueprint files in sync:

  • playground/blueprint.json powers the GitHub README and WordPress.org readme demo link; it installs the latest GitHub Release ZIP through the WordPress Playground CORS proxy so the demo exercises the packaged release artifact without direct GitHub asset CORS failures.
  • .wordpress-org/blueprints/blueprint.json deploys to WordPress.org SVN as assets/blueprints/blueprint.json for the plugin-directory Preview button. WordPress.org installs the plugin automatically in that preview, so this blueprint does not install Borges itself.
  • Both files intentionally declare phpExtensionBundles: ["kitchen-sink"] and features: { "networking": true, "intl": true }. The bundle form follows WordPress.org Preview documentation; the features.intl flag is required by the live browser Playground runtime so formatter requests do not fall back with bibliography_builder_formatter_extension_missing.

Run npm run test -- --runTestsByPath src/blueprint.test.js after editing either Blueprint.

Plugin File Structure

borges-bibliography-builder/
├── bibliography-builder.php      # Plugin bootstrap
├── block.json                    # Block metadata & attributes
├── src/
│   ├── index.js                  # Block registration
│   ├── edit.js                   # Editor component
│   ├── save.js                   # Static save entrypoint
│   ├── save-markup.js            # Shared static save markup
│   ├── editor.scss               # Editor-only styles
│   ├── style.scss                # Frontend bibliography styles
│   └── lib/
│       ├── parser.js             # Input detection & parsing orchestration
│       ├── sorter.js             # Style-family bibliography sort comparator
│       ├── coins.js              # CSL-JSON → COinS builder
│       ├── jsonld.js             # CSL-JSON → Schema.org JSON-LD mapper
│       └── formatting/           # Style registry + CSL-backed formatting
├── package.json
└── readme.txt                    # WordPress.org readme

See SPEC.md for the authoritative behavior specification and future plans.

Known Limitations

  • OSCOLA grouped bibliography — OSCOLA convention requires the bibliography to be divided into source-type groups (cases, legislation, books, articles, online sources). Borges currently renders a single alphabetized list regardless of style. This limitation is displayed as a dismissible notice in the editor when OSCOLA is selected. Grouped-bibliography support is tracked as Epic-OSCOLA in docs/planning/sort-conformance-plan.md.

Contributing

See CONTRIBUTING.md for development setup, coding standards, and PR process.

Security

See SECURITY.md for reporting vulnerabilities.

License

GPL-2.0-or-later. See LICENSE for the full text.