Skip to content

Commit 7bd4b9e

Browse files
skylarmbgithub-actions[bot]
authored andcommitted
chore(release): Release v1.1.0
1 parent f3c8815 commit 7bd4b9e

141 files changed

Lines changed: 3583 additions & 1117 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

‎CHANGELOG.md‎

Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,30 @@
11
## [Unreleased]
22

3+
## [1.1.0] - 2026-05-19
4+
5+
### Added
6+
7+
- **Charts API: `client.charts` CRUD surface**
8+
- New `client.charts.create()`, `.list()`, `.get(chart_id)`, `.update(chart_id, request)`, and `.delete(chart_id)` methods (plus `*_async` variants) backed by `POST /v1/charts`, `GET /v1/charts`, `GET /v1/charts/{chart_id}`, `PUT /v1/charts/{chart_id}`, and `DELETE /v1/charts/{chart_id}`. Chart request and response models are exported from `honeyhive.models`.
9+
10+
### Changed
11+
12+
- **CrewAI integration example refreshed**
13+
- The CrewAI example (`examples/integrations/crewai_integration.py`) has been rewritten with three realistic customer-support scenarios (single-agent with tool calls, sequential two-agent crew, and `@trace` escalation). Crews are now named for clearer span labels, and teardown properly flushes remaining spans.
14+
15+
### Fixed
16+
17+
- **Tracer init: `project` / `HH_PROJECT` no longer required**
18+
- `HoneyHiveTracer.init()` previously required `project` and treated a missing value as degraded mode. Since the backend determines the project from the API key, only `api_key` is actually needed. Callers that followed the v1.0.1 deprecation guidance and removed `project` were silently running in degraded mode — this is now fixed. `project` and `HH_PROJECT` remain accepted for backwards compatibility (deprecated, to be removed in v2.0).
19+
20+
- **Duplicate `model` spans in `evaluate()`**
21+
- `evaluate()` could occasionally emit two `model` spans for a single LLM call when running multiple datapoints concurrently. The underlying race condition in instrumentation setup has been fixed.
22+
23+
### Removed
24+
25+
- **`cp_base_url=` parameter and `HH_CP_API_URL` env var removed**
26+
- These options were vestigial configuration for an incomplete Control Plane integration that was never wired up or shipped. No customer code could have depended on them. They have been removed to clean up the public API surface. If you happen to pass `cp_base_url=` or set `HH_CP_API_URL`, simply remove them — `HH_API_URL` / `base_url=` is the only base-URL setting.
27+
328
## [1.0.2] - 2026-05-11
429

530
### Fixed
@@ -9,7 +34,7 @@
934
- The two legacy write paths have been removed now that the scores are correctly written to the chain span as the single source of truth.
1035

1136
- **API Client: `event_id` typed as required on `POST /events` responses**
12-
- `PostEventResponse.event_id` was incorrectly typed as `Optional[str]` in the OpenAPI spec; the backend always returns the field on a 2xx response. The spec was corrected and the generated SDK now reflects the runtime guarantee, removing the need for defensive `if event.event_id:` guards. No runtime behavior change, but strictly typed mypy codebases with `warn_unreachable = True` or pyright with `reportUnnecessaryComparison` enabled may produce "unnecessary comparison" or "redundant Optional guard" warnings, depending on exact usage patterns.
37+
- `PostEventResponse.event_id` was incorrectly typed as `Optional[str]` in the OpenAPI spec; the backend always returns the field on a 2xx response. The spec was corrected and the generated SDK now reflects the runtime guarantee, removing the need for defensive `if event.event_id:` guards. No runtime behavior change, but strictly typed mypy codebases with `warn_unreachable = True` or pyright with `reportUnnecessaryComparison` enabled may produce "unnecessary comparison" or "redundant Optional guard" warnings, depending on exact usage patterns.
1338

1439
### Added
1540

‎CONTRIBUTING.md‎

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -76,7 +76,7 @@ make help
7676
Key commands:
7777
- `make check` - Run all comprehensive checks (format, lint, tests, validation)
7878
- `make test` - Run all tests
79-
- `make format` - Format code with Black and isort
79+
- `make format` - Format code with ruff
8080
- `make lint` - Run linting checks
8181
- `make generate-sdk` - Generate SDK from OpenAPI spec
8282

@@ -88,8 +88,7 @@ make check
8888
```
8989

9090
This runs all quality checks:
91-
- ✅ Black formatting
92-
- ✅ Import sorting (isort)
91+
- ✅ Ruff formatting and import sorting
9392
- ✅ Static analysis (pylint + mypy)
9493
- ✅ Unit tests (fast, mocked)
9594
- ✅ Integration test validation

‎Makefile‎

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
.PHONY: help install install-dev test test-all test-unit test-integration check-integration lint format check check-format check-lint typecheck check-tracer-patterns check-no-mocks generate generate-sdk compare-sdk docs-serve docs-build clean clean-all build publish
22

33
# Use uv run to automatically resolve the workspace venv and dependencies.
4-
# --extra dev ensures SDK dev optional-dependencies (black, isort, tox, etc.) are installed.
4+
# --extra dev ensures SDK dev optional-dependencies (ruff, tox, etc.) are installed.
55
# Override with: UV_RUN="python3" make build
66
UV_RUN ?= uv run --extra dev
77
PYTHON ?= $(UV_RUN) python
@@ -23,7 +23,7 @@ help:
2323
@echo " make test-integration - Run integration tests only (requires .env)"
2424
@echo ""
2525
@echo "Code Quality:"
26-
@echo " make format - Format code with black and isort"
26+
@echo " make format - Format code with ruff"
2727
@echo " make lint - Run linting checks"
2828
@echo " make typecheck - Run mypy type checking"
2929
@echo " make check - Run ALL checks"
@@ -84,8 +84,8 @@ check-integration:
8484

8585
# Code Quality
8686
format:
87-
$(UV_RUN) black src tests examples scripts
88-
$(UV_RUN) isort src tests examples scripts
87+
$(UV_RUN) ruff format src tests examples scripts
88+
$(UV_RUN) ruff check --select I --fix src tests examples scripts
8989

9090
lint:
9191
$(UV_RUN) tox -e lint

‎docs/gen_ref_pages.py‎

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -179,8 +179,7 @@ def _is_nav_visible(parts: tuple[str, ...]) -> bool:
179179
identifier = ".".join(parts)
180180
with mkdocs_gen_files.open(full_doc_path, "w") as fd:
181181
fd.write(
182-
f"---\ntitle: {identifier}\n---\n\n"
183-
f"# `{identifier}`\n\n::: {identifier}\n"
182+
f"---\ntitle: {identifier}\n---\n\n# `{identifier}`\n\n::: {identifier}\n"
184183
)
185184

186185
# Write the literate-nav summary so the nav tree mirrors the package layout.

‎examples/advanced_usage.py‎

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -20,8 +20,12 @@
2020
import time
2121
from typing import Any, Dict, Optional
2222

23-
from honeyhive import enrich_span # Legacy pattern for context manager demo
24-
from honeyhive import HoneyHiveTracer, trace, trace_class
23+
from honeyhive import (
24+
HoneyHiveTracer,
25+
enrich_span, # Legacy pattern for context manager demo
26+
trace,
27+
trace_class,
28+
)
2529
from honeyhive.config.models import SessionConfig, TracerConfig
2630
from honeyhive.models import EventType
2731

‎examples/basic_usage.py‎

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -156,7 +156,8 @@ def process_data(input_data):
156156

157157
# Initialize API client
158158
client = HoneyHive(
159-
api_key="your-api-key-here", test_mode=True # Use test mode for examples
159+
api_key="your-api-key-here",
160+
test_mode=True, # Use test mode for examples
160161
)
161162
print("✓ API client initialized")
162163
print("✓ Ready for API operations (events, datasets, etc.)")

‎examples/debug_openai_instrumentor_spans.py‎

Lines changed: 17 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -49,13 +49,13 @@
4949

5050
def init_honeyhive_tracer(session_name: str):
5151
"""Initialize HoneyHive tracer with verbose logging enabled."""
52-
print(f"\n{'='*80}")
52+
print(f"\n{'=' * 80}")
5353
print(f"INITIALIZING HONEYHIVE TRACER")
54-
print(f"{'='*80}")
54+
print(f"{'=' * 80}")
5555
print(f"Session: {session_name}")
5656
print(f"Server URL: {HH_SERVER_URL or 'default'}")
5757
print(f"Verbose: True")
58-
print(f"{'='*80}\n")
58+
print(f"{'=' * 80}\n")
5959

6060
tracer = HoneyHiveTracer.init(
6161
api_key=HH_API_KEY,
@@ -70,11 +70,11 @@ def init_honeyhive_tracer(session_name: str):
7070

7171
def instrument_openai(tracer):
7272
"""Initialize OpenAI instrumentor with tracer provider."""
73-
print(f"\n{'='*80}")
73+
print(f"\n{'=' * 80}")
7474
print(f"INSTRUMENTING OPENAI")
75-
print(f"{'='*80}")
75+
print(f"{'=' * 80}")
7676
print(f"Using tracer provider: {tracer.provider}")
77-
print(f"{'='*80}\n")
77+
print(f"{'=' * 80}\n")
7878

7979
instrumentor = OpenAIInstrumentor()
8080
instrumentor.instrument(tracer_provider=tracer.provider)
@@ -228,7 +228,7 @@ def test_multiple_sequential_calls(queries: list) -> list:
228228
results = []
229229

230230
for i, query in enumerate(queries):
231-
print(f"[TEST 4] Processing query {i+1}/{len(queries)}: {query}")
231+
print(f"[TEST 4] Processing query {i + 1}/{len(queries)}: {query}")
232232

233233
response = client.chat.completions.create(
234234
model="gpt-3.5-turbo",
@@ -242,9 +242,9 @@ def test_multiple_sequential_calls(queries: list) -> list:
242242
result = response.choices[0].message.content
243243
if result:
244244
results.append(result)
245-
print(f"[TEST 4] Response {i+1}: {result}")
245+
print(f"[TEST 4] Response {i + 1}: {result}")
246246
else:
247-
print(f"[TEST 4] Response {i+1}: <empty>")
247+
print(f"[TEST 4] Response {i + 1}: <empty>")
248248

249249
# Enrich with aggregated metrics
250250
print(f"[TEST 4] Attempting enrich_span with aggregated metrics...")
@@ -262,9 +262,9 @@ def test_multiple_sequential_calls(queries: list) -> list:
262262

263263
def main():
264264
"""Run all debug tests."""
265-
print(f"\n{'#'*80}")
265+
print(f"\n{'#' * 80}")
266266
print(f"# OPENAI INSTRUMENTOR SPAN DEBUG SCRIPT")
267-
print(f"{'#'*80}\n")
267+
print(f"{'#' * 80}\n")
268268

269269
# Initialize tracer
270270
tracer = init_honeyhive_tracer("Debug Session - OpenAI Instrumentor Spans")
@@ -285,23 +285,23 @@ def main():
285285
# Test 4: Multiple sequential calls
286286
test_multiple_sequential_calls(["What is AI?", "What is ML?", "What is DL?"])
287287

288-
print(f"\n{'='*80}")
288+
print(f"\n{'=' * 80}")
289289
print(f"ALL TESTS COMPLETED")
290-
print(f"{'='*80}\n")
290+
print(f"{'=' * 80}\n")
291291

292292
except Exception as e:
293-
print(f"\n{'!'*80}")
293+
print(f"\n{'!' * 80}")
294294
print(f"ERROR OCCURRED: {e}")
295-
print(f"{'!'*80}\n")
295+
print(f"{'!' * 80}\n")
296296
import traceback
297297

298298
traceback.print_exc()
299299

300300
finally:
301301
# Flush tracer to ensure all spans are sent
302-
print(f"\n{'='*80}")
302+
print(f"\n{'=' * 80}")
303303
print(f"FLUSHING TRACER")
304-
print(f"{'='*80}\n")
304+
print(f"{'=' * 80}\n")
305305
flush(tracer)
306306

307307
# Uninstrument to clean up

‎examples/evaluate_with_adk_instrumentor.py‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -76,7 +76,7 @@ def get_current_time(city: str) -> dict:
7676

7777
tz = ZoneInfo(tz_identifier)
7878
now = datetime.datetime.now(tz)
79-
report = f'The current time in {city} is {now.strftime("%Y-%m-%d %H:%M:%S %Z%z")}'
79+
report = f"The current time in {city} is {now.strftime('%Y-%m-%d %H:%M:%S %Z%z')}"
8080
return {"status": "success", "report": report}
8181

8282

‎examples/evaluate_with_enrichment.py‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -199,15 +199,15 @@ def postprocess(text: str) -> str:
199199

200200
# For demo, manually iterate
201201
for i, datapoint in enumerate(mock_dataset):
202-
print(f"\n Datapoint {i+1}/{len(mock_dataset)}:")
202+
print(f"\n Datapoint {i + 1}/{len(mock_dataset)}:")
203203
result = simple_llm_task(datapoint)
204204
print(f" ✓ Output: {result['output'][:50]}...")
205205

206206
print("\n✓ Simple task evaluation completed")
207207

208208
print("\n 📝 Running complex task on mock dataset...")
209209
for i, datapoint in enumerate(mock_dataset):
210-
print(f"\n Datapoint {i+1}/{len(mock_dataset)}:")
210+
print(f"\n Datapoint {i + 1}/{len(mock_dataset)}:")
211211
result = complex_task_with_steps(datapoint)
212212
print(f" ✓ Output: {result['output'][:50]}...")
213213

0 commit comments

Comments
 (0)