elastic/elasticsearch
Plugin system
Purpose
Plugins extend an Elasticsearch node with new actions, REST handlers, mappers, analyzers, repositories, scripts, engines, ingest processors, security realms, and more. Most major features ship as plugins, including everything under x-pack/.
Directory layout
server/src/main/java/org/elasticsearch/plugins/
├── Plugin.java Base class for all plugins
├── PluginsService.java Loader, classloader isolation
├── PluginsLoader.java On-disk discovery
├── ActionPlugin.java Contributes actions + REST handlers + interceptors
├── SearchPlugin.java Queries, aggregations, suggesters, retrievers
├── MapperPlugin.java Field types and metadata mappers
├── AnalysisPlugin.java Analyzers, tokenizers, filters
├── EnginePlugin.java Replacement Engine implementations
├── RepositoryPlugin.java Snapshot repositories
├── IngestPlugin.java Ingest processors
├── ClusterPlugin.java Allocation deciders, custom metadata
├── DiscoveryPlugin.java Discovery providers
├── NetworkPlugin.java Transport / HTTP replacement
├── ScriptPlugin.java Script engines
├── PersistentTaskPlugin.java Long-running task types
├── ReloadablePlugin.java Hot-reload of secure settings
└── ...
libs/plugin-api/ Public SPI types reused by plugin code
libs/plugin-analysis-api/ Analysis SPI
libs/plugin-scanner/ Compile-time scanner for plugin descriptors
distribution/tools/plugin-cli/ `bin/elasticsearch-plugin` install CLIKey abstractions
| Type | File | Role |
|---|---|---|
Plugin |
server/src/main/java/org/elasticsearch/plugins/Plugin.java |
Base class — lifecycle hooks, components, settings |
PluginsService |
.../plugins/PluginsService.java |
Loads, isolates, and queries plugins |
<X>Plugin interfaces |
.../plugins/<X>Plugin.java |
Capability mixins implemented by Plugin subclasses |
| Plugin descriptor | plugin-descriptor.properties |
Bundled with each plugin: name, version, classname |
Plugin shape
A plugin is a Java module containing a class extending Plugin and zero or more capability interfaces:
public class MyPlugin extends Plugin implements ActionPlugin, MapperPlugin {
@Override
public List<RestHandler> getRestHandlers(Settings settings, ...) {
return List.of(new RestMyAction());
}
@Override
public List<ActionHandler> getActions() {
return List.of(new ActionHandler(MyAction.INSTANCE, TransportMyAction.class));
}
@Override
public Map<String, Mapper.TypeParser> getMappers() {
return Map.of("my_field", MyFieldMapper.PARSER);
}
}The plugin-descriptor file declares the entry-point class, version compatibility, and security policy file.
Loading
PluginsService runs at node startup. It scans modules/ (mandatory, always-on) and plugins/ (optional, installed via bin/elasticsearch-plugin). Each plugin gets its own classloader, isolated from server classes (with a curated set of exported APIs from libs/plugin-api/). The order of loading is dependency-aware via the extended.plugins descriptor field.
Three flavors of plugins
| Flavor | Where | Notes |
|---|---|---|
| Module | modules/ |
Built by the project, ships with the default distribution, always loaded. |
| External plugin | plugins/ |
Built by the project but installed on demand via bin/elasticsearch-plugin install <name>. |
| X-Pack plugin | x-pack/plugin/ |
Built by the project, ships with the default distribution, may require a license. |
In all three cases the underlying Plugin API is the same.
Security model
Plugins run inside the same JVM but with constrained permissions. The legacy SecurityManager-based model is being replaced by Entitlement (libs/entitlement/), a custom security framework that gates JDK calls (file, network, process) per plugin. Plugins declare their needed entitlements in plugin-descriptor.properties (and in JPMS module descriptors).
Stable plugin API (libs/plugin-api)
The publishable plugin API is a deliberate subset of internals — types like Setting, XContentBuilder, BytesReference, ActionListener, IndexModule, ScriptEngine — guaranteed to be ABI-stable across minor versions. Plugin authors should compile against this surface only.
Persistent tasks
Plugins that want to run cluster-wide background work (ML jobs, transforms, ILM, watcher) extend PersistentTaskPlugin. The persistent-task framework (server/src/main/java/org/elasticsearch/persistent/) tracks tasks in cluster state and recovers them after node failures.
Examples
- Smallest interesting external plugin:
plugins/mapper-size(adds the_sizemetadata field). - Analysis plugin:
plugins/analysis-icuwraps Lucene's ICU support. - Repository plugin:
plugins/repository-hdfs. - Comprehensive: any subdirectory of
x-pack/plugin/(security, ml, esql, ilm).
Entry points for modification
- Writing a new plugin? Start from the smallest reference (
plugins/mapper-size) and copy its layout. - Modifying loading?
PluginsServiceandPluginsLoader. - Touching plugin security?
libs/entitlementand theplugin-descriptor.propertiesparser. - Adding a new plugin capability interface? Extend
Plugin-base API inserver/src/main/java/org/elasticsearch/plugins/.
Built by Factory AutoWiki from public repository content. It is a generated preview for codebase exploration, not source-maintained documentation.