Skip to content

Customizing your plugin's listing

Draga Doncila Pop edited this page Sep 19, 2023 · 21 revisions

napari plugin developers can customize their plugin's listing on the napari hub by updating the metadata associated with their Python package or adding napari hub-specific configuration files to their GitHub repository.

Data sources

We have three sources of plugin information for the napari hub:

  • PyPI (modifiable through Python Package Configuration files, such as setup.cfg)
  • GitHub (modifiable through .napari-hub configuration folder)
  • npe2 (modifiable through the npe2 manifest file)

PyPI

napari and the napari hub support discovery of plugins on PyPI that are tagged with the "Framework :: Napari" trove classifier (we do not currently support discovery of plugins on conda-forge or Anaconda cloud). Most of the information about a napari plugin is specified in the Python package metadata & PyPI is our primary source of plugin metadata. The PyPI API provides information about Python packages through a simple JSON structure. We use PyPI to source information such as the Python versions that a plugin supports, its dependencies, etc.

Plugin developers can modify these fields when they package their plugin by setting values in the Python package metadata.

GitHub

For some fields, we look to the plugin developer's GitHub repository instead of (or in addition to) PyPI. This is only supported, however, if the plugin developer has added a link to their GitHub repository in their PyPI metadata (see Source Code).

Plugin developers can modify these fields by adding a .napari-hub/ configuration folder to their repository, along with the relevant configuration files for a given field. We currently support two configuration files:

  • .napari-hub/DESCRIPTION.md for a napari hub-specific description (see Description)
  • .napari-hub/config.yml for all other configurable fields

NOTE: We currently support loading these metadata from .napari/ but to prevent confusion with the plugin manifest file (canonically, napari.yml), .napari-hub/ is the preferred location for hub-specific configuration, metadata, and plugin documentation. We will deprecate support for .napari/ at some point in the future.

npe2 manifest

For some napari-specific fields, we leverage metadata that is defined in the npe2 manifest. We access these fields by downloading the Python package and inspecting the manifest directly.

See the npe2 manifest reference for more details.

Fields

For each of the fields in a plugin's listing, we outline below how the field is used and where we source the data.

Metadata Full view List view Filterable Sortable Searched Primary Source Alternate Source
Display Name npe2 --
Name PyPI --
Version PyPI --
Summary PyPI Github
Description PyPI Github
Workflow Step npe2 Github
Image Modality GitHub --
Supported Data GitHub --
Plugin Type npe2 --
Save Extension npe2 --
Save Layers npe2 --
Open Extension npe2 --
Authors PyPI GitHub
License GitHub PyPI
Python Version PyPI --
Operating System PyPI --
Requirements PyPI --
Documentation PyPI --
Project Site PyPI --
Support PyPI --
Report Issues PyPI --
Twitter PyPI --
Source Code PyPI --
Release Date PyPI --
Visibility -- -- -- -- -- npe2 --

Display Name

This is the display name of the plugin in napari.

We display this on the detailed plugin page and the plugin listings.

We index this field for searching.

We source this from the npe2 metadata.

You can set this by setting the display_name value in your npe2 manifest.

See the npe2 manifest reference for more details.

Name

This is the name of the Python package that implements the plugin.

We display this on the detailed plugin page and the plugin listings.

We index this field for searching.

We source this from the ["info"]["name"] field of the JSON returned by the PyPI API.

You can set this by setting the name value in your package metadata.

# setup.cfg
[metadata]
# ...
name=starfish
# ...

Summary

This is a short summary of the plugin.

We display this on the detailed plugin page and the plugin listings.

We index this field for searching.

We source this from the ["info"]["summary"] field of the JSON returned by the PyPI API, which is set in the summary value in your package metadata.

# setup.cfg
[metadata]
# ...
summary = Pipelines and pipeline components for the analysis of image-based transcriptomics data
# ...

Description

This is a detailed description of the plugin.

We display this on the detailed plugin page only.

We index this field for searching.

We source this from the ["info"]["description"] field of the JSON returned by the PyPI API, which can be set by setting the long_description and long_description_content_type values in your package metadata.

# setup.cfg
[metadata]
# ...
long_description = file: README.md
long_description_content_type = text/markdown
# ...

If you'd like to provide a different description for the napari hub plugin page, you can specify it in your GitHub repository at .napari-hub/DESCRIPTION.md.

You can denote sections your plugin description by adding Level 2 Headings (e.g. ## Summary). We will automatically generate sidebar navigation for your plugin from the Level 2 Headings present in your plugin description. If your description begins with a Level 1 Heading, we will assume that this is a title (e.g. for your README) and drop it from the description.

Workflow Step

This is a list of workflow steps that your plugin supports.

We display this on the detailed plugin page and the plugin listings.

We index this field for searching.

We let users filter plugins based on this field.

You can set this field by defining categories in your manifest file. The categories "Annotation", "Segmentation", "Image_Processing", "Transformations" and "Visualization" will all map onto the Workflow Step napari hub category. If you would like more categories to be added, please open an issue on the npe2 repo.

Image Modality

This is a list of Image Modalities that your plugin supports.

We display this on the detailed plugin page and the plugin listings.

We index this field for searching.

We let users filter plugins based on this field.

We currently read this field from labels defined in your napari hub configuration file, .napari-hub/config.yml, but this will change in the future as we move towards manifest defined categories.

Supported Data

This is a list of data types that your plugin supports.

We display this on the detailed plugin page.

We let users filter plugins based on this field.

We currently read this field from labels defined in your napari hub configuration file, .napari-hub/config.yml, but this will change in the future as we move towards manifest defined categories.

Plugin Type

Save Extension

Save Layers

Open Extension

Authors

This is a list of authors of the plugin.

We display this on the detailed plugin page and the plugin listings.

We index this field for searching.

If a CITATION.cff file is included in the repository, we will attempt to get author names from it. This will override data in the Authors field taken from PyPI.

We source this from the ["info"]["author"] field of the JSON returned by the PyPI API, which can set by setting the author value in your package metadata.

# setup.cfg
[metadata]
# ...
author=Deep Ganguli
# ...

We currently use regex to split up the author string into individual authors on these characters: ',', '&', ' and '. For example, if the author value was originally 'author 1, author 2', we will split that up into a list containing 'author 1' and 'author 2', similar to the result of setting authors in .napari-hub/config.yml. Any empty strings or strings containing only whitespace existing before and after the splitting process will be removed.

Alternatively, if you have a CITATION.cff file, we will get author names from the given-names and family-names fields or just the name field if given-names and family-names fields don't exist, and override pypi data with that information. given-names and family-names take priority over names. Information gathered from config.yml will override data from CITATION.cff.

License

This is the SPDX Identifier for the license that the plugin is distributed under.

We display this on the detailed plugin page and the plugin listings.

We support filtering plugins based on whether the plugin is released under an OSI-approved open source license.

We source this from the GitHub Licenses API. If we cannot find one, we will source from ["info"]["license"] field of the JSON returned by the PyPI API, which can be set this by setting the license value in your package metadata.

NOTE: You must use either a valid SPDX Identifier or "Other". If you specify a license here which is not an SPDX Identifier, we will display "Other". You can find the full list of SPDX Identifiers at https://spdx.org/licenses/

# setup.cfg
[metadata]
# ...
license = MIT
# ...

Version

This is the version of the latest release of your plugin.

We display this on the detailed plugin page and the plugin listings.

We source this from the key of the latest release listed under ["releases"] in the PyPI API.

You can set this by setting the version of your Python package. See the Python Packaging User Guide for more info.

NOTE: We strongly encourage plugin developers to use Semantic Versioning, along with Python conventions for pre-releases (see PEP 440).

Python Versions

These are the Python versions your plugin supports.

We display this on the detailed plugin page and the plugin listings.

We support filtering plugins according to the minor versions of Python they support, based on this field. For example, if a plugin developer notes that a plugin supports, Python ">=3.8", then the plugin will be tagged with Python versions 3.8 and 3.9.

We source this from ["info"]["requires_python"] field of the JSON returned by the PyPI API.

You can set this by setting the python_requires value for your Python package in your package metadata.

# setup.cfg
[metadata]
# ...
python_requires = '>=3.8'
# ...

Operating System

These are the operating systems your plugin supports.

We display this on the detailed plugin page and the plugin listings. We support filtering plugins based on this value.

We source this from the list of classifiers in the ["info"]["classifiers"] field of the JSON returned by the PyPI API.

You can set this by setting the relevant "Operating System" classifiers for your Python package in your package metadata.

# setup.cfg
[metadata]
# ...
classifier =
  Operating System :: MacOS :: MacOS X
  Operating System :: Microsoft :: Windows
  Operating System :: POSIX :: Linux
# ...
# setup.cfg
[metadata]
# ...
classifier =
  Operating System :: OS Independent
# ...

Requirements

This is a list of Python packages that are required by your plugin.

We display this on the detailed plugin page.

We source this from the list of requirements in the ["info"]["requires_dist"] field of the JSON returned by the PyPI API. We do not display requirements for napari-plugin-engine or napari.

You can set this by setting the install_requires value for your Python package in your package metadata.

# setup.cfg
[options]
# ...
install_requires =
  dataclasses==0.6
  h5py
  jsonschema
  matplotlib
  napari-plugin-engine
  numpy != 1.13.0
  pandas >= 0.23.4
  read_roi
  regional
  scikit-image >= 0.14.0
  scikit-learn
  scipy
  sympy ~= 1.5.0
  trackpy
  validators
  xarray >= 0.14.1
# ...

Project Site

This is a link to the main project site for your plugin.

We display this on the detailed plugin page.

We source this from ["info"]["home_page"] field of the JSON returned by the PyPI API, which can be set by setting the url value for your Python package in your package metadata.

# setup.cfg
[metadata]
# ...
url = https://spacetx-starfish.readthedocs.io/en/latest/
project_urls =
    Bug Tracker = https://github.com/spacetx/starfish/issues
    Documentation = https://spacetx-starfish.readthedocs.io/en/latest/
    Source Code = https://github.com/spacetx/starfish
# ...

NOTE: If we detect that a GitHub repository is the target of the url value, we will assign this URL to the "Source Code" field instead of the Project Site field.

Documentation

This is a link to further documentation for your plugin.

We display this on the detailed plugin page.

We source this from ["info"]["project_urls"]["Documentation"] field of the JSON returned by the PyPI API, which can be set by adding a Documentation link to the project_urls value for your Python package in your package metadata.

# setup.cfg
[metadata]
# ...
url = https://spacetx-starfish.readthedocs.io/en/latest/
project_urls =
    Bug Tracker = https://github.com/spacetx/starfish/issues
    Documentation = https://spacetx-starfish.readthedocs.io/en/latest/
    Source Code = https://github.com/spacetx/starfish
    User Support = https://forum.image.sc/tag/starfish
# ...

User Support

This is a link to user support for your plugin.

We display this on the detailed plugin page.

We source this from ["info"]["project_urls"]["User Support"] field of the JSON returned by the PyPI API, which can be set by adding a User Support link to the project_urls value for your Python package in your package metadata.

# setup.cfg
[metadata]
# ...
url = https://spacetx-starfish.readthedocs.io/en/latest/
project_urls =
    Bug Tracker = https://github.com/spacetx/starfish/issues
    Documentation = https://spacetx-starfish.readthedocs.io/en/latest/
    Source Code = https://github.com/spacetx/starfish
    User Support = https://forum.image.sc/tag/starfish
# ...

Report Issues

This is a link to where users can report issues with your plugin.

We display this on the detailed plugin page.

We source this from ["info"]["project_urls"]["Bug Tracker"] field of the JSON returned by the PyPI API, which can be set by adding a Bug Tracker link to the project_urls value for your Python package in your package metadata.

# setup.cfg
[metadata]
# ...
url = https://spacetx-starfish.readthedocs.io/en/latest/
project_urls =
    Bug Tracker = https://github.com/spacetx/starfish/issues
    Documentation = https://spacetx-starfish.readthedocs.io/en/latest/
    Source Code = https://github.com/spacetx/starfish
    User Support = https://forum.image.sc/tag/starfish
# ...

Twitter

This is a link to the Twitter feed for your plugin.

We display this on the detailed plugin page.

We source this from ["info"]["project_urls"]["Twitter"] field of the JSON returned by the PyPI API, which you can set by adding a Twitter link to the project_urls value for your Python package in your package metadata.

# setup.cfg
[metadata]
# ...
project_urls =
  Twitter = https://twitter.com/napari_imaging
# ...

Source Code

This is a link to the source code repository for your plugin.

We display this on the detailed plugin page.

We source this from ["info"]["project_urls"]["Source Code"] field of the JSON returned by the PyPI API.

You can set this by adding a Source Code link to the project_urls value for your Python package in your package metadata. We will also source this from the url field if the target is a GitHub repository.

# setup.cfg
[metadata]
# ...
url = https://spacetx-starfish.readthedocs.io/en/latest/
project_urls =
    Bug Tracker = https://github.com/spacetx/starfish/issues
    Documentation = https://spacetx-starfish.readthedocs.io/en/latest/
    Source Code = https://github.com/spacetx/starfish
    User Support = https://forum.image.sc/tag/starfish
# ...

Citation

The napari hub supports display and downloading of citation information in a variety of formats for plugins which have specified citation information in a CITATION.cff file using the Citation File Format.

Learn more about the Citation File Format at https://citation-file-format.github.io/

Visibility

This field lets you control the visibility of your plugin on the napari hub and can be set in the npe2 manifest. We support two levels of visibility:

  • public (default): plugin is available through search and plugin listings
  • hidden: plugin details page is available, but the plugin does not show up in search
# napari.yaml
# ...
visibility: public

# ...

Note: You must release a new version of your plugin if you update the visibility in order for the change to take effect.

Removing your plugin from both napari and the napari hub

As shown, the visibility of a plugin in the napari hub is determined by its level of visibility, which can be set to public, or hidden. However, regardless of its visibility level, any Python package on PyPI or conda with the framework :: napari trove classifier will appear in the napari plugin installation dialog. This means that even if a plugin is hidden or disabled in the napari hub, it can still be installed via the plugin installation dialog as long as it has the framework :: napari classifier.

Additionally, if a package with the framework :: napari classifier links to a private code repository, it will default to being public on the napari hub. This is because the hub cannot access the underlying configuration files in the repository.

If you want to completely remove a plugin from the napari hub and the napari plugin installer, you need to remove the framework :: napari classifier from the project metadata. Once this classifier is removed, the Python package will be completely hidden from the napari hub and the plugin installer. However, it will still work as a plugin in napari when manually installed via pip install <plugin>.

To remove the framework :: napari classifier, you can delete it from the project configuration file. Here's an example of how to do this in both a setup.cfg and pyproject.toml file:

# setup.cfg file
[metadata]
classifiers = 
    Framework :: napari # Remove this entry to hide your plugin
    Programming Language :: Python
    # And so on...
# pyproject.toml
[project]
classifiers = [
    "Framework :: napari", # Remove this entry to hide your plugin
    "Programming Language :: Python",
    # And so on...
]

Note: You must release a new version of your plugin in order for the change to take effect.

If you do not want your plugin to be discoverable in any way, but want to keep the framework classifier, please open an issue on the npe2 repo with your motivation, so that the napari core devs can discuss the addition of a new visibility setting.