Skip to content

Plugin Support via Entry Points #6626

@vgvoleg

Description

@vgvoleg

Current Situation

SQLGlot does not support automatic discovery of dialect plugins. All dialects must be in the sqlglot.dialects package and explicitly listed in DIALECTS.

Proposed Solution

Use Python's standard plugin mechanism - entry points via setuptools. This is the same approach used by pytest, SQLAlchemy, and many other popular Python packages.

Benefits

  1. Standard approach in Python ecosystem
  2. No changes required to plugin package structure
  3. Automatic discovery upon installation
  4. Backward compatible with existing dialects

Proposed Changes

Modify sqlglot/dialects/dialect.py to check entry points when a dialect is not found in the standard modules:

# Add at the top of the file (after imports)
try:
    from importlib.metadata import entry_points
except ImportError:
    # For Python < 3.10
    try:
        from importlib_metadata import entry_points
    except ImportError:
        entry_points = None

# Modify the _try_load method:
@classmethod
def _try_load(cls, key: str | Dialects) -> None:
    if isinstance(key, Dialects):
        key = key.value

    # 1. Try standard sqlglot modules first
    if key in DIALECT_MODULE_NAMES:
        importlib.import_module(f"sqlglot.dialects.{key}")
        return

    # 2. Try entry points (for plugins)
    if entry_points is not None:
        try:
            for entry_point in entry_points(group="sqlglot.dialects", name=key):
                dialect_class = entry_point.load()
                if issubclass(dialect_class, Dialect):
                    return
        except (ImportError, AttributeError, TypeError):
            pass

    # 3. Try direct import (for backward compatibility)
    try:
        importlib.import_module(f"sqlglot.dialects.{key}")
    except ImportError:
        pass

Plugin Example

A plugin would register its dialect like this:

# setup.py
setup(
    name="sqlglot-dialect-customdb",
    entry_points={
        "sqlglot.dialects": [
            "customdb = sqlglot_dialect_customdb.dialect:CustomDB",
        ],
    },
)

Usage:

# No explicit import needed!
from sqlglot import transpile

result = transpile(sql, read="customdb", write="postgres")

Migration

Changes are fully backward compatible:

  • Existing dialects continue to work unchanged
  • Plugins can use entry points
  • Old approach (explicit import) still works

If this proposal is acceptable, I'd be happy to implement it.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions