Metadata-Version: 2.4
Name: zmon
Version: 1.6.3
Summary: Monitoring for zCFD runs
Author-email: Zenotech <support@zenotech.com>
License: MIT
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Requires-Python: >=3.10
Description-Content-Type: text/markdown
Requires-Dist: fastapi
Requires-Dist: uvicorn
Provides-Extra: test
Requires-Dist: httpx; extra == "test"

# zMon

zMon monitors zCFD runs in a browser: a React frontend (Vite + TypeScript) and a
FastAPI backend, shipped together as the `zmon` Python wheel. zui mounts the same
backend (`from zmon.main import mount`) in its zCFD Dashboard tab.

## Project Structure

- `frontend/` - React frontend application (Vite + TypeScript)
- `zmon/` - Python package: the API, and the `zmon` command that serves it with the built frontend
- `zmon-setup` - Prepares and runs the Python backend
- `zmon-wheel` - Builds the distributable wheel, frontend included
- `zmon-dev` - Runs the backend and the Vite dev server for local development

Running zMon needs Python, and [zutil](https://pypi.org/project/zutil/) (i.e. a
zCFD environment) to open control files; report CSVs open without it.
[Bun](https://bun.sh) is only needed to build or develop the frontend.

## Running zMon

zMon is a pip-installable Python package, so it can ship inside zCFD, mount into
zui's zCFD Dashboard tab, and be installed standalone to monitor jobs on a remote
cluster. See [docs/packaging-plan.md](docs/packaging-plan.md) for the design.

One command does everything — create the virtualenv, install the package, build
the frontend, and launch:

```bash
./zmon-setup /path/to/case.py
```

It works from any directory (`/path/to/zMon/zmon-setup mycase.py` is fine, and
relative case paths resolve against wherever you ran it), and re-running is
instant because each step is skipped when it's already done. `--setup-only`
prepares everything without launching.

Bun is not needed to run zMon, and `zmon-setup` will build the frontend with the
existing `frontend/node_modules` if bun isn't installed. Bun is still the
frontend build tool when it is available.

Launching serves the API and the built SPA on an unused port chosen by the OS and
opens a browser. Add `--no-browser` to just print the URL. Useful flags:

- `--port N` — pin the port (for an SSH tunnel). Also `ZMON_PORT`.
- `--host` — defaults to `127.0.0.1`; anything else exposes the file browser to
  other users on the machine.
- `--exit-when-idle` — shut down when no browser is connected (the old
  standalone behaviour). Off by default: it is unsafe behind an SSH tunnel.

Run the tests with:

```bash
./.venv/bin/python -m unittest discover -s tests
```

The API is served under `/api/monitor`. A host app embeds zMon with
`zmon.main.mount(app)`, which adds the API and the SPA at `/monitor/`; the page
then takes `#token=…`, `?file=…` and `?theme=…` from its URL. zui's Monitor tab
works this way — see "zui integration" in
[docs/packaging-plan.md](docs/packaging-plan.md) for the contract.

## Development Instructions

From the root of the project, install the frontend dependencies once:

```bash
bun install
```

Then start the backend and the Vite dev server together:

```bash
./zmon-dev /path/to/case.py
```

This runs the Python backend from this checkout (`python3 -m zmon.cli --port 3001
--no-browser`, arguments passed through; set `PYTHON` to use another interpreter)
and the Vite dev server via `bun run --filter frontend dev`, which proxies `/api`
to the backend. Open the URL Vite prints (usually `http://localhost:5173`), not
the one the backend prints. The backend does not auto-reload; restart
`zmon-dev` after Python changes.

To run either side individually:

```bash
python3 -m zmon.cli --port 3001 --no-browser  # backend only
bun run --filter frontend dev                 # frontend only
```

## Releasing to PyPI

- **Stable release:** run the **Release App** workflow from `main`. It bumps the version, tags `vX.Y.Z`, opens the release PR, creates a GitHub release (notes only, no attachments), and dispatches **Publish to PyPI** against that tag. The wheel on PyPI is the only distributable.
- **Feature trial:** run the **Trial Release** workflow with a feature branch — or `main`, to trial it ahead of a stable release — selected under "Use workflow from". It tags the branch head as the next alpha (e.g. `v1.6.0a1`, derived from the latest stable tag) and publishes it as a PyPI pre-release. Testers install it with `pip install zmon==1.6.0a1` (or `pip install --pre zmon`); plain `pip install zmon` still gets the latest stable release.
- **Re-publishing a tag by hand:** `gh workflow run pypi.yml --ref vX.Y.Z` — the ref must be the tag, not a branch.
