Skip to main content

Overview

The Font endpoints provide access to manage custom fonts used in web stories. The API supports both built-in fonts (Google Fonts) and custom uploaded fonts. Base Path: /wp-json/web-stories/v1/web-story-font

List Fonts

Retrieves a collection of available fonts.
GET /web-stories/v1/web-story-font
curl https://yoursite.com/wp-json/web-stories/v1/web-story-font

Query Parameters

context
string
default:"view"
Scope: view, edit, or embed
service
string
default:"all"
Filter by font service:
  • all - Returns both built-in and custom fonts
  • builtin - Returns only built-in fonts (Google Fonts + system fonts)
  • custom - Returns only user-uploaded custom fonts
Search fonts by family name (case-insensitive)
include
array
Limit results to specific font families (case-insensitive)Example: ?include[]=Roboto&include[]=Open+Sans

Response

[
  {
    "id": 123,
    "family": "Roboto",
    "fallbacks": ["sans-serif"],
    "weights": [400, 700],
    "styles": ["normal", "italic"],
    "variants": [
      [400, 0],
      [400, 1],
      [700, 0],
      [700, 1]
    ],
    "service": "builtin",
    "metrics": {
      "upm": 1000,
      "asc": 950,
      "des": -250,
      "tAsc": 750,
      "tDes": -250,
      "tLGap": 0,
      "wAsc": 1000,
      "wDes": 250,
      "xH": 500,
      "capH": 700
    },
    "url": "https://fonts.googleapis.com/css2?family=Roboto:ital,wght@0,400;0,700;1,400;1,700"
  },
  {
    "id": 456,
    "family": "My Custom Font",
    "fallbacks": ["serif"],
    "weights": [400],
    "styles": ["normal"],
    "variants": [[400, 0]],
    "service": "custom",
    "metrics": {...},
    "url": "https://example.com/wp-content/uploads/2024/03/custom-font.woff2"
  }
]

Response Fields

id
integer
Unique identifier for custom fonts (null for built-in fonts)
family
string
Font family name
fallbacks
array
Fallback font families (e.g., ["sans-serif"], ["serif"])
weights
array
Available font weights (100-900, in increments of 100)Example: [400, 700] for normal and bold
styles
array
Available font stylesExample: ["normal", "italic"]
variants
array
Font weight and style combinations as [weight, style] tuplesStyle: 0 = normal, 1 = italicExample: [[400, 0], [400, 1], [700, 0]]
service
string
Font source: builtin for Google Fonts/system fonts, custom for uploaded fonts
metrics
object
Font metrics for text rendering
url
string
Font file URL or Google Fonts CSS URL

Get Font

Retrieves a single custom font by ID.
GET /web-stories/v1/web-story-font/:id
curl https://yoursite.com/wp-json/web-stories/v1/web-story-font/456
This endpoint only works for custom fonts (with numeric IDs). Built-in fonts don’t have individual endpoints.

Path Parameters

id
integer
required
Unique identifier for the custom font

Response

Returns a single font object (same structure as list response).

Create Custom Font

Registers a new custom font.
POST /web-stories/v1/web-story-font
curl -X POST https://yoursite.com/wp-json/web-stories/v1/web-story-font \
  -H "Content-Type: application/json" \
  -u "username:password" \
  -d '{
    "family": "My Custom Font",
    "fallbacks": ["serif"],
    "weights": [400, 700],
    "styles": ["normal"],
    "variants": [[400, 0], [700, 0]],
    "url": "https://example.com/fonts/custom-font.woff2",
    "metrics": {
      "upm": 1000,
      "asc": 800,
      "des": -200,
      "tAsc": 800,
      "tDes": -200,
      "tLGap": 0,
      "wAsc": 1000,
      "wDes": 200,
      "xH": 500,
      "capH": 700
    }
  }'

Request Body

family
string
required
Font family name (must be unique)
fallbacks
array
required
Array of fallback font familiesExample: ["sans-serif"] or ["Georgia", "serif"]
weights
array
required
Array of available font weights (integers 100-900)Minimum: 1 weight required
styles
array
required
Array of available stylesExample: ["normal"] or ["normal", "italic"]Minimum: 1 style required
variants
array
required
Array of [weight, style] tuples where style is 0 (normal) or 1 (italic)Must have exactly 2 items per variantMinimum: 1 variant required
url
string
required
Direct URL to the font file (WOFF2, WOFF, TTF, or OTF)
metrics
object
required
Font metrics object with all required properties (see Response Fields above)

Response

Returns the created font object with HTTP 201 status.
Font family names must be unique. Attempting to create a font with a name that already exists (case-insensitive) will return a rest_invalid_field error.

Delete Custom Font

Deletes a custom font. Built-in fonts cannot be deleted.
DELETE /web-stories/v1/web-story-font/:id
curl -X DELETE https://yoursite.com/wp-json/web-stories/v1/web-story-font/456 \
  -u "username:password"

Path Parameters

id
integer
required
Unique identifier for the custom font

Response

{
  "deleted": true,
  "previous": {
    "id": 456,
    "family": "My Custom Font"
  }
}
Fonts are force-deleted (no trash). The deletion is permanent.

Built-in Fonts

The plugin includes built-in fonts from Google Fonts. These fonts:
  • Are loaded from /includes/data/fonts/fonts.json
  • Have service: "builtin"
  • Do not have numeric IDs
  • Cannot be modified or deleted via the API
  • Include popular fonts like Roboto, Open Sans, Lato, etc.

Font Filtering Examples

Get all fonts

curl https://yoursite.com/wp-json/web-stories/v1/web-story-font

Get only custom fonts

curl https://yoursite.com/wp-json/web-stories/v1/web-story-font?service=custom

Get only built-in fonts

curl https://yoursite.com/wp-json/web-stories/v1/web-story-font?service=builtin

Search for fonts

curl https://yoursite.com/wp-json/web-stories/v1/web-story-font?search=roboto

Get specific fonts by family name

curl "https://yoursite.com/wp-json/web-stories/v1/web-story-font?include[]=Roboto&include[]=Open+Sans"

Font Sorting

Fonts are returned sorted alphabetically by family name:
  • Custom fonts are sorted by title (case-insensitive)
  • Built-in fonts are pre-sorted
  • When mixing both (service=all), the combined list is sorted by family name

Permissions

get_items_permissions_check
permission
List Fonts: Requires read_post capability for the font post type
create_item_permissions_check
permission
Create Font: Requires edit_web-stories capability
delete_item_permissions_check
permission
Delete Font: Requires delete_web-story or delete_others_web-stories capability

Common Errors

rest_forbidden
error
Status 403: You don’t have permission to list/create fontsRequired capability: read_post for listing, edit_web-stories for creating
rest_invalid_field
error
Status 400: A font with this name already existsFont family names must be unique (case-insensitive comparison)
rest_post_invalid_id
error
Status 404: Custom font with the specified ID does not exist

Font Data Storage

Custom fonts are stored as custom posts:
  • Post Type: web-story-font
  • Post Title: Font family name
  • Post Content: JSON-encoded font data (fallbacks, weights, styles, variants, metrics, url)
  • Post Status: Always publish
The font data JSON is decoded and merged into the response.

Build docs developers (and LLMs) love