Skip to content

Plugin Development

A software development kit for developing plugins to Recogito Studio, an open source platform for collaborative annotation of TEI, IIIF and PDF documents.

The Recogito Studio SDK is designed to facilitate plugin development for the Recogito Studio Client without the need to set up your own full-stack installation or forking the platform. It provides essential tools and abstractions to help you build useful extensions for the Recogito Studio ecosystem.

The following steps walk you through the development of a Hello World plugin that adds a simple message to the annotation editor.

Before starting, make sure you have the following installed:

  • NodeJS (version 20 recommended)
  • npm

Step 1: Choose from GitHub Template or Manual Setup

Section titled “Step 1: Choose from GitHub Template or Manual Setup”

There is a GitHub template that you can use to quickly bootstrap your new project. However if you prefer you can build your project from scratch.

Step 1.1.1: Create New Project From Template

Section titled “Step 1.1.1: Create New Project From Template”
  1. In your browser, go to the template repository
  2. Above the file list, click Use this template.
  3. Select Create a new repository.

Use this template button

  1. Use the Owner dropdown menu to select the account you want to own the repository.
  2. Type a name for your repository, and an optional description.

Create repository owner selection

  1. Choose a repository visibility.

  2. Click Create repository.

Step 1.1.2: Clone Repository to Your Local Workspace

Section titled “Step 1.1.2: Clone Repository to Your Local Workspace”

In a terminal window clone the repository that you just created:

Terminal window
git clone https://github.com/[Your Repository].git

Change your directory to the cloned repository and run:

Terminal window
npm install

Open your package.json file and name your plugin. It should match the name you created above (i.e. @performant/plugin-hello-world).

{
"name": "@recogito/plugin-template",
"name": "@performant/plugin-hello-world"
"version": "0.1.0",
"description": "A template to boot-strap a new Recogito Studio plugin project.",
"description": "My new Recogito Studio Plugin"
...
}

You can now proceed to Step 2. You will find that some of the proceeding steps have been taken care of by the template.

The entry point is a TypeScript file (src/index.ts) that exports an Astro Integration and registers a Plugin. Here’s a sample implementation:

import type { AstroIntegration } from "astro";
import { Plugin, registerPlugin } from "@recogito/studio-sdk";
const HelloWorldPlugin: Plugin = {
name: "My Hello World Plugin",
module_name: '@performant/plugin-hello-world',
description: "An example Hello World plugin.",
author: "Performant Software",
homepage: "https://www.performantsoftware.com/",
};
const plugin = (): AstroIntegration => ({
name: "plugin-hello-world",
hooks: {
"astro:config:setup": ({ config, logger }) => {
registerPlugin(HelloWorldPlugin, config, logger);
},
},
});
export default plugin;

Step 3: Install the Test Application Template

Section titled “Step 3: Install the Test Application Template”

Run the following command to set up the test application:

Terminal window
npx copy-template

Add a development script to your package.json:

{
"scripts": {
"dev": "npm start --prefix .dev/"
}
}

Update .dev/package.json to include your plugin:

{
"dependencies": {
"@performant/plugin-hello-world": "file:../"
}
}

Modify .dev/astro.config.mjs:

import { defineConfig } from 'astro/config';
import react from '@astrojs/react';
import node from '@astrojs/node';
import HelloWorldPlugin from '@performant/plugin-hello-world';
export default defineConfig({
integrations: [
react(),
HelloWorldPlugin()
],
// ... other configurations
});

Create a React component in src/extensions/HelloWorldMessage.tsx:

./src/extensions/HelloWorldMessage.tsx
export const HelloWorldMessage = () => {
return <div>Hello World</div>;
};

Update the index.ts file to register the component as a UI extension:

import type { AstroIntegration } from 'astro';
import { Plugin, registerPlugin } from '@recogito/studio-sdk';
const HelloWorldPlugin: Plugin = {
name: 'My Hello World Plugin',
module_name: '@performant/plugin-hello-world',
description: 'An example Hello World plugin.',
author: 'Performant Software',
homepage: 'https://www.performantsoftware.com/',
extensions: [{
name: 'hello-world-message',
component_name: 'HelloWorldMessage',
extension_point: 'annotation:*:annotation-editor'
}]
};
const plugin = (): AstroIntegration => ({
name: 'plugin-hello-world',
hooks: {
'astro:config:setup': ({ config, logger }) => {
registerPlugin(HelloWorldPlugin, config, logger);
}
}
});
export default plugin;

In the package.json, add an export for the UI extension:

{
"exports": {
".": "./dist/index.js",
"./HelloWorldMessage": "./dist/extensions/HelloWorldMessage.js"
}
}
  1. Build the plugin package:
Terminal window
npm run build
  1. Add plugin to test application dependencies in .dev/package.json:
{
"dependencies": {
"@performant/plugin-hello-world": "file:../"
}
}
  1. Configure Astro integration in .dev/astro.config.mjs:
import HelloWorldPlugin from "@performant/plugin-hello-world";
export default defineConfig({
integrations: [
react(),
HelloWorldPlugin(),
],
// other configurations...
});
  1. Run the development process:
Terminal window
npm install
npm run dev
  1. Open browser to http://localhost:4321/

Plugins can be installed via:

  • npm registry publication
  • Direct GitHub repository installation

Installation steps:

  1. Install package in Recogito Studio Client folder
  2. Add plugin to astro.config.mjs

The Recogito Studio Client utilizes Radix UI primitives for building accessible and consistent interface components. We recommend that plugin developers also adopt Radix when developing extension components.​

To make it easier to build visually consistent extensions that match Recogito Studio’s native look and feel, the SDK provides a set of pre-defined CSS classes for common UI primitives. The following primitives and classes are currently available:

  • Accordion. Base styles for the Radix Accordion primitive.
  • Avatar. The Recogito-themed user avatar.
  • Button. A range of button variant styles (primary, minimal, unstyled, danger, etc.)
  • Checkbox. Base styles for the Radix checkbox primitive.
  • Dialog. Default Radix popup dialog styles.
  • Dropdown. Base styles for Recogito-themed dropdown menus.
  • Form. Minimal styles for form input elements.
  • Popover. Base styles for the Radix popover primitive.
  • Radio. Base styles for the Radix Radio primitive.
  • Select. Base styles for the Radix Select primitive.
  • Switch. Base styles for the Radix Switch primitive.
  • Tooltip. Styles for Recogito-themed mouse hover tooltips.

To apply SDK-provided theming, all that’s needed is to add the appropriate CSS classes to your components. For example:

// Use Radix Accordion in your extension component
import * as Accordion from '@radix-ui/react-accordion';
// ...
<Accordion.Root
// Apply Recogito-provided `accordion-root` class
className="accordion-root"
type="multiple">
<Accordion.AccordionItem
value="item-1"
// Recogito-provided `accordion-item` class
className="accordion-item">
<Accordion.Header
// Recogito-provided `accordion-header` class
className="accordion-header">
<Accordion.Trigger
// Recogito-provided `accordion-trigger` class
className="accordion-trigger">
Accordion Item 1 Trigger
</Accordion.Trigger>
</Accordion.Header>
<Accordion.AccordionContent
// Recogito-provided `accordion-content` class
className="accordion-content">
Accordion Item 1 Content
</Accordion.AccordionContent>
</Accordion.AccordionItem>
</Accordion.Root>

Styled example:

Styled accordion example

For details, classes and other components, check the stylesheet files directly.

Here are the existing plugins available for Recogito Studio:

  • Geotagging - Recogito Geotagging Plugin.

  • Named Entity Recognition - Recogito Studio plugin which can perform Named Entity Recognition on TEI and Plain Text.

  • Revisions - Allows users to make a read-only annotation editable, by cloning it into the active layer.

  • TEI Inliner - A plugin for exporting TEI annotations as inline markup.

  • Reconciliation Service - Use a Reconciliation Service API endpoint as a tag source in Recogito Studio projects.

  • Sandcastle Export - A custom annotation export for Duke University’s Unreal 3D importer.