Jump to content

Connect Leeroopedia MCP: Equip your AI agents to search best practices, build plans, verify code, diagnose failures, and look up hyperparameter defaults.

Implementation:Apache Paimon FactoryUtil

From Leeroopedia


Knowledge Sources
Domains Plugin System, Service Discovery
Last Updated 2026-02-08 00:00 GMT

Overview

FactoryUtil provides utility methods for discovering and loading Factory implementations using Java's Service Provider Interface.

Description

FactoryUtil is the central component of Paimon's plugin discovery mechanism. It uses Java's ServiceLoader to dynamically discover and instantiate Factory implementations at runtime, enabling a highly extensible architecture without compile-time dependencies.

The class maintains a soft-reference cache of discovered factories per ClassLoader, improving performance by avoiding repeated classpath scanning. The cache uses Caffeine with a maximum size of 100 entries and executes cache operations synchronously to ensure thread safety. Soft references allow the JVM to garbage collect cached entries under memory pressure.

FactoryUtil provides three main discovery patterns: finding a specific factory by identifier and type, discovering all identifiers for a given factory type, and discovering a singleton factory when only one implementation should exist. Each pattern includes comprehensive error handling with clear messages when factories are missing, ambiguous, or multiple implementations exist when only one is expected.

The utility gracefully handles NoClassDefFoundError exceptions during service loading, which commonly occur when optional dependencies are not present on the classpath. This allows Paimon to support many plugin types without requiring all dependencies to be available.

Usage

Use FactoryUtil when you need to discover and instantiate plugin implementations at runtime. This is typically done in framework code that needs to create instances of user-configured components like catalogs, file formats, or connectors. The utility handles all aspects of SPI discovery, validation, and error reporting.

Code Reference

Source Location

Signature

public class FactoryUtil {
    private static final Cache<ClassLoader, List<Factory>> FACTORIES;

    public static <T extends Factory> T discoverFactory(
        ClassLoader classLoader,
        Class<T> factoryClass,
        String identifier)

    public static <T extends Factory> List<String> discoverIdentifiers(
        ClassLoader classLoader,
        Class<T> factoryClass)

    public static <T> List<T> discoverFactories(
        ClassLoader classLoader,
        Class<T> klass)

    public static <T> Optional<T> discoverSingletonFactory(
        ClassLoader classLoader,
        Class<T> klass)
}

Import

import org.apache.paimon.factories.FactoryUtil;

I/O Contract

Inputs

Name Type Required Description
classLoader ClassLoader Yes ClassLoader to use for SPI discovery
factoryClass Class<T> Yes The factory interface class to search for
identifier String Yes The factory identifier to match (for discoverFactory)
klass Class<T> Yes The class to discover instances of

Outputs

Name Type Description
factory T extends Factory The discovered factory instance matching the criteria
identifiers List<String> List of all available factory identifiers for the given type
factories List<T> All discovered instances of the given class
singletonFactory Optional<T> Single factory instance if exactly one exists

Usage Examples

// Discover a specific catalog factory by identifier
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
CatalogFactory catalogFactory = FactoryUtil.discoverFactory(
    classLoader,
    CatalogFactory.class,
    "hive"
);

// Discover all available catalog types
List<String> catalogTypes = FactoryUtil.discoverIdentifiers(
    classLoader,
    CatalogFactory.class
);
System.out.println("Available catalogs: " + catalogTypes);
// Output: [filesystem, hive, jdbc]

// Discover all factories of a given type
List<FileFormatFactory> formatFactories = FactoryUtil.discoverFactories(
    classLoader,
    FileFormatFactory.class
);

// Discover singleton factory (when only one should exist)
Optional<MetricsReporter> reporter = FactoryUtil.discoverSingletonFactory(
    classLoader,
    MetricsReporter.class
);

// Using discovered factory to create instances
String catalogType = options.get("metastore");
CatalogFactory factory = FactoryUtil.discoverFactory(
    classLoader,
    CatalogFactory.class,
    catalogType
);
Catalog catalog = factory.createCatalog(catalogContext);

// Error handling - factory not found
try {
    FactoryUtil.discoverFactory(
        classLoader,
        CatalogFactory.class,
        "nonexistent"
    );
} catch (FactoryException e) {
    // Exception message lists available factory identifiers
    System.err.println(e.getMessage());
}

// Error handling - multiple factories found
try {
    FactoryUtil.discoverSingletonFactory(
        classLoader,
        MetricsReporter.class
    );
} catch (FactoryException e) {
    // Exception message lists ambiguous factory classes
    System.err.println(e.getMessage());
}

// Using with custom classloader
ClassLoader pluginClassLoader = new URLClassLoader(pluginJars);
CustomFactory factory = FactoryUtil.discoverFactory(
    pluginClassLoader,
    CustomFactory.class,
    "custom-implementation"
);

Related Pages

Page Connections

Double-click a node to navigate. Hold to expand connections.
Principle
Implementation
Heuristic
Environment