From f2bd537573f7cc5e3d281d38a043edb1d04d4fdc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mateusz=20Hordy=C5=84ski?= Date: Wed, 18 Sep 2024 18:09:47 +0200 Subject: [PATCH] feat(cli): add basic cli setup with package discovery --- packages/ragbits-cli/README.md | 1 + packages/ragbits-cli/pyproject.toml | 53 +++++++++++++++++++ .../ragbits-cli/src/ragbits/cli/__init__.py | 30 +++++++++++ packages/ragbits-core/src/ragbits/core/cli.py | 20 +++++++ pyproject.toml | 8 ++- uv.lock | 14 +++++ 6 files changed, 124 insertions(+), 2 deletions(-) create mode 100644 packages/ragbits-cli/README.md create mode 100644 packages/ragbits-cli/pyproject.toml create mode 100644 packages/ragbits-cli/src/ragbits/cli/__init__.py create mode 100644 packages/ragbits-core/src/ragbits/core/cli.py diff --git a/packages/ragbits-cli/README.md b/packages/ragbits-cli/README.md new file mode 100644 index 000000000..e9f62f634 --- /dev/null +++ b/packages/ragbits-cli/README.md @@ -0,0 +1 @@ +# Ragbits CLI diff --git a/packages/ragbits-cli/pyproject.toml b/packages/ragbits-cli/pyproject.toml new file mode 100644 index 000000000..66fbeaa9e --- /dev/null +++ b/packages/ragbits-cli/pyproject.toml @@ -0,0 +1,53 @@ +[project] +name = "ragbits-cli" +version = "0.1.0" +description = "A CLI application for ragbits - building blocks for rapid development of GenAI applications" +readme = "README.md" +requires-python = ">=3.10" +license = "MIT" +authors = [ + { name = "deepsense.ai", email = "contact@deepsense.ai"} +] +keywords = [ + "Retrieval Augmented Generation", + "RAG", + "Large Language Models", + "LLMs", + "Generative AI", + "GenAI", + "Prompt Management" +] +classifiers = [ + "Development Status :: 1 - Planning", + "Environment :: Console", + "Intended Audience :: Science/Research", + "License :: OSI Approved :: MIT License", + "Natural Language :: English", + "Operating System :: OS Independent", + "Programming Language :: Python :: 3.10", + "Programming Language :: Python :: 3.11", + "Programming Language :: Python :: 3.12", + "Topic :: Scientific/Engineering :: Artificial Intelligence", + "Topic :: Software Development :: Libraries :: Python Modules", + "Private :: Do Not Upload" +] +dependencies = [ + "typer>=0.12.5", +] + +[project.scripts] +ragbits = "ragbits.cli:main" +rbts = "ragbits.cli:main" + +[build-system] +requires = ["hatchling"] +build-backend = "hatchling.build" + +[tool.hatch.metadata] +allow-direct-references = true + +[tool.hatch.build.targets.wheel] +packages = ["src/ragbits"] + +[tool.pytest.ini_options] +asyncio_mode = "auto" diff --git a/packages/ragbits-cli/src/ragbits/cli/__init__.py b/packages/ragbits-cli/src/ragbits/cli/__init__.py new file mode 100644 index 000000000..9710e486b --- /dev/null +++ b/packages/ragbits-cli/src/ragbits/cli/__init__.py @@ -0,0 +1,30 @@ +import importlib.util +import pkgutil + +from typer import Typer + +import ragbits + +app = Typer() + + +def main(): + """ + Main entry point for the CLI. + + This function registers all the CLI modules in the ragbits packages: + - iterates over every package in the ragbits.* namespace + - it looks for `cli` package / module + - if found it imports the `register` function from the `cli` module and calls it with the `app` object + - register function should add the CLI commands to the `app` object + """ + + cli_enabled_modules = [ + module for module in pkgutil.iter_modules(ragbits.__path__) + if module.ispkg and module.name != "cli" and importlib.util.find_spec(f"ragbits.{module.name}.cli") + ] + for module in cli_enabled_modules: + register_func = importlib.import_module(f"ragbits.{module.name}.cli").register + register_func(app) + + app() diff --git a/packages/ragbits-core/src/ragbits/core/cli.py b/packages/ragbits-core/src/ragbits/core/cli.py new file mode 100644 index 000000000..3e33048b5 --- /dev/null +++ b/packages/ragbits-core/src/ragbits/core/cli.py @@ -0,0 +1,20 @@ +from typer import Typer + + +prompts_app = Typer() + + +@prompts_app.command() +def foo(): + """Placeholder command""" + print("foo") + + +def register(app: Typer) -> None: + """ + Register the CLI commands for the ragbits-core package. + + Args: + app: The Typer object to register the commands with. + """ + app.add_typer(prompts_app, name="prompts") diff --git a/pyproject.toml b/pyproject.toml index f127fe4a2..503cf153d 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -7,7 +7,8 @@ requires-python = ">=3.10" dependencies = [ "ragbits[litellm,local]", "ragbits-dev-kit", - "ragbits-document-search" + "ragbits-document-search", + "ragbits-cli" ] [tool.uv] @@ -23,12 +24,14 @@ dev-dependencies = [ ragbits = { workspace = true } ragbits-dev-kit = { workspace = true } ragbits-document-search = { workspace = true } +ragbits-cli = { workspace = true } [tool.uv.workspace] members = [ "packages/ragbits-core", "packages/ragbits-dev-kit", - "packages/ragbits-document-search" + "packages/ragbits-document-search", + "packages/ragbits-cli" ] [tool.isort] @@ -119,6 +122,7 @@ mypy_path = [ 'packages/ragbits-core/src', 'packages/ragbits-dev-kit/src', 'packages/ragbits-document-search/src', + 'packages/ragbits-cli/src', ] [[tool.mypy.overrides]] diff --git a/uv.lock b/uv.lock index 618aeedaf..7f1bdf013 100644 --- a/uv.lock +++ b/uv.lock @@ -10,6 +10,7 @@ resolution-markers = [ [manifest] members = [ "ragbits", + "ragbits-cli", "ragbits-dev-kit", "ragbits-document-search", "ragbits-workspace", @@ -1763,6 +1764,17 @@ dev = [ { name = "pytest-cov", specifier = "~=5.0.0" }, ] +[[package]] +name = "ragbits-cli" +version = "0.1.0" +source = { editable = "packages/ragbits-cli" } +dependencies = [ + { name = "typer" }, +] + +[package.metadata] +requires-dist = [{ name = "typer", specifier = ">=0.12.5" }] + [[package]] name = "ragbits-dev-kit" version = "0.1.0" @@ -1839,6 +1851,7 @@ version = "0.1.0" source = { virtual = "." } dependencies = [ { name = "ragbits", extra = ["litellm", "local"] }, + { name = "ragbits-cli" }, { name = "ragbits-dev-kit" }, { name = "ragbits-document-search" }, ] @@ -1855,6 +1868,7 @@ dev = [ [package.metadata] requires-dist = [ { name = "ragbits", extras = ["litellm", "local"], editable = "packages/ragbits-core" }, + { name = "ragbits-cli", editable = "packages/ragbits-cli" }, { name = "ragbits-dev-kit", editable = "packages/ragbits-dev-kit" }, { name = "ragbits-document-search", editable = "packages/ragbits-document-search" }, ]