jev-logtriage
Jev decides whether a batch of logs is worth acting on.
Your code keeps the thresholds. Nothing is executed.
Independent. Not an official TypeSafe AI project.
logs -> collapse -> jev (6 questions, one call) -> code gates
|
suppress | watch | review | notify | page
Prometheus is good at conditions you already know how to write in PromQL. This is for the rest. Repeated benign warnings get suppress. A helm reconcile error and a failed ntfy push get notify. Low confidence never auto-acts. It goes to review.
Try it
Needs uv and a TypeSafe API key. Loki is not required.
From this repo:
export TYPESAFE_API_KEY=apikey_...
uv run logtriage --demo
Without cloning:
export TYPESAFE_API_KEY=apikey_...
uvx --from git+https://github.com/jyatesdotdev/jev-logtriage logtriage --demo
uv run creates .venv, installs uv.lock, and runs the script. Python 3.10+ is enough.
Without uv:
pip install -r requirements.txt
export TYPESAFE_API_KEY=apikey_...
python -m logtriage --demo
--demo loads bundled fixtures (logtriage/fixtures/demo.json), a sanitized hour of homelab warn/error lines, and runs the same pipeline a Loki query would.
DECISION SEV PRIO CONF CATEGORY SOURCE
-----------------------------------------------------------------
notify 2.0 0.47 0.80 network alertmanager
notify 2.1 0.44 0.80 security forgejo-runner
notify 1.8 0.42 0.73 network helm-controller
notify 1.2 0.29 0.73 config authentik
watch 1.4 0.42 0.38 infra coredns
watch 0.6 0.19 0.54 expected_noise news-linker
suppress 0.6 0.17 0.54 expected_noise kube-state-metrics
Numbers move a little from run to run. The gates do not.
What Jev decides
One System One call per source. Question ids are not sent to the model. The instructions are.
| id | type | question |
|---|---|---|
is_routine_noise |
noul | would an on-call engineer dismiss this? |
severity |
score | 0 routine to 3 critical |
impact_scope |
score | 0 one pod to 3 cluster-wide |
needs_action |
noul | should a human do something? |
auto_remediable |
noul | is there a safe, unambiguous automated fix? |
category |
choice | app_error, resource, infra, network, config, security, expected_noise |
Patterns from the TypeSafe docs:
- Speculative fan-out. Ask all six up front. Ignore answers that do not apply.
- Composite scoring.
priority = 0.60 * severity/3 + 0.40 * impact/3. Weights live in code. - Confidence-gated routing. Below
--confidence-floor(default 0.50) the decision isreview.
Gates, in order:
is_routine_noise >= 0.80and severity below the page line →suppressneeds_action < 0.50→watch- min confidence below the floor →
review - severity
>= 2.0and priority>= 0.70→page auto_remediable >= 0.85and a safe category →auto_remediate_candidate- otherwise →
notify
Security is never an auto-remediation candidate. auto_remediate_candidate is a label. This repo does not restart pods, call webhooks, or page anyone.
Loki
If you already run Loki, point the same script at it.
# kubectl port-forward -n monitoring svc/loki 3100:3100
uv run logtriage --since 1h --errors-only --exclude-app loki
--port-forward will start that kubectl command if http://127.0.0.1:3100/ready fails.
A JSON report is written to reports/triage-<timestamp>.json unless you pass --no-report. It includes the exact state sent to Jev, the typed answers, and the rationale strings built from those answers. Jev does not generate prose.
Limits
There is no memory across runs. The same coredns glob warning will be classified every time you invoke the script. Do not cron this until you add a fingerprint. That is intentional for v0.
--fail-on page exits 2 if any batch was paged, which is enough to hang off a CI job or a wrapper.
uv run python -m unittest discover -s tests -t . -v
License
MIT. See LICENSE.
Release files for jev-logtriage 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| jev_logtriage-0.1.0.tar.gz | 22.9 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| jev_logtriage-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 43.9 kB
Release files / jev_logtriage-0.1.0.tar.gz
| Download URL | jev_logtriage-0.1.0.tar.gz |
|---|---|
| Size | 22.9 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
5220cb742507028c62e8a65509520c9f6bc60abf4287cce16300e15384b383b2
|
|
BLAKE2b-256 checksum How to use checksums |
6e700e78836a651fcc2f6f08ffb37c68c10234edde12868ea700c44856a4a98c
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
uv/0.11.32 {"installer":{"name":"uv","version":"0.11.32","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
|
Release files / jev_logtriage-0.1.0-py3-none-any.whl
| Download URL | jev_logtriage-0.1.0-py3-none-any.whl |
|---|---|
| Size | 21.0 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
87056180a240012c3566092b03f1f8b8a1a7b01ed85b9add2f363e7dd936abed
|
|
BLAKE2b-256 checksum How to use checksums |
114a5089cedba2b6bc68f45eb35e6afa4db8fd7e1abe7ff81aea25a960400eb6
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
uv/0.11.32 {"installer":{"name":"uv","version":"0.11.32","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
|