builders

package
v0.1.11 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Aug 4, 2025 License: Apache-2.0 Imports: 8 Imported by: 0

README

MCP Tools Builder Framework

This is the tool builder framework for StreamNative MCP Server, designed to provide unified management and construction of MCP tools.

Overview

The tool builder framework separates tool creation logic from server registration logic, providing an extensible and testable architecture for managing MCP tools.

Core Components

1. ToolBuilder Interface

The core interface that all tool builders must implement:

type ToolBuilder interface {
    GetName() string
    GetRequiredFeatures() []string
    BuildTools(ctx context.Context, config ToolBuildConfig) ([]server.ServerTool, error)
    Validate(config ToolBuildConfig) error
}
2. BaseToolBuilder

An abstract builder that provides basic implementation:

type BaseToolBuilder struct {
    metadata         ToolMetadata
    requiredFeatures []string
}
3. ToolRegistry

A registry that manages all tool builders:

type ToolRegistry struct {
    mu       sync.RWMutex
    builders map[string]ToolBuilder
    metadata map[string]ToolMetadata
}
4. Configuration Management

Supports flexible configuration management:

type ToolBuildConfig struct {
    ReadOnly bool
    Features []string
    Options  map[string]interface{}
}

Usage Examples

Basic Usage
package main

import (
    "context"
    "fmt"
    
    "github.com/mark3labs/mcp-go/server"
    "github.com/streamnative/streamnative-mcp-server/pkg/mcp/builders"
)

func main() {
    // Create registry
    registry := builders.NewToolRegistry()
    
    // Register builders (actual builder implementation needed here)
    // registry.Register(kafkaBuilders.NewKafkaConnectToolBuilder())
    
    // Configure tools
    configs := map[string]builders.ToolBuildConfig{
        "kafka_connect": {
            ReadOnly: false,
            Features: []string{"kafka_admin_kafka_connect"},
        },
    }
    
    // Build all tools
    tools, err := registry.BuildAll(configs)
    if err != nil {
        panic(err)
    }
    
    // Create MCP server and add tools
    mcpServer := server.NewMCPServer("example", "1.0.0")
    for _, tool := range tools {
        mcpServer.AddTool(tool.Tool, tool.Handler)
    }
    
    fmt.Printf("Successfully added %d tools\n", len(tools))
}
Configuration-Driven Usage
// Use configuration file
config, err := builders.LoadToolsConfig("tools.yaml")
if err != nil {
    panic(err)
}

// Convert to build configurations
buildConfigs := config.ToToolBuildConfigs()

// Build tools
tools, err := registry.BuildAll(buildConfigs)
if err != nil {
    panic(err)
}
Configuration File Example
# tools.yaml
tools:
  kafka_connect:
    enabled: true
    readOnly: false
    features:
      - "kafka_admin_kafka_connect"
    options:
      timeout: "30s"
      
  pulsar_functions:
    enabled: true
    readOnly: true
    features:
      - "pulsar_admin_functions"
    options:
      maxRetries: 3

Creating Custom Builders

1. Implement the ToolBuilder Interface
type MyToolBuilder struct {
    *builders.BaseToolBuilder
}

func NewMyToolBuilder() *MyToolBuilder {
    metadata := builders.ToolMetadata{
        Name:        "my_tool",
        Version:     "1.0.0",
        Description: "My custom tool",
        Category:    "custom",
        Tags:        []string{"custom", "example"},
    }
    
    features := []string{"my_feature"}
    
    return &MyToolBuilder{
        BaseToolBuilder: builders.NewBaseToolBuilder(metadata, features),
    }
}
2. Implement the BuildTools Method
func (b *MyToolBuilder) BuildTools(ctx context.Context, config builders.ToolBuildConfig) ([]server.ServerTool, error) {
    // Validate configuration
    if err := b.Validate(config); err != nil {
        return nil, err
    }
    
    // Check features
    if !b.HasAnyRequiredFeature(config.Features) {
        return nil, nil // Return empty list
    }
    
    // Build tools
    tool := b.buildMyTool()
    handler := b.buildMyHandler(config.ReadOnly)
    
    return []server.ServerTool{
        {
            Tool:    tool,
            Handler: handler,
        },
    }, nil
}
3. Register the Builder
registry := builders.NewToolRegistry()
registry.Register(NewMyToolBuilder())

Testing

The framework provides complete test coverage:

cd pkg/mcp/builders
go test -v

Configuration Options

The framework provides various configuration options:

config := builders.NewToolBuildConfig(
    builders.WithReadOnly(true),
    builders.WithFeatures("feature1", "feature2"),
    builders.WithTimeout(30*time.Second),
    builders.WithMaxRetries(3),
    builders.WithOption("custom", "value"),
)

Best Practices

  1. Keep it Simple: Each builder should only be responsible for one tool or a group of closely related tools
  2. Error Handling: Provide clear error messages for easy debugging
  3. Configuration Validation: Validate all required configurations before building
  4. Thread Safety: Ensure builders can be used safely concurrently
  5. Test Coverage: Write comprehensive unit tests for each builder

Architecture Benefits

  • Separation of Concerns: Tool creation and server registration logic are separated
  • Reusability: Builders can be reused in different contexts
  • Testability: Each builder can be tested independently
  • Extensibility: New tools only need to implement the interface
  • Configuration-Driven: Supports managing tools through configuration files

Next Steps

  1. Implement specific tool builders (such as Kafka Connect)
  2. Integrate into existing tool registration functions
  3. Add more configuration options and features
  4. Improve documentation and examples

Version: 1.0.0
Created: 2025-08-01

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type BaseToolBuilder

type BaseToolBuilder struct {
	// contains filtered or unexported fields
}

BaseToolBuilder provides common functionality implementation for all builders It serves as the foundation for concrete tool builder implementations

func NewBaseToolBuilder

func NewBaseToolBuilder(metadata ToolMetadata, features []string) *BaseToolBuilder

NewBaseToolBuilder creates a new base tool builder instance

func (*BaseToolBuilder) GetMetadata

func (b *BaseToolBuilder) GetMetadata() ToolMetadata

GetMetadata returns the tool metadata

func (*BaseToolBuilder) GetName

func (b *BaseToolBuilder) GetName() string

GetName returns the builder name

func (*BaseToolBuilder) GetRequiredFeatures

func (b *BaseToolBuilder) GetRequiredFeatures() []string

GetRequiredFeatures returns the list of required features

func (*BaseToolBuilder) HasAnyRequiredFeature

func (b *BaseToolBuilder) HasAnyRequiredFeature(features []string) bool

HasAnyRequiredFeature checks if any required feature is present

func (*BaseToolBuilder) Validate

func (b *BaseToolBuilder) Validate(config ToolBuildConfig) error

Validate validates the builder configuration It checks if the configuration contains at least one required feature

type ConfigOption

type ConfigOption func(*ToolBuildConfig)

ConfigOption defines the function type for configuration options

func WithFeatures

func WithFeatures(features ...string) ConfigOption

WithFeatures sets the feature list

func WithMaxRetries

func WithMaxRetries(maxRetries int) ConfigOption

WithMaxRetries sets the maximum retry count option

func WithOption

func WithOption(key string, value interface{}) ConfigOption

WithOption sets a configuration option

func WithReadOnly

func WithReadOnly(readOnly bool) ConfigOption

WithReadOnly sets the read-only mode

func WithTimeout

func WithTimeout(timeout time.Duration) ConfigOption

WithTimeout sets the timeout option

type ToolBuildConfig

type ToolBuildConfig struct {
	ReadOnly bool                   `json:"readOnly"`
	Features []string               `json:"features"`
	Options  map[string]interface{} `json:"options,omitempty"`
}

ToolBuildConfig contains all configuration information needed to build tools It specifies build parameters such as read-only mode, features, and options

func NewToolBuildConfig

func NewToolBuildConfig(options ...ConfigOption) ToolBuildConfig

NewToolBuildConfig creates a new tool build configuration

type ToolBuilder

type ToolBuilder interface {
	// GetName returns the builder name
	GetName() string

	// GetRequiredFeatures returns the list of required features
	GetRequiredFeatures() []string

	// BuildTools builds and returns a list of server tools
	BuildTools(ctx context.Context, config ToolBuildConfig) ([]server.ServerTool, error)

	// Validate validates the builder configuration
	Validate(config ToolBuildConfig) error
}

ToolBuilder defines the interface that all tool builders must implement It specifies the methods required for building and managing MCP tools

type ToolConfig

type ToolConfig struct {
	Enabled  bool                   `yaml:"enabled"`
	ReadOnly bool                   `yaml:"readOnly"`
	Features []string               `yaml:"features"`
	Options  map[string]interface{} `yaml:"options,omitempty"`
}

ToolConfig represents the configuration for a single tool

func (*ToolConfig) Validate

func (tc *ToolConfig) Validate() error

Validate validates the tool configuration

type ToolHandlerFunc

type ToolHandlerFunc func(ctx context.Context, request mcp.CallToolRequest) (*mcp.CallToolResult, error)

ToolHandlerFunc defines the tool handler function type It maintains consistency with server.ToolHandlerFunc

type ToolMetadata

type ToolMetadata struct {
	Name         string   `json:"name"`
	Version      string   `json:"version"`
	Description  string   `json:"description"`
	Category     string   `json:"category"`
	Dependencies []string `json:"dependencies,omitempty"`
	Tags         []string `json:"tags,omitempty"`
}

ToolMetadata describes the basic information and attributes of a tool It contains descriptive information about the tool builder

type ToolRegistry

type ToolRegistry struct {
	// contains filtered or unexported fields
}

ToolRegistry manages the registration and building of all tool builders It provides centralized management for tool builder registration and tool construction

func NewToolRegistry

func NewToolRegistry() *ToolRegistry

NewToolRegistry creates a new tool registry instance

func (*ToolRegistry) BuildAll

func (r *ToolRegistry) BuildAll(configs map[string]ToolBuildConfig) ([]server.ServerTool, error)

BuildAll builds tools for all specified configurations Returns all successfully built tools and any errors encountered

func (*ToolRegistry) BuildAllWithFeatures

func (r *ToolRegistry) BuildAllWithFeatures(readOnly bool, features []string) ([]server.ServerTool, error)

BuildAllWithFeatures builds all relevant tools based on the feature list Automatically creates configuration for each builder

func (*ToolRegistry) BuildSingle

func (r *ToolRegistry) BuildSingle(name string, config ToolBuildConfig) ([]server.ServerTool, error)

BuildSingle builds tools for a single tool builder

func (*ToolRegistry) Clear

func (r *ToolRegistry) Clear()

Clear removes all registered builders

func (*ToolRegistry) Count

func (r *ToolRegistry) Count() int

Count returns the number of registered builders

func (*ToolRegistry) GetBuilder

func (r *ToolRegistry) GetBuilder(name string) (ToolBuilder, bool)

GetBuilder retrieves the tool builder with the specified name

func (*ToolRegistry) GetMetadata

func (r *ToolRegistry) GetMetadata(name string) (ToolMetadata, bool)

GetMetadata retrieves the metadata for the specified builder

func (*ToolRegistry) ListBuilders

func (r *ToolRegistry) ListBuilders() []string

ListBuilders returns a list of all registered builder names

func (*ToolRegistry) ListMetadata

func (r *ToolRegistry) ListMetadata() map[string]ToolMetadata

ListMetadata returns metadata for all registered builders

func (*ToolRegistry) MustRegister

func (r *ToolRegistry) MustRegister(builder ToolBuilder)

MustRegister registers a tool builder and panics if it fails

func (*ToolRegistry) Register

func (r *ToolRegistry) Register(builder ToolBuilder) error

Register registers a tool builder Returns an error if the builder already exists

func (*ToolRegistry) Unregister

func (r *ToolRegistry) Unregister(name string) bool

Unregister removes the specified tool builder

type ToolsConfig

type ToolsConfig struct {
	Tools map[string]ToolConfig `yaml:"tools"`
}

ToolsConfig represents the structure of the tools configuration file

func DefaultToolsConfig

func DefaultToolsConfig() *ToolsConfig

DefaultToolsConfig creates a default tool configuration

func (*ToolsConfig) GetEnabledTools

func (tc *ToolsConfig) GetEnabledTools() []string

GetEnabledTools returns the names of all enabled tools

func (*ToolsConfig) IsToolEnabled

func (tc *ToolsConfig) IsToolEnabled(name string) bool

IsToolEnabled checks if the specified tool is enabled

func (*ToolsConfig) SetToolEnabled

func (tc *ToolsConfig) SetToolEnabled(name string, enabled bool)

SetToolEnabled sets the enabled status of a tool

func (*ToolsConfig) ToToolBuildConfigs

func (tc *ToolsConfig) ToToolBuildConfigs() map[string]ToolBuildConfig

ToToolBuildConfigs converts tool configuration to build configurations

func (*ToolsConfig) Validate

func (tc *ToolsConfig) Validate() error

Validate validates the entire tools configuration file

Directories

Path Synopsis

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL