> ## Documentation Index
> Fetch the complete documentation index at: https://docs.formae.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Overview

> Build plugins that let formae manage any infrastructure with an API, using the Go plugin SDK.

formae is designed to be highly extensible. It uses a flexible yet simple plugin model to allow engineers to add support for technologies that aren't yet supported.

## Policy

**The following policy defines the architectural and licensing expectations for plugins.**

Plugins are independent works developed and distributed separately from formae components.

Plugins execute as separate processes or remote services and communicate with formae components exclusively through documented public interfaces. Plugins are not loaded, linked, or executed in-process.

Plugin developers may license their plugins under any license of their choosing, including open-source or proprietary licenses. Such licenses apply only to the plugin itself and do not affect the licensing of formae components or other plugins.

Plugins must not impose license terms, usage restrictions, or distribution obligations on formae components, their source code, or their users beyond those explicitly agreed in writing.

No formae component is a derivative work of any plugin, and no plugin is a derivative work of any formae component.

## Plugin SDK

The formae Plugin SDK lets you extend formae to manage any infrastructure that exposes any sort of an API. Plugins implement CRUD operations (Create, Read, Update, Delete) and discovery for resource types that formae doesn't support out of the box.

## When to build a plugin

Build a plugin when you need formae to manage resources in a system it doesn't already support:

* An infrastructure platform (SFTP servers, databases, message queues)
* A SaaS platform with an API (monitoring tools, CI/CD systems, DNS providers)
* Internal systems with custom APIs
* Any system where resources have a lifecycle (create, modify, delete)

## How plugins work

Plugins run as **separate processes** that communicate with the formae agent. When the agent starts, it discovers installed plugins and spawns them. Each plugin announces its capabilities (supported resource types, rate limits) and the agent routes operations to the appropriate plugin.

```mermaid theme={"languages":{"custom":["/languages/pkl.json"]}}
flowchart LR
  agent["<b>formae agent</b><br/>• Discovers plugins<br/>• Routes requests<br/>• Enforces rate limits"]:::agentNode
  plugin["<b>Your plugin</b><br/>• Announces capabilities<br/>• Handles CRUD<br/>• Returns results"]:::pluginNode

  agent -->|requests| plugin
  plugin -->|results| agent

  classDef agentNode fill:#ffffff,stroke:#FF8201,stroke-width:2px,color:#02024B
  classDef pluginNode fill:#FFF3E6,stroke:#FF8201,stroke-width:2px,color:#02024B
```

This architecture provides:

* **Isolation**: plugin crashes don't affect the agent
* **Independent updates**: update plugins without updating formae
* **Simplicity**: your plugin just implements a Go interface

## What you'll build

After scaffolding a formae plugin project, you'll implement two things:

1. **Resource schemas** (`schema/pkl/*.pkl`): define your resource types in PKL
2. **ResourcePlugin interface** (`plugin.go`): implement CRUD operations and discovery

```go theme={"languages":{"custom":["/languages/pkl.json"]}}
type ResourcePlugin interface {
    // Configuration
    RateLimit() RateLimitConfig
    LabelConfig() LabelConfig
    DiscoveryFilters() []MatchFilter

    // CRUD + Discovery
    Create(context.Context, *CreateRequest) (*CreateResult, error)
    Read(context.Context, *ReadRequest) (*ReadResult, error)
    Update(context.Context, *UpdateRequest) (*UpdateResult, error)
    Delete(context.Context, *DeleteRequest) (*DeleteResult, error)
    Status(context.Context, *StatusRequest) (*StatusResult, error)
    List(context.Context, *ListRequest) (*ListResult, error)
}
```

## Prerequisites

Before building a plugin, you should be familiar with:

* **Go programming**: structs, interfaces, error handling, JSON marshaling
* **Your target system's API**: how to authenticate and perform CRUD operations
* **PKL basics**: for defining resource schemas (see the [PKL cheatsheet](/documentation/reference/pkl-cheatsheet))

## Getting started

The [Tutorial](/plugin-development/tutorial) walks you through building a complete SFTP File plugin from scratch. You'll learn:

1. How to scaffold a plugin project
2. How to define resource schemas in PKL
3. How to implement CRUD operations with proper error handling
4. How to write tests using TDD
5. How to run conformance tests in CI

For quick reference, see the ResourcePlugin interface (full API specification), the manifest format (plugin manifest fields), and the schema reference (PKL annotations for resources).
