[project] name = "docsift" version = "0.5.7" description = "Convert documents once. Give agents only what they need." readme = "README.md" requires-python = ">=3.11" license = { text = "MIT" } authors = [{ name = "Anish Monci Varghese" }] dependencies = [ "typer>=0.12", # Direct, not transitive: typer bundles rich today, but the CLI's progress # renderer depends on it explicitly and should say so. "rich>=13", "pydantic>=2.7", "tiktoken>=0.8", ] keywords = ["pdf", "markdown", "docling", "markitdown", "rag", "llm", "document-conversion"] classifiers = [ "Development Status :: 3 - Alpha", "Intended Audience :: Developers", "License :: OSI Approved :: MIT License", "Programming Language :: Python :: 3.11", "Programming Language :: Python :: 3.12", "Topic :: Text Processing :: Markup :: Markdown", ] [project.optional-dependencies] markitdown = ["markitdown[docx,pptx,xlsx,pdf]>=0.1.1"] docling = ["docling>=2.0"] api = ["fastapi>=0.115", "uvicorn[standard]>=0.30", "python-multipart>=0.0.9"] mcp = ["mcp>=2.0"] all = ["docsift[markitdown]", "docsift[docling]", "docsift[api]", "docsift[mcp]"] [project.scripts] docsift = "docsift.cli.main:app" [project.urls] Homepage = "https://github.com/anishmoncivarghese/docsift" Repository = "https://github.com/anishmoncivarghese/docsift" Changelog = "https://github.com/anishmoncivarghese/docsift/blob/main/CHANGELOG.md" [dependency-groups] dev = [ "pytest>=8.0", "ruff>=0.5", "fpdf2>=2.7", "httpx>=0.27", "openapi-spec-validator>=0.7", ] # Not a real dependency set -- torch and torchvision already arrive with the # docling extra. Declaring them here makes them *direct* requirements, which is # the only way [tool.uv.sources] can redirect them to the CPU index; uv sources # do not apply to transitive dependencies. A group (rather than an extra) keeps # this out of the published wheel's metadata entirely. The Dockerfile syncs it. cpu-torch = [ "torch", "torchvision", ] [build-system] requires = ["hatchling"] build-backend = "hatchling.build" [tool.hatch.build.targets.wheel] packages = ["src/docsift"] [tool.hatch.build.targets.sdist] include = [ "src", "tests", "README.md", "LICENSE", "CHANGELOG.md", "SECURITY.md", "PRIVACY.md", "examples", "pyproject.toml", ] [[tool.uv.index]] # Docling pulls in torch, and the default Linux wheel bundles CUDA runtimes -- # several GB of GPU code that a CPU-only container will never execute. This # index serves the CPU builds instead. `explicit = true` means nothing resolves # here unless [tool.uv.sources] below names it. name = "pytorch-cpu" url = "https://download.pytorch.org/whl/cpu" explicit = true [tool.uv.sources] # Linux only: macOS torch wheels have no CUDA variant to avoid, and pinning the # index there would break local development on Apple silicon. These are uv # development-time sources -- they do not appear in the published wheel's # metadata, so `pip install docsift[docling]` is unaffected. torch = [{ index = "pytorch-cpu", marker = "sys_platform == 'linux'" }] torchvision = [{ index = "pytorch-cpu", marker = "sys_platform == 'linux'" }] [tool.ruff] line-length = 100 src = ["src", "tests"] # Planning documents contain illustrative Python fragments — indented method # bodies, partial call sites — that are not valid standalone modules. Ruff # formats code blocks inside Markdown, so linting them fails CI on prose. extend-exclude = ["docs/superpowers/plans"] [tool.ruff.lint] select = ["E", "F", "I", "UP", "B"] [tool.ruff.lint.flake8-bugbear] # Typer's and FastAPI's documented patterns: typer.Argument()/typer.Option() and # fastapi.File()/fastapi.Form() as parameter defaults are how each framework # declares its inputs; they aren't mutable-default bugs. extend-immutable-calls = ["typer.Argument", "typer.Option", "fastapi.File", "fastapi.Form"] [tool.pytest.ini_options] testpaths = ["tests"] markers = ["integration: needs real conversion engines (may download models)"] addopts = "-m 'not integration'"