Skip to content

redhat-developer/rhdh-dynamic-plugin-factory

Repository files navigation

RHDH Dynamic Plugin Factory

A comprehensive tool for building and exporting dynamic plugins for Red Hat Developer Hub (RHDH) from Backstage plugin source code.

Table of Contents

Overview

The RHDH Plugin Factory automates the process of converting Backstage plugins into RHDH dynamic plugins. It provides:

  • Source Repository Management: Clone and checkout plugin source repositories
  • Patch & Overlay System: Apply custom modifications to plugin source code before exporting
  • Dependency Management: Automated yarn installation with TypeScript compilation
  • Dynamic Plugin Packaging: Build, export and package plugins using the RHDH CLI
  • Container Image Publishing: Optionally push to container registries (Quay, OpenShift, etc.)

Installation

The RHDH Plugin Factory is distributed as a pre-built container image. It is recommended to use Podman for all platforms.

Using Pre-built Container Images

Pre-built container images are published to quay.io/rhdh-community/dynamic-plugins-factory with tags corresponding to the version of RHDH they were designed for:

# Pull the latest version
podman pull quay.io/rhdh-community/dynamic-plugins-factory:latest
# Or pull a specific RHDH version
podman pull quay.io/rhdh-community/dynamic-plugins-factory:1.8

Container Requirements

The container requires specific capabilities and device access for building dynamic plugins:

  • Volume Mounts: Mount your configuration, workspace, and/or output directories to the /config, /workspace and /outputs directories respectively
  • Device Access: Mount /dev/fuse for filesystem operations (required for buildah)
  • SELinux Context: Use :z flag for volume mounts on SELinux-enabled systems (RHEL/Fedora/CentOS)

The --device /dev/fuse flag passes the FUSE device from the Linux environment (native on Linux, or from Podman Machine's VM on macOS/Windows) to the container, enabling buildah operations.

Basic Container Usage

podman run --rm -it \
  --device /dev/fuse \
  -v ./config:/config:z \
  -v ./workspace:/workspace:z \
  -v ./outputs:/outputs:z \
  quay.io/rhdh-community/dynamic-plugins-factory:latest \
  --workspace-path <path-to-workspace>

Note: The --config-dir, --repo-path, and --output-dir options use default values of /config, /workspace, and /outputs respectively, which map to your local directories through volume mounts.

Running Locally Without Containers

For local execution without containers, see CONTRIBUTING.md.

Configuration

Directory Structure

The factory expects the following directory structure:

./
├── config/                                   # Configuration directory (Can be set with --config-dir)
│   ├── .env                                  # Optional: Override environment variables
│   ├── source.json                           # Source repository configuration
│   ├── plugins-list.yaml                     # List of plugins to build
│   ├── patches/                              # Optional: Patch files to apply
│   └── <path-to-plugin-in-workspace>/overlays/   # Optional: Files to overlay on plugin source
├── workspace/                                # Source code location (Can be set with --repo-path)
└── outputs/                                  # Build output directory (Can be set with --output-dir)

Configuration Files

1. default.env (Provided)

This file contains required version settings and defaults for RHDH CLI:

# Tooling versions
RHDH_CLI_VERSION="1.8.0"

2. config/source.json (Required for remote repositories)

Defines the source repository to clone:

{
  "repo": "https://github.com/backstage/community-plugins",
  "repo-ref": "main",
}

Fields:

  • repo: Repository URL (HTTPS or SSH)
  • repo-ref: Git reference (branch, tag, or commit SHA)

3. config/plugins-list.yaml (Required)

A list of plugin paths (with respect to root of workspace) to plugins to build along with optional build arguments:

# Simple plugins (no additional arguments)
plugins/todo:
plugins/todo-backend:
# Plugins with embed packages
plugins/scaffolder-backend: --embed-package @backstage/plugin-scaffolder-backend-module-github
# Multiple embed packages
plugins/search-backend: |
  --embed-package @backstage/plugin-search-backend-module-catalog
  --embed-package @backstage/plugin-search-backend-module-techdocs

4. config/.env (Optional)

Override default settings to publish to a remote image registry:

# Registry configuration (required only with --push-images)
REGISTRY_URL=quay.io
REGISTRY_USERNAME=your_username
REGISTRY_PASSWORD=your_password
REGISTRY_NAMESPACE=your_namespace
REGISTRY_INSECURE=false

# Logging
LOG_LEVEL=DEBUG
WORKSPACE_PATH=<path_to_workspace_with_respect_to_plugin_repo_root>

LOG_LEVEL can be set to one of DEBUG, INFO (default), WARN, ERROR, or CRITICAL

WORKSPACE_PATH can be set in lieu of the --workspace-path argument

Patches and Overlays

WARNING: This is a destructive operation

Patches and overlays modify files directly in the --repo-path directory. These operations are destructive and will permanently change the repository contents.

  • When using --use-local with a local repository, patches and overlays WILL modify your local files
  • Consider using version control OR cloning a fresh copy of your repository if you need to preserve the original state

Patches Directory (config/patches/)

Place .patch files to apply modifications to the source code:

config/
└── patches/
    └── 001-fix-dependency.patch

Patches are applied using the override-sources.sh script before building.

See the AWS ECS plugin example config for an example on how patches are applied

Overlays Directory (config/<path-to-plugin-root-with-respect-to-workspace>/overlays/)

Place files that should be copied over the source code:

config/
└── plugins/
    └── my-plugin/
        └── overlay/
            └── custom-config.ts

See the TODO plugin example config and Gitlab plugin example config for an example on using overlays.

Usage

Command-Line Options

Option Default Description
--config-dir /config Configuration directory containing source.json, plugins-list.yaml, patches, and overlays
--repo-path /workspace Path where plugin source code will be cloned/stored
--workspace-path (required) Path to the workspace from repository root (e.g., workspaces/todo)
--output-dir /outputs Directory for build artifacts (.tgz files and container images)
--push-images / --no-push-images --no-push-images Whether to push container images to registry. Defaults to not pushing if no argument is provided
--use-local false Use local repository instead of cloning from source.json
--log-level INFO Logging level: DEBUG, INFO, WARNING, ERROR, CRITICAL
--verbose false Show verbose output with file and line numbers

Understanding Volume Mounts

When using the container, you can mount directories based on your needs:

Volume Mount Required? Purpose When to Use
-v ./config:/config:z Required Configuration files Always - contains your plugins-list.yaml, source.json, patches, and overlays
-v ./workspace:/workspace:z Optional Source code location Only if using --use-local OR if you want to preserve/inspect the cloned/patched remote repository
-v ./outputs:/outputs:z Optional Build artifacts Only if you want the output .tgz files saved locally (otherwise they stay in the container)

Important: These volume mount paths (/config, /workspace, /outputs) correspond to the default values of --config-dir, --repo-path, and --output-dir. If you override these arguments with custom paths, adjust your volume mounts accordingly.

Note: Use the :z flag for systems with SELinux enabled (RHEL/Fedora/CentOS). On other systems, you can omit it.

Container Usage Examples

The following examples demonstrate common use cases with the container image. All examples assume you have the necessary configuration files (source.json, plugins-list.yaml, and optionally patches/overlays) in your configuration directory. See the Configuration section for details.

Minimal example (no local files saved)

This minimal example builds the TODO plugins without saving the workspace or output files locally:

podman run --rm -it \
  --device /dev/fuse \
  -v ./examples/example-config-todo:/config:z \
  quay.io/rhdh-community/dynamic-plugins-factory:latest \
  --workspace-path workspaces/todo

This will clone the repository, build the plugins, and NOT push the result to a remote repository.

Build plugins and save outputs locally

This example builds plugins and saves the .tgz files to your local ./outputs/ directory:

podman run --rm -it \
  --device /dev/fuse \
  -v ./config:/config:z \
  -v ./outputs:/outputs:z \
  quay.io/rhdh-community/dynamic-plugins-factory:latest \
  --workspace-path workspaces/todo

This will clone the repository specified in ./config/source.json, build the plugins listed in ./config/plugins-list.yaml, and save the .tgz files to ./outputs/.

Build and push to registry

This example builds plugins and pushes them directly to a container registry (no local .tgz files saved).

First, create a ./config/.env file with your registry credentials:

REGISTRY_URL=quay.io
REGISTRY_USERNAME=myuser
REGISTRY_PASSWORD=mytoken
REGISTRY_NAMESPACE=mynamespace

Then run the factory with --push-images:

podman run --rm -it \
  --device /dev/fuse \
  -v ./config:/config:z \
  quay.io/rhdh-community/dynamic-plugins-factory:latest \
  --workspace-path workspaces/announcements \
  --push-images

The factory will automatically read the load the environmental variables from ./config/.env.

Using a local repository (skip cloning)

If you already have the source code locally, use the --use-local flag and mount your existing workspace:

podman run --rm -it \
  --device /dev/fuse \
  -v ./config:/config:z \
  -v /path/to/existing-workspace:/workspace:z \
  -v ./outputs:/outputs:z \
  quay.io/rhdh-community/dynamic-plugins-factory:latest \
  --workspace-path path/to/workspace \
  --use-local

Note: When using --use-local, patches and overlays will still be applied to your local repository. Make sure you have backups or are using version control.

Output

Build Artifacts

The factory also produces the following outputs in the directory specified by --output-dir:

outputs/
├── plugin-name-dynamic-1.0.0.tgz           # Plugin tarball
├── plugin-name-dynamic-1.0.0.tgz.integrity # Integrity checksum
└── ...

Container Images

When --push-images is enabled, images are tagged as:

${REGISTRY_URL}/${REGISTRY_NAMESPACE}/plugin-name-dynamic:1.0.0

NOTE: If the repository name (ex: plugin-name-dynamic) in the namespace specified by REGISTRY_NAMESPACE does not exist, the dynamic plugin factory will create a new registry. Depending on the registry specified by REGISTRY_URL, the newly created repository may be private. This will be the case for quay.io.

Examples

The examples directory contains ready-to-use configuration examples demonstrating different use cases and features.

Example Description Details
TODO Basic workspace with custom scalprum-config View README
GitLab Overlays for non-BCP workspace format View README
AWS ECS Patches and embed packages in plugins-list.yaml View README

Quick Example: TODO Workspace

Build the TODO plugin from Backstage community plugins:

podman run --rm -it \
  --device /dev/fuse \
  -v ./examples/example-config-todo:/config:z \
  quay.io/rhdh-community/dynamic-plugins-factory:latest \
  --workspace-path workspaces/todo \
  --no-push-images

This example includes:

  • Custom scalprum-config.json configuration
  • Standard Backstage Community Plugins (BCP) workspace format
  • Both frontend and backend plugins in the workspace

For detailed instructions, package verification steps, and additional examples, see the individual README files linked in the table above.

Local Development & Contributing

For users who want to run the factory locally without containers or contribute to the project, see CONTRIBUTING.md.

Resources

To learn more about how dynamic plugins work refer to the dynamic plugins documentation in the RHDH Repository

About

Container toolbox for creating dynamic plugins for RHDH. NO OFFICIAL SUPPORT.

Resources

License

Contributing

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Contributors 3

  •  
  •  
  •