noburn 0.1.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,6 @@
1
+ __pycache__/
2
+ *.py[cod]
3
+ .pytest_cache/
4
+ dist/
5
+ *.egg-info/
6
+ .venv/
noburn-0.1.0/PKG-INFO ADDED
@@ -0,0 +1,112 @@
1
+ Metadata-Version: 2.4
2
+ Name: noburn
3
+ Version: 0.1.0
4
+ Summary: Hard LLM spend enforcement for Python — pre-call budget checks and per-user metering.
5
+ Project-URL: Homepage, https://noburn.dev
6
+ Project-URL: Documentation, https://noburn.dev/docs
7
+ Project-URL: Repository, https://github.com/orvi2014/noburn
8
+ License: MIT
9
+ Keywords: ai,anthropic,budget,cost-control,langchain,llm,openai
10
+ Classifier: Development Status :: 4 - Beta
11
+ Classifier: Intended Audience :: Developers
12
+ Classifier: License :: OSI Approved :: MIT License
13
+ Classifier: Programming Language :: Python :: 3
14
+ Classifier: Programming Language :: Python :: 3.9
15
+ Classifier: Programming Language :: Python :: 3.10
16
+ Classifier: Programming Language :: Python :: 3.11
17
+ Classifier: Programming Language :: Python :: 3.12
18
+ Classifier: Topic :: Software Development :: Libraries
19
+ Requires-Python: >=3.9
20
+ Description-Content-Type: text/markdown
21
+
22
+ # noburn
23
+
24
+ Hard LLM spend enforcement for Python — pre-call budget checks and per-user metering.
25
+
26
+ Check a planned LLM call against project-, per-user-, and per-run budget caps
27
+ *before* you make it, then record what it actually cost.
28
+
29
+ ## Install
30
+
31
+ ```bash
32
+ pip install noburn
33
+ ```
34
+
35
+ Requires Python ≥ 3.9. No third-party dependencies. Ships type hints (`py.typed`).
36
+
37
+ ## Quick start
38
+
39
+ ```python
40
+ import os
41
+ from noburn import NoburnGuard
42
+
43
+ guard = NoburnGuard(
44
+ api_key=os.environ["NOBURN_API_KEY"],
45
+ project_id=os.environ["NOBURN_PROJECT_ID"],
46
+ budget_cap_usd=10.0, # optional local fallback cap
47
+ on_error="allow", # "allow" (default, fail-open) | "block" (fail-closed)
48
+ )
49
+
50
+ decision = guard.check(
51
+ model="gpt-4o",
52
+ estimated_tokens_in=1000,
53
+ estimated_tokens_out=300,
54
+ end_user_id="user_123", # optional — enforces that user's cap
55
+ )
56
+
57
+ if decision.blocked:
58
+ raise RuntimeError(f"Blocked by noburn: {decision.block_reason}")
59
+
60
+ # ... make your LLM call ...
61
+
62
+ guard.record(
63
+ model="gpt-4o",
64
+ tokens_in=980,
65
+ tokens_out=290,
66
+ cost_usd=0.005,
67
+ was_blocked=False,
68
+ end_user_id="user_123",
69
+ )
70
+ ```
71
+
72
+ `record()` is fire-and-forget — it returns immediately (delivery happens on a
73
+ background daemon thread) and never raises, so it adds no latency to your call
74
+ path.
75
+
76
+ ## Agent runs
77
+
78
+ Bound a single agent invocation with its own cap:
79
+
80
+ ```python
81
+ run = guard.start_run(budget_cap_usd=0.5)
82
+
83
+ decision = guard.check(
84
+ model="gpt-4o",
85
+ estimated_tokens_in=1000,
86
+ estimated_tokens_out=300,
87
+ run_id=run.run_id,
88
+ )
89
+
90
+ guard.record(model="gpt-4o", tokens_in=980, tokens_out=290,
91
+ cost_usd=0.005, was_blocked=False, run_id=run.run_id)
92
+
93
+ summary = guard.end_run(run.run_id) # EndRunResult(status=..., spend_usd=..., ...)
94
+ ```
95
+
96
+ ## Behavior
97
+
98
+ - **`check()` never raises** except `NoburnAuthError` (bad key). Every call asks
99
+ the server for an authoritative decision; if the server is unreachable it
100
+ falls back to a local in-memory check.
101
+ - **`on_error`** controls that fallback when nothing local blocks the call:
102
+ `"allow"` (default) fails open so a noburn outage never breaks your app;
103
+ `"block"` fails closed (`block_reason="noburn_unreachable"`).
104
+ - **`start_run()` raises** on network/auth error (`NoburnTimeoutError` on
105
+ timeout) — a run must be registered before you proceed.
106
+
107
+ > Note: `check()`/`start_run()` use blocking HTTP. In async apps, run them in a
108
+ > thread executor (e.g. `await asyncio.to_thread(guard.check, ...)`).
109
+
110
+ ## License
111
+
112
+ MIT
noburn-0.1.0/README.md ADDED
@@ -0,0 +1,91 @@
1
+ # noburn
2
+
3
+ Hard LLM spend enforcement for Python — pre-call budget checks and per-user metering.
4
+
5
+ Check a planned LLM call against project-, per-user-, and per-run budget caps
6
+ *before* you make it, then record what it actually cost.
7
+
8
+ ## Install
9
+
10
+ ```bash
11
+ pip install noburn
12
+ ```
13
+
14
+ Requires Python ≥ 3.9. No third-party dependencies. Ships type hints (`py.typed`).
15
+
16
+ ## Quick start
17
+
18
+ ```python
19
+ import os
20
+ from noburn import NoburnGuard
21
+
22
+ guard = NoburnGuard(
23
+ api_key=os.environ["NOBURN_API_KEY"],
24
+ project_id=os.environ["NOBURN_PROJECT_ID"],
25
+ budget_cap_usd=10.0, # optional local fallback cap
26
+ on_error="allow", # "allow" (default, fail-open) | "block" (fail-closed)
27
+ )
28
+
29
+ decision = guard.check(
30
+ model="gpt-4o",
31
+ estimated_tokens_in=1000,
32
+ estimated_tokens_out=300,
33
+ end_user_id="user_123", # optional — enforces that user's cap
34
+ )
35
+
36
+ if decision.blocked:
37
+ raise RuntimeError(f"Blocked by noburn: {decision.block_reason}")
38
+
39
+ # ... make your LLM call ...
40
+
41
+ guard.record(
42
+ model="gpt-4o",
43
+ tokens_in=980,
44
+ tokens_out=290,
45
+ cost_usd=0.005,
46
+ was_blocked=False,
47
+ end_user_id="user_123",
48
+ )
49
+ ```
50
+
51
+ `record()` is fire-and-forget — it returns immediately (delivery happens on a
52
+ background daemon thread) and never raises, so it adds no latency to your call
53
+ path.
54
+
55
+ ## Agent runs
56
+
57
+ Bound a single agent invocation with its own cap:
58
+
59
+ ```python
60
+ run = guard.start_run(budget_cap_usd=0.5)
61
+
62
+ decision = guard.check(
63
+ model="gpt-4o",
64
+ estimated_tokens_in=1000,
65
+ estimated_tokens_out=300,
66
+ run_id=run.run_id,
67
+ )
68
+
69
+ guard.record(model="gpt-4o", tokens_in=980, tokens_out=290,
70
+ cost_usd=0.005, was_blocked=False, run_id=run.run_id)
71
+
72
+ summary = guard.end_run(run.run_id) # EndRunResult(status=..., spend_usd=..., ...)
73
+ ```
74
+
75
+ ## Behavior
76
+
77
+ - **`check()` never raises** except `NoburnAuthError` (bad key). Every call asks
78
+ the server for an authoritative decision; if the server is unreachable it
79
+ falls back to a local in-memory check.
80
+ - **`on_error`** controls that fallback when nothing local blocks the call:
81
+ `"allow"` (default) fails open so a noburn outage never breaks your app;
82
+ `"block"` fails closed (`block_reason="noburn_unreachable"`).
83
+ - **`start_run()` raises** on network/auth error (`NoburnTimeoutError` on
84
+ timeout) — a run must be registered before you proceed.
85
+
86
+ > Note: `check()`/`start_run()` use blocking HTTP. In async apps, run them in a
87
+ > thread executor (e.g. `await asyncio.to_thread(guard.check, ...)`).
88
+
89
+ ## License
90
+
91
+ MIT
@@ -0,0 +1,32 @@
1
+ [build-system]
2
+ requires = ["hatchling"]
3
+ build-backend = "hatchling.build"
4
+
5
+ [project]
6
+ name = "noburn"
7
+ version = "0.1.0"
8
+ description = "Hard LLM spend enforcement for Python — pre-call budget checks and per-user metering."
9
+ readme = "README.md"
10
+ license = { text = "MIT" }
11
+ requires-python = ">=3.9"
12
+ keywords = ["llm", "ai", "budget", "cost-control", "openai", "anthropic", "langchain"]
13
+ classifiers = [
14
+ "Development Status :: 4 - Beta",
15
+ "Intended Audience :: Developers",
16
+ "License :: OSI Approved :: MIT License",
17
+ "Programming Language :: Python :: 3",
18
+ "Programming Language :: Python :: 3.9",
19
+ "Programming Language :: Python :: 3.10",
20
+ "Programming Language :: Python :: 3.11",
21
+ "Programming Language :: Python :: 3.12",
22
+ "Topic :: Software Development :: Libraries",
23
+ ]
24
+ dependencies = []
25
+
26
+ [project.urls]
27
+ Homepage = "https://noburn.dev"
28
+ Documentation = "https://noburn.dev/docs"
29
+ Repository = "https://github.com/orvi2014/noburn"
30
+
31
+ [tool.hatch.build.targets.wheel]
32
+ packages = ["src/noburn"]
@@ -0,0 +1,4 @@
1
+ from .guard import NoburnGuard, CheckResult, NoburnAuthError, NoburnTimeoutError
2
+
3
+ __all__ = ["NoburnGuard", "CheckResult", "NoburnAuthError", "NoburnTimeoutError"]
4
+ __version__ = "0.1.0"