Skip to main content

A Wagtail plugin to add support for glossary terms entity to Draftail

Project description

Wagtail Terms

A Wagtail package to add support for a glossary terms entity to Draftail

Installation

pip install wagtailterms

Add wagtailterms to your INSTALLED_APPS in your Django settings file. Make sure you have rest_framework in your installed apps as well.

Migrate the database

python manage.py migrate

Add wagtailterms.urls to your urlpatterns in your Django urls file. the url should look like this:

path('api/terms/', include('wagtailterms.urls')),

⚠️ Note

The url path can be anything you want. This is the url that will be used to access the terms on the frontend


Settings

All configurations for wagtailterms are done in the settings.py file in a dictionary called WAGTAILTERMS.

  • icon - The icon for the terms. It is used in the draftail editor and for the viewset. All the icons available for wagtail are valid options
  • menu_order - Change the position of the terms snippet in the menu.
  • style - Change the default css inline-style of the term
  • disable_tags - Set to True to disable the tagging functionality. This removes the tag filtering interface from the term selector and hides tag-related features.
    WAGTAILTERMS = {
        'icon': 'snippet',
        'menu_order': 200,
        'style': "text-decoration-line: underline; text-decoration-color: green;text-decoration-thickness: 3px;color:green;",
        'disable_tags': False,  # Set to True to disable tagging functionality
    }

Usage

This wagtail package adds a Draftail entity to create a term that is mapped to a definition. The most common use case would be for the user to hover over a word/phrase on a page and a definition would appear next to the word/phrase. It allows you to Highlight a word/phrase in the Draftail/richtext editor and search for a definition that was created as a TermSnippet. In the editor the term name and definition will appear on top of the phrase when hovering over the phrase.

Creating new terms

Click in the admin side bar Terms -> Add New

With tagging

Use term entity in editor

Search for term

Select term

Without tags

Entity displayed in editor

Using Tags

Terms can be tagged to help organize and filter them. When creating or editing a term, you can add tags to categorize it. In the term selector popup, you can:

  1. Filter terms by tags using the "Filter by Tags" input
  2. Search for tags by typing in the tag filter box
  3. Select multiple tags to filter terms that have all selected tags
  4. Remove tags by clicking on the tag chips

When hovering over a term in both the editor and frontend, tags will be displayed in the tooltip along with the term definition.

You can disable the tagging functionality completely by setting disable_tags to True in your WAGTAILTERMS settings:

WAGTAILTERMS = {
    # ...other settings...
    'disable_tags': True,
}

This will remove the tag filtering interface from the term selector and hide all tag-related features.

The REST API responses include tags for each term when tagging is enabled:

{
    "term": "example term",
    "definition": "<p>Definition here</p>",
    "id": 1,
    "tags": ["category1", "category2"]
}

Search in the Page Editor

The search functionality in the admin interface integrates with Wagtail's built-in search backend. This means:

  1. The search will use whatever search backend you have configured for your Wagtail site (e.g., database, Elasticsearch)
  2. It searches across term names, definitions, and tags
  3. The search respects Wagtail's search configuration settings and optimizations

Display in template

To display the terms on the frontend the term shows up as a <span> element tag with a green underline and green text. In a future update this will be customizable. The element has a data-term attribute that contains the term id. It is up to the developer to fetch the term and definition to display it. To get the term by id fetch the term by id using the term API.

Rendered HTML of the term in the frontend:

<span style="text-decoration-line: underline; text-decoration-color: green;text-decoration-thickness: 3px;color:green;" data-term="1">term 1</span>

ℹ️ Above is the default style but this can be modified in the settings.

Quick implementation: (See full example)

Include in the template at the bottom of the page template.

...
{% include 'wagtailterms/wagtailterms.html' %}

ℹ️ This loads the advanced implementation in page template.

The most basic implementation: (See full example)

function showterm(e){
    const termid = e.target.dataset.term
    fetch(`/api/terms/${termid}/`)
        .then(response=> response.json())
        .then(data => {
            alert(`term = ${data.term} \ndefinition = ${data.definition}`)
        })
}

for(const term of document.querySelectorAll('[data-term]')){
    term.onmouseover=showterm;
}

The page would look like this:

On hover

A more advanced way would be to use a library like tippy.js to

create a tooltip that appears when hovering over the term. (See full example)

function add_tooltips(){
    const tips = tippy('[data-term]', {
        content: 'Loading...',
        allowHTML:true,
        interactive:true,
        theme:'light',
        animation: 'scale-subtle',
        onCreate(instance) {
            // Setup our own custom state properties
            // set if was loaded
            instance._fetchInitualized = false;
            instance._error = null;
        },
        onShow(instance) {
            if (instance._fetchInitualized || instance._error) {
                return;
            }

            instance._fetchInitualized = true;
            fetch(`/api/terms/${instance.reference.dataset.term}/`)
                .then(response => response.json())
                .then(data => {
                    if (data.term){
                        instance.setContent(`<h4>${data.term}</h4><p>${data.definition}</p>`);
                    }else{
                        instance.setContent("<p style='color: red'>Could not find definition</p>");
                    }
                })
                .catch(error => {
                    instance._error = error;
                    instance.setContent(`Request failed. ${error}`);
                });
        },
    });
}
add_tooltips();

The page would look like this:

On hover

REST API

Terms Endpoints

/api/terms/ will return a paginated list of terms. The response format depends on your disable_tags setting:

The list endpoint supports the following query parameters:

  • page: The page number to retrieve (e.g., /api/terms/?page=2)
  • q: Search terms by name and definition (e.g., /api/terms/?q=example)
  • tags: Filter terms by one or more tags. Can be used multiple times to filter by multiple tags (e.g., /api/terms/?tags=python&tags=django)

When disable_tags is False (default):

{
    "count": 3,
    "total_pages": 1,
    "current_page": 1,
    "next": null,
    "previous": null,
    "results": [
        {
            "term": "Term 1",
            "definition": "<p>This is a definition for term 1</p>",
            "id": 1,
            "tags": ["tag1", "tag2", "tag3"]
        },
        {
            "term": "Example term",
            "definition": "<p>Lorem ipsum dolor sit amet</p>",
            "id": 2,
            "tags": ["tag2", "tag4"]
        }
    ]
}

When disable_tags is True:

{
    "count": 3,
    "total_pages": 1,
    "current_page": 1,
    "next": null,
    "previous": null,
    "results": [
        {
            "term": "Term 1",
            "definition": "<p>This is a definition for term 1</p>",
            "id": 1
        },
        {
            "term": "Example term",
            "definition": "<p>Lorem ipsum dolor sit amet</p>",
            "id": 2
        }
    ]
}

The list endpoint supports pagination through query parameters:

  • page: The page number to retrieve (e.g., /api/terms/?page=2)
  • Response includes:
    • count: Total number of terms
    • total_pages: Total number of pages
    • current_page: Current page number
    • next: URL for the next page (null if on last page)
    • previous: URL for the previous page (null if on first page)
    • results: Array of terms for the current page

Fetching a single term with /api/terms/1/ will return:

With tags enabled:

{
    "term": "term 1",
    "definition": "<p>this is term 1</p>",
    "id": 1,
    "tags": ["tag1", "tag2"]
}

With tags disabled:

{
    "term": "term 1",
    "definition": "<p>this is term 1</p>",
    "id": 1
}

Tags Endpoint

When tags are enabled (disable_tags is False), you can use /api/terms/tags/ to get a list of all available tags:

{
    "tags": [
        {
            "name": "tag1",
            "count": 5
        },
        {
            "name": "tag2",
            "count": 3
        }
    ],
    "hasMore": false
}

The tags endpoint supports pagination through the page query parameter:

  • /api/terms/tags/?page=1
  • Each tag object includes:
    • name: The name of the tag
    • count: Number of terms using this tag
  • hasMore: Indicates if there are more pages of tags available

When tags are disabled (disable_tags is True), this endpoint will return a 404 response.

Changelog

0.2.1

  • Add Wagtail 7.2.x support
  • Add Wagtail 7.1.x support
  • Remove Python 3.9 support
  • Add Python 3.14 support

0.2.0

  • Added tags support for terms
  • Added tag filtering in term selector
  • Added tags display in tooltips
  • Updated REST API to include tags in responses
  • Updated the picker UI to match the rest of the wagtail admin
  • Tags filter uses infinite scroll
  • Remove popup-js dependency
  • Add pagination to the terms list
  • Improve search to search terms and definitions
  • Added disable_tags setting to completely disable the tagging functionality
  • Add formal wagtail 7.0.x support

0.1.3

  • Added setting to change frontend styles
  • Added quick start template for default frontend implementation

0.1.2

  • fixed term search form wider than modal
  • Add dark mode support

0.1.1

  • added settings to change the icon and menu order.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

wagtailterms-0.2.1.tar.gz (42.4 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

wagtailterms-0.2.1-py3-none-any.whl (42.4 kB view details)

Uploaded Python 3

File details

Details for the file wagtailterms-0.2.1.tar.gz.

File metadata

  • Download URL: wagtailterms-0.2.1.tar.gz
  • Upload date:
  • Size: 42.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for wagtailterms-0.2.1.tar.gz
Algorithm Hash digest
SHA256 475208fb376cd5f0ff99ce44eb59a4ee454a0a250bc271d4a1b978ff24588eec
MD5 efbacd540343873cd5a08358354048b2
BLAKE2b-256 c9d10ee31e4b6a2753737d8a314c3e9320c5dca0c688fb1bdeae89c1640c17e7

See more details on using hashes here.

Provenance

The following attestation bundles were made for wagtailterms-0.2.1.tar.gz:

Publisher: python-publish.yml on smark-1/wagtailterms

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file wagtailterms-0.2.1-py3-none-any.whl.

File metadata

  • Download URL: wagtailterms-0.2.1-py3-none-any.whl
  • Upload date:
  • Size: 42.4 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for wagtailterms-0.2.1-py3-none-any.whl
Algorithm Hash digest
SHA256 544d25f84efcdfb365766229181b1722b8f488bafcf747758f7a3e89ae9adbf7
MD5 d298a5c2eac84229aacc2a76b8a51372
BLAKE2b-256 36e06a43439e802c50e09fea8c9f70a8c9c3128af25766e344b49b73817fd7d2

See more details on using hashes here.

Provenance

The following attestation bundles were made for wagtailterms-0.2.1-py3-none-any.whl:

Publisher: python-publish.yml on smark-1/wagtailterms

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page