Packages
ragex
0.34.1
0.36.3
0.36.2
0.36.1
0.36.0
0.35.0
0.34.1
0.34.0
0.33.2
0.33.1
0.33.0
0.32.2
0.32.1
0.32.0
0.31.0
0.30.0
0.29.3
0.29.2
0.29.1
0.29.0
0.28.0
0.27.1
0.27.0
0.26.3
0.26.2
0.26.1
0.26.0
0.25.1
0.25.0
0.24.3
0.24.2
0.24.1
0.24.0
0.23.3
0.23.2
0.23.1
0.23.0
0.22.0
0.21.0
0.20.0
0.19.0
0.18.5
0.18.4
0.18.2
0.18.1
0.18.0
0.17.3
0.17.2
0.17.1
0.17.0
0.16.0
0.15.0
0.14.1
0.14.0
0.13.0
0.12.0
0.11.0
0.10.1
0.10.0
0.9.1
0.9.0
0.8.1
0.8.0
0.7.0
0.6.2
0.6.1
0.6.0
0.5.0
0.4.1
0.4.0
0.3.1
0.3.0
0.2.5
0.2.4
0.2.3
0.2.2
0.2.1
0.2.0
Hybrid Retrieval-Augmented Generation (RAG) system for multi-language codebase analysis. MCP server combining static analysis, knowledge graphs, semantic search with local ML, and advanced graph algorithms for AI-powered code understanding.
Current section
Files
Jump to
Current section
Files
stuff/docs/CUSTOM_PLUGINS.md
# Writing Custom Plugins for Ragex
Ragex features an **Extended Plugin Architecture** (`Ragex.Plugin` & `Ragex.Plugin.Registry`) that allows developers and teams to create custom MCP tools, code analyzers, and service integrations without modifying Ragex core files.
### Built-in Domain Plugins
Ragex comes pre-packaged with modular domain plugins:
- **`Ragex.Plugins.GraphAnalytics`**: Knowledge Graph entity lookup & centrality algorithms.
- **`Ragex.Plugins.GitArchaeology`**: Line-by-line git blame, history, PR details, and co-change coupling.
- **`Ragex.Plugins.CodeQuality`**: Code smell detection, dead code analysis, and duplication scanner.
- **`Ragex.Plugins.SecurityAudit`**: CWE security vulnerability scanner and secret checker.
- **`Ragex.Plugins.URLAnalyzer`**: URL analysis for remote Git repositories, web pages, and API specs.
---
## ๐ Quick Start: Scaffolding a New Plugin
Ragex provides a built-in Mix task to generate plugin scaffolds and unit test files:
```bash
mix ragex.plugin SecurityAuditor --tool scan_vulnerabilities --description "Scans project files for custom security compliance rules"
```
### Generated Files
1. **Plugin Implementation**: `lib/ragex/plugins/security_auditor.ex`
2. **Unit Test File**: `test/ragex/plugins/security_auditor_test.exs`
---
## ๐ The `Ragex.Plugin` Behaviour Contract
All plugins implement the `@behaviour Ragex.Plugin` contract:
```elixir
defmodule MyCompany.Plugins.JiraIntegration do
@behaviour Ragex.Plugin
@doc """
Returns plugin metadata.
"""
@impl true
def info do
%{
id: :jira_integration,
name: "Jira Issue Tracker",
version: "1.0.0",
description: "Integrates Ragex with Jira to link code elements to active tickets.",
author: "DevOps Team",
category: :integration,
dependencies: [],
priority: 50,
capabilities: [:jira_sync]
}
end
@doc """
Returns MCP tool schemas provided by this plugin.
"""
@impl true
def tools do
[
%{
name: "get_jira_ticket",
description: "Retrieves details for a Jira ticket by key.",
inputSchema: %{
type: "object",
properties: %{
ticket_key: %{
type: "string",
description: "Jira ticket ID (e.g. PROJ-1234)"
}
},
required: ["ticket_key"]
},
destruction_level: :none
}
]
end
@doc """
Executes a tool call requested by an MCP client or AI agent.
"""
@impl true
def execute("get_jira_ticket", %{"ticket_key" => key} = _args) do
# Fetch ticket info from your external API or internal service
{:ok, %{ticket_key: key, status: "IN_PROGRESS", assignee: "alice@example.com"}}
end
def execute(tool_name, _args) do
{:error, "Unknown tool '\#{tool_name}' for JiraIntegration plugin"}
end
@doc """
Optional initialization callback invoked when the plugin is registered.
"""
@impl true
def init(opts) do
# Perform startup configuration checks or service connections
:ok
end
end
```
---
## โ๏ธ Plugin Registration & Configuration
Plugins can be registered automatically at application startup or dynamically at runtime.
### 1. Configuration (`config/config.exs`)
Add your plugin module to the `:plugins` list in your application configuration:
```elixir
config :ragex,
plugins: [
MyCompany.Plugins.JiraIntegration,
MyCompany.Plugins.DockerScanner
]
```
### 2. Runtime Registration
Register plugins programmatically at any time:
```elixir
# Register plugin
:ok = Ragex.Plugin.Registry.register_plugin(MyCompany.Plugins.JiraIntegration)
# Unregister plugin
:ok = Ragex.Plugin.Registry.unregister_plugin(:jira_integration)
```
### 3. Hot Enabling & Disabling
Plugins can be enabled or disabled on the fly without restarting the server:
```elixir
# Disable plugin temporarily
Ragex.Plugin.Registry.disable_plugin(:jira_integration)
# Re-enable plugin
Ragex.Plugin.Registry.enable_plugin(:jira_integration)
```
---
## ๐ก Listening for System Events (`handle_event/2`)
Plugins can subscribe to system lifecycle events by implementing the optional `handle_event/2` callback:
```elixir
defmodule MyCompany.Plugins.EventNotifier do
@behaviour Ragex.Plugin
@impl true
def info do
%{
id: :event_notifier,
name: "Event Notifier",
version: "1.0.0",
description: "Sends slack notifications on security alerts.",
category: :integration,
dependencies: [],
priority: 90,
capabilities: [:slack_notify]
}
end
@impl true
def tools, do: []
@impl true
def execute(_tool, _args), do: {:error, :no_tools}
@impl true
def handle_event(:security_alert, %{file: file, issue: issue}) do
# React to security alert event
Logger.warning("Security alert on \#{file}: \#{issue}")
:ok
end
def handle_event(_event_name, _payload), do: :ok
end
```
Broadcasting events across plugins:
```elixir
Ragex.Plugin.EventBus.broadcast(:security_alert, %{file: "lib/app.ex", issue: "Hardcoded key"})
```
Custom plugins can leverage the full range of Ragex internal services:
### 1. Knowledge Graph Queries (`Ragex.Graph.Store`)
```elixir
# Query nodes or relationships
nodes = Ragex.Graph.Store.query_nodes(:function, %{module: "MyApp.Account"})
```
### 2. Directory Code Analysis (`Ragex.Analyzers.Directory`)
```elixir
# Execute AST code analysis on target directory
{:ok, summary} = Ragex.Analyzers.Directory.analyze_directory("/path/to/target")
```
### 3. AI Providers & Generation (`Ragex.AI.Provider.Registry`)
```elixir
# Call configured AI provider (Anthropic, OpenAI, Ollama, DeepSeek)
{:ok, provider} = Ragex.AI.Provider.Registry.get_provider()
{:ok, response} = provider.generate("Summarize code architecture", context)
```
---
## ๐งช Testing Your Plugin
Scaffolded plugins include ExUnit test templates out of the box. You can test your plugin isolated or via `Ragex.Plugin.Registry`:
```elixir
defmodule MyCompany.Plugins.JiraIntegrationTest do
use ExUnit.Case, async: true
alias MyCompany.Plugins.JiraIntegration
alias Ragex.Plugin.Registry, as: PluginRegistry
test "returns metadata and tool definitions" do
info = JiraIntegration.info()
assert info.id == :jira_integration
tools = JiraIntegration.tools()
assert hd(tools).name == "get_jira_ticket"
end
test "executes tool via plugin registry" do
start_supervised!(PluginRegistry)
PluginRegistry.register_plugin(JiraIntegration)
assert {:ok, %{status: "IN_PROGRESS"}} =
PluginRegistry.dispatch_tool("get_jira_ticket", %{"ticket_key" => "PROJ-123"})
end
end
```
Run tests with:
```bash
mix test test/ragex/plugins/
```