diff --git a/.bandit b/.bandit deleted file mode 100644 index b7df176..0000000 --- a/.bandit +++ /dev/null @@ -1,2 +0,0 @@ -[bandit] -exclude: ./tests diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 07e9d3a..401bce1 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -5,27 +5,23 @@ on: - main pull_request: jobs: - docs: + dist: runs-on: ubuntu-latest steps: - uses: actions/checkout@v6 - - uses: actions/setup-python@v6 + - uses: astral-sh/setup-uv@v7 + - run: uvx --from build pyproject-build --sdist --wheel + - run: uvx twine check dist/* + - uses: actions/upload-artifact@v6 with: - python-version: "3.x" - - run: sudo apt install -y python3-enchant graphviz - - run: python -m pip install sphinxcontrib-spelling - - run: python -m pip install -e '.[docs]' - - run: python -m sphinx -W -b spelling docs docs/_build - dist: + path: dist/* + docs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v6 - - uses: actions/setup-python@v6 - with: - python-version: "3.x" - - run: python -m pip install --upgrade pip build wheel twine readme-renderer - - run: python -m build --sdist --wheel - - run: python -m twine check dist/* + - run: sudo apt-get install -y gettext graphviz + - uses: astral-sh/setup-uv@v7 + - run: uv run --group docs sphinx-build -W -b doctest -b spelling -b html docs docs/_build PyTest: needs: - dist @@ -41,29 +37,28 @@ jobs: django-version: - "5.2" extras: - - "test" + - "" include: - - python-version: "3.x" + - python-version: "3.13" django-version: "5.2" - extras: "test,dramatiq" - - python-version: "3.x" + extras: "--extra dramatiq" + - python-version: "3.13" django-version: "5.2" - extras: "test,celery" - - python-version: "3.x" + extras: "--extra celery" + - python-version: "3.13" django-version: "5.2" - extras: "test,reversion" - - python-version: "3.x" + extras: "--extra reversion" + - python-version: "3.13" django-version: "5.2" - extras: "test,graphviz,dramatiq" + extras: "--extra graphviz --extra dramatiq" steps: - uses: actions/checkout@v6 - - uses: actions/setup-python@v6 + - run: sudo apt install -y graphviz redis-server + - uses: astral-sh/setup-uv@v7 with: python-version: ${{ matrix.python-version }} - - run: sudo apt install -y graphviz redis-server - - run: python -m pip install "django==${{ matrix.django-version }}.*" - - run: python -m pip install -e .[${{ matrix.extras }}] - - run: python -m pytest + - run: uv run ${{ matrix.extras }} --with Django~=${{ matrix.django-version }}.0 pytest - uses: codecov/codecov-action@v5 with: token: ${{ secrets.CODECOV_TOKEN }} + flags: python-${{ matrix.python-version }}-django-${{ matrix.django-version }} diff --git a/.gitignore b/.gitignore index 46b330a..b6fa679 100644 --- a/.gitignore +++ b/.gitignore @@ -105,3 +105,6 @@ venv.bak/ # flit joeflow/_version.py + +# uv +uv.lock diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index b096530..80bbb45 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -47,6 +47,10 @@ repos: rev: v1.36.4 hooks: - id: djlint-reformat-django + - repo: https://github.com/sphinx-contrib/sphinx-lint + rev: v1.0.2 + hooks: + - id: sphinx-lint ci: autoupdate_schedule: weekly skip: diff --git a/.readthedocs.yaml b/.readthedocs.yaml index 45b3438..d715c7e 100644 --- a/.readthedocs.yaml +++ b/.readthedocs.yaml @@ -3,16 +3,14 @@ # See https://docs.readthedocs.io/en/stable/config-file/v2.html for details version: 2 build: - os: ubuntu-20.04 - tools: - python: "3.11" + os: ubuntu-24.04 apt_packages: - graphviz -sphinx: - configuration: docs/conf.py -python: - install: - - method: pip - path: . - extra_requirements: - - docs + tools: + python: "3" + jobs: + install: + - curl -LsSf https://astral.sh/uv/install.sh | sh + build: + html: + - $HOME/.local/bin/uv run --group docs sphinx-build -b html docs $READTHEDOCS_OUTPUT/html diff --git a/MANIFEST.in b/MANIFEST.in deleted file mode 100644 index 1eeef06..0000000 --- a/MANIFEST.in +++ /dev/null @@ -1 +0,0 @@ -prune tests diff --git a/README.md b/README.md new file mode 100644 index 0000000..841c12a --- /dev/null +++ b/README.md @@ -0,0 +1,20 @@ +

+ + + + Django joeflow: Lean workflow automation for machines with hearts + +
+ Documentation | + Issues | + Changelog | + Funding 💚 +

+ +# joeflow + +_Lean workflow automation for machines with hearts._ + +[![version](https://img.shields.io/pypi/v/joeflow.svg)](https://pypi.python.org/pypi/joeflow/) +[![coverage](https://codecov.io/gh/codingjoe/joeflow/branch/main/graph/badge.svg)](https://codecov.io/gh/codingjoe/joeflow) +[![license](https://img.shields.io/badge/license-BSD-blue.svg)](https://raw.githubusercontent.com/codingjoe/joeflow/main/LICENSE) diff --git a/README.rst b/README.rst deleted file mode 100644 index 8a92672..0000000 --- a/README.rst +++ /dev/null @@ -1,99 +0,0 @@ -joeflow -======= - -**The lean workflow automation framework for machines with heart.** - -.. figure:: docs/img/pexels-photo-1020325.jpeg - :alt: a hand drawn robot - -Joeflow is a free workflow automation framework designed to bring -simplicity to complex workflows. Joeflow written in `Python`_ based on -the world famous `Django`_ web framework. - -Here is a little sample of what a workflow written in joeflow may look -like: - -.. code-block:: python - - from django.core.mail import send_mail - from jowflow.models import WorkflowState - from joeflow import tasks - from joeflow.workflows import Workflow - - - class Shipment(WorkflowState): - email = models.EmailField(blank=True) - shipping_address = models.TextField() - tracking_code = models.TextField() - - class ShippingWorkflow(Shipment, Workflow): - checkout = tasks.StartView(fields=["shipping_address", "email"]) - - ship = tasks.UpdateView(fields=["tracking_code"]) - - def has_email(self): - if self.email: - return [self.send_tracking_code] - - def send_tracking_code(self): - send_mail( - subject="Your tracking code", - message=self.tracking_code, - from_email=None, - recipient_list=[self.email], - ) - - def end(self, task): - pass - - edges = [ - (checkout, ship), - (ship, has_email), - (has_email, send_tracking_code), - (has_email, end), - (send_tracking_code, end), - ] - -Design Principles -================= - -Common sense is better than convention --------------------------------------- - -Joeflow does not follow any academic modeling notation developed by a -poor PhD student who actually never worked a day in their life. -Businesses are already complex which is why Joeflow is rather simple. -There are only two types of tasks – human & machine – as well as edges -to connect them. It’s so simple a toddler (or your CEO) could design a -workflow. - -Lean Automation (breaking the rules) ------------------------------------- - -Things don’t always go according to plan especially when humans are -involved. Even the best workflow can’t cover all possible edge cases. -Joeflow embraces that fact. It allows uses to interrupt a workflow at any -given point and modify it’s current state. All while tracking all -changes. This allows developers to automate the main cases and users -handle manually exceptions. This allows you businesses to ship -prototypes and MVPs of workflows. Improvements can be shipped in -multiple iterations without disrupting the business. - -People ------- - -Joeflow is build with all users in mind. Managers should be able to -develop better workflows. Users should able to interact with the tasks -every single day. And developers should be able to rapidly develop and -test new features. - -Free ----- - -Joeflow is open source and collaboratively developed by industry leaders -in automation and digital innovation. - -*Photo by rawpixel.com from Pexels* - -.. _Python: https://python.org -.. _Django: https://www.djangoproject.com/ diff --git a/SECURITY.md b/SECURITY.md deleted file mode 100644 index f9dc270..0000000 --- a/SECURITY.md +++ /dev/null @@ -1,7 +0,0 @@ -# Security Policy - -## Security contact information - -To report a security vulnerability, please use the -[Tidelift security contact](https://tidelift.com/security). -Tidelift will coordinate the fix and disclosure. diff --git a/docs/conf.py b/docs/conf.py index b7cd569..0b69118 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -61,7 +61,7 @@ def linkcode_resolve(domain, info): master_doc = "index" project = "Joeflow" -html_theme = "alabaster" +html_theme = "furo" intersphinx_mapping = { "python": ("https://docs.python.org/3", None), diff --git a/docs/images/logo-dark.svg b/docs/images/logo-dark.svg new file mode 100644 index 0000000..70a3fb6 --- /dev/null +++ b/docs/images/logo-dark.svg @@ -0,0 +1,17 @@ + + + + + + + + + Django + + + joeflow + + + Lean workflow automation for machines with hearts + + diff --git a/docs/images/logo-light.svg b/docs/images/logo-light.svg new file mode 100644 index 0000000..6a07af7 --- /dev/null +++ b/docs/images/logo-light.svg @@ -0,0 +1,17 @@ + + + + + + + + + Django + + + joeflow + + + Lean workflow automation for machines with hearts + + diff --git a/docs/img/pexels-photo-1020325.jpeg b/docs/img/pexels-photo-1020325.jpeg deleted file mode 100644 index 72e05a1..0000000 Binary files a/docs/img/pexels-photo-1020325.jpeg and /dev/null differ diff --git a/docs/index.rst b/docs/index.rst index db739bc..3d960d4 100644 --- a/docs/index.rst +++ b/docs/index.rst @@ -1,11 +1,25 @@ +.. image:: https://github.com/codingjoe/joeflow/raw/main/docs/images/logo-light.svg + :align: center + :alt: Django joeflow: Lean workflow automation for machines with hearts + :class: only-light + +.. image:: https://github.com/codingjoe/joeflow/raw/main/docs/images/logo-dark.svg + :align: center + :alt: Django joeflow: Lean workflow automation for machines with hearts + :class: only-dark + ======= joeflow ======= -**The lean workflow automation framework for machines with heart.** +**Lean workflow automation for machines with hearts.** + +`Documentation`_ | `Issues`_ | `Changelog`_ | `Funding`_ 💚 -.. image:: img/pexels-photo-1020325.jpeg - :alt: a hand drawn robot +.. _documentation: https://joeflow.rtfd.io/ +.. _issues: https://github.com/codingjoe/joeflow/issues/new/choose +.. _changelog: https://github.com/codingjoe/joeflow/releases +.. _funding: https://github.com/sponsors/codingjoe Joeflow is a free workflow automation framework designed to bring simplicity to complex workflows. Joeflow written in Python_ based on the world famous diff --git a/pyproject.toml b/pyproject.toml index 51fb3bc..8281b64 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -7,7 +7,7 @@ name = "joeflow" authors = [ { name = "Johannes Maron", email = "johannes@maron.family" } ] -readme = "README.rst" +readme = "README.md" license = { file = "LICENSE" } dynamic = ["version", "description"] classifiers = [ @@ -53,6 +53,24 @@ dependencies = [ ] [project.optional-dependencies] +graphviz = [ + "graphviz>=0.18", +] +reversion = [ + "django-reversion", +] +celery = [ + "celery>=4.2.0", +] +dramatiq = [ + "dramatiq>=2.0.0", + "django_dramatiq", +] + +[dependency-groups] +dev = [ + { include-group = "test" }, +] test = [ "pytest", "pytest-cov", @@ -61,6 +79,8 @@ test = [ "redis", ] docs = [ + "sphinx", + "furo", "celery>=4.2.0", "django-reversion", "dramatiq>=2.0.0", @@ -68,22 +88,16 @@ docs = [ "redis", "graphviz>=0.18", ] -graphviz = [ - "graphviz>=0.18", -] -reversion = [ - "django-reversion", -] -celery = [ - "celery>=4.2.0", -] -dramatiq = [ - "dramatiq>=2.0.0", - "django_dramatiq", -] [project.urls] -Project-URL = "https://github.com/codingjoe/joeflow" +# https://packaging.python.org/en/latest/specifications/well-known-project-urls/#well-known-labels +Homepage = "https://github.com/codingjoe/joeflow" +Changelog = "https://github.com/codingjoe/joeflow/releases" +Source = "https://github.com/codingjoe/joeflow" +Releasenotes = "https://github.com/codingjoe/joeflow/releases/latest" +Documentation = "https://joeflow.rtfd.io/" +Issues = "https://github.com/codingjoe/joeflow/issues" +Funding = "https://github.com/sponsors/codingjoe" [tool.flit.module] name = "joeflow" @@ -93,7 +107,7 @@ write_to = "joeflow/_version.py" [tool.pytest.ini_options] minversion = "6.0" -addopts = "--cov=joeflow --doctest-modules" +addopts = "--cov=joeflow --cov-report=xml --cov-report=term --doctest-modules" testpaths = [ "tests", ] @@ -103,7 +117,7 @@ env = "D:DRAMATIQ_BROKER = dramatiq.brokers.stub.StubBroker" [tool.coverage.report] show_missing = true - +skip_covered = true [tool.ruff] src = ["joeflow", "tests"]