Metadata-Version: 2.4
Name: pygim
Version: 0.1.0.dev2
Summary: Full Python Gimmicks project with all of its sub-projects.
Project-URL: homepage, https://github.com/Debith/pygim
Project-URL: documentation, https://readthedocs.org/projects/pygim/
Project-URL: source, https://github.com/Debith/pygim
Project-URL: download, https://pypi.org/project/pygim/#files
Project-URL: tracker, https://github.com/Debith/pygim/issues
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: Programming Language :: Python
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Programming Language :: Python :: 3.14
Classifier: Topic :: Software Development :: Libraries :: Python Modules
Classifier: Topic :: Software Development :: Quality Assurance
Classifier: Typing :: Typed
Description-Content-Type: text/x-rst
License-File: LICENSE
Requires-Dist: click>=8
Requires-Dist: pyarrow==25.0.*
Requires-Dist: polars>=0.20
Requires-Dist: tabulate>=0.9
Requires-Dist: typing_extensions>=4.0
Provides-Extra: dev
Requires-Dist: pytest; extra == "dev"
Requires-Dist: pytest-xdist; extra == "dev"
Requires-Dist: mypy; extra == "dev"
Requires-Dist: coverage; extra == "dev"
Requires-Dist: coverage[toml]; extra == "dev"
Requires-Dist: pandas; extra == "dev"
Requires-Dist: pybind11; extra == "dev"
Requires-Dist: pyodbc; extra == "dev"
Requires-Dist: ruff; extra == "dev"
Requires-Dist: markdown; extra == "dev"
Provides-Extra: test
Requires-Dist: pytest; extra == "test"
Requires-Dist: pytest-xdist; extra == "test"
Requires-Dist: coverage; extra == "test"
Requires-Dist: coverage[toml]; extra == "test"
Requires-Dist: pyodbc; extra == "test"
Requires-Dist: pyyaml; extra == "test"
Requires-Dist: tomli; python_version < "3.11" and extra == "test"
Requires-Dist: markdown; extra == "test"
Provides-Extra: docs
Requires-Dist: markdown; extra == "docs"
Provides-Extra: pandas
Requires-Dist: pandas; extra == "pandas"
Dynamic: license-file
Dynamic: requires-dist

#######################
Python Gimmicks (pygim)
#######################

| |docs| |downloads| |wheel| |pyversions|

.. |docs| image:: https://readthedocs.org/projects/pygim/badge/
    :target: https://readthedocs.org/projects/pygim
    :alt: Documentation Status

.. |downloads| image:: https://img.shields.io/pypi/dm/pygim.svg
    :alt: PyPI Package monthly downloads
    :target: https://pypi.org/project/pygim/

.. |wheel| image:: https://img.shields.io/pypi/format/pygim.svg
    :alt: PyPI Wheel
    :target: https://pypi.org/project/pygim/

.. |pyversions| image:: https://img.shields.io/pypi/pyversions/pygim.svg


Python Gimmicks is a library that contains magical but useful tools
that can be used to improve productivity of any Python project. The
goal is to use whatever Pythonic means to provide as light-weight
and high-performance solutions as possible.

Installation
============

To install this project, simply write the following command:

.. code-block:: bash

    $ pip install pygim

Command Line Interface
======================

Installing the package also exposes a ``pygim`` command that wraps the
project's housekeeping helpers. Run ``pygim --help`` to see the available
sub-commands, including quick clean-up tools and a shortcut for running the
coverage workflow used in this repository.

.. code-block:: bash

    $ pygim clean-up --all --yes
    Starting clean up in `/your/project/path`
    Excellent! You never see them again!

You can also trigger the test coverage routine in one line:

.. code-block:: bash

    $ pygim show-test-coverage

Both commands accept the same flags described in ``pygim --help``, so you can
mix and match automation-friendly options (like ``--quiet`` or ``--yes``) to
fit your workflow.

Sub-modules
-----------

This library is divided into multiple different smaller packages.

  * pygim: This is the main project that contains the CLI and all the examples.


The ``oo`` command is the AI-flavoured front door. Free text goes to the
assistant; ``oo docs serve`` serves a documentation tree locally with a review
layer on top of every HTML page:

.. code-block:: bash

    $ oo docs serve --dir build/html --rebuild "make html"

Every served page gets a ✎ button (click anywhere, or select text, to leave a
comment); comments append to ``__notes__/site-comments.jsonl`` under the served
root, ready to be read back and acted on. Dropping an image on a page writes it
under ``images/``. ``GET /pages`` lists the site's pages, and ``--rebuild``
reports which pages the rebuild added and removed. Opening a Markdown page
generates its HTML beside it (Mermaid fences become diagrams, ``.md`` links
point at the generated pages) and serves that, so the commenter works on it
and comments key on the HTML page — a design folder is served as it is
written:

.. code-block:: bash

    $ oo docs serve --dir docs/design --host 127.0.0.1

``/`` falls back to the first of ``site/``, ``docs/``,
``build/html/`` or ``docs/_build/html/`` that has an ``index.html`` (override
with ``--index``). It binds all interfaces by default so the page is reachable
via the WSL IP; set ``PYGIM_HOST`` or pass ``--host 127.0.0.1`` for
localhost only.

Persistence (Experimental)
--------------------------

An experimental high-performance persistence layer (DDD-style DataStore) now exists as a C++ extension:

* Strategies: pluggable objects with ``fetch(key)->data|None`` and ``save(key,value)``.
* Optional transformer pipeline (pre-save / post-load) when enabled at construction.
* Optional factory callable to turn raw data into rich entities.
* Native MSSQL strategy (ODBC) with pybind-free core/adapter architecture.
* Fluent ``Query`` for lightweight SQL assembly without manual string concatenation.
* Arrow IPC utilities for zero-copy hand-off between Polars and C++ pipelines.

Example (read):

.. code-block:: python

        from pygim import persistence

        store = persistence.acquire_datastore("Driver={ODBC Driver 18 for SQL Server};Server=localhost;...")

        df = store.load("users")
        print(df)

Write (upsert) example: ``docs/examples/persistence/mssql_write_example.py``.

Architecture Diagram:

See PlantUML: ``docs/design/persistence_class_diagram.puml`` for component relationships.

.. note:: The MSSQL native strategy uses a pybind-free core/adapter split. ODBC headers must be available at build time for native SQL Server support.

Query Security & Dialect Notes
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

Passing a built ``Query`` object directly to ``DataStore.load(query)``
will bind parameters using ODBC. The builder renders
queries via ``MssqlDialect``, emitting ``TOP n`` for SQL Server.

Native Arrow Persist Path
~~~~~~~~~~~~~~~~~~~~~~~~~

Bulk DataFrame persistence is handled inside native bindings via
``DataStore.save(...)``. The strategy prefers Arrow C Data
Interface (``__arrow_c_stream__``) and falls back to IPC serialization only
when needed.

.. code-block:: python

    from pygim import persistence

    conn = "Driver={ODBC Driver 18 for SQL Server};Server=localhost;..."
    store = persistence.acquire_datastore(conn)
    df = generate_polars_dataset(n=100_000)

    metrics = store.save(df, "stress_data")
    print(metrics)



Changelog
=========

See the detailed list of changes in ``CHANGELOG.rst``. For upcoming (unreleased) work, consult the top "Unreleased" section before the next version tag.
