hud-python 0.4.56__py3-none-any.whl → 0.4.58__py3-none-any.whl

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.

Potentially problematic release.


This version of hud-python might be problematic. Click here for more details.

hud/server/server.py CHANGED
@@ -13,9 +13,12 @@ from typing import TYPE_CHECKING, Any
13
13
 
14
14
  import anyio
15
15
  from fastmcp.server.server import FastMCP, Transport
16
+ from starlette.requests import Request
16
17
  from starlette.responses import JSONResponse, Response
17
18
 
19
+ from hud.cli.eval import run_full_dataset
18
20
  from hud.server.low_level import LowLevelServerWithInit
21
+ from hud.types import Task
19
22
 
20
23
  if TYPE_CHECKING:
21
24
  from collections.abc import AsyncGenerator, Callable
@@ -485,6 +488,84 @@ class MCPServer(FastMCP):
485
488
  self._prompt_manager._prompts[new_key] = prompt
486
489
  # await self.import_server(hidden_router, prefix=None, **kwargs)
487
490
 
491
+ def _get_docker_logs(
492
+ self,
493
+ tail: int = 100,
494
+ since: str | None = None,
495
+ until: str | None = None,
496
+ timestamps: bool = False,
497
+ ) -> dict[str, Any]:
498
+ """Helper function to get Docker container logs.
499
+
500
+ Args:
501
+ tail: Number of lines to show from the end of the logs
502
+ since: Show logs since timestamp or relative time
503
+ until: Show logs before a timestamp or relative time
504
+ timestamps: Show timestamps in log output
505
+
506
+ Returns:
507
+ Dictionary with logs data or error information
508
+ """
509
+ import subprocess
510
+
511
+ container_name = os.environ.get("_HUD_DEV_DOCKER_CONTAINER")
512
+ if not container_name:
513
+ return {"items": [], "container_name": None, "error": "No container name found"}
514
+
515
+ # Build docker logs command
516
+ cmd = ["docker", "logs", "--tail", str(tail)]
517
+
518
+ if since:
519
+ cmd.extend(["--since", since])
520
+ if until:
521
+ cmd.extend(["--until", until])
522
+ if timestamps:
523
+ cmd.append("--timestamps")
524
+
525
+ cmd.append(container_name)
526
+
527
+ try:
528
+ # Run docker logs to get output
529
+ result = subprocess.run( # noqa: S603
530
+ cmd,
531
+ stdout=subprocess.PIPE,
532
+ stderr=subprocess.STDOUT,
533
+ text=True,
534
+ encoding="utf-8",
535
+ errors="replace",
536
+ timeout=5,
537
+ )
538
+
539
+ # Parse logs into items
540
+ items = []
541
+ lines = result.stdout.strip().split("\n") if result.stdout else []
542
+
543
+ for i, line in enumerate(lines):
544
+ if line.strip():
545
+ items.append(
546
+ {
547
+ "id": i,
548
+ "stream": "mixed",
549
+ "log": line,
550
+ "container_name": container_name,
551
+ }
552
+ )
553
+
554
+ return {
555
+ "items": items,
556
+ "container_name": container_name,
557
+ "total_lines": len(items),
558
+ }
559
+
560
+ except subprocess.TimeoutExpired:
561
+ return {"error": "Docker logs timeout", "container_name": container_name, "items": []}
562
+ except Exception as e:
563
+ return {
564
+ "error": f"Failed to get logs: {e!s}",
565
+ "container_name": container_name,
566
+ "items": [],
567
+ }
568
+
488
569
  def _register_hud_helpers(self) -> None:
489
570
  """Register development helper endpoints.
490
571
 
@@ -492,6 +573,8 @@ class MCPServer(FastMCP):
492
573
  - GET /docs - Interactive documentation and tool testing
493
574
  - POST /api/tools/{name} - REST wrappers for MCP tools
494
575
  - GET /openapi.json - OpenAPI spec for REST endpoints
576
+ - GET /logs - Development log endpoint (when provided by dev runtime)
577
+ - hud-logs tool - MCP tool for fetching logs (when in Docker mode)
495
578
  """
496
579
 
497
580
  # Register REST wrapper for each tool
@@ -542,6 +625,195 @@ class MCPServer(FastMCP):
542
625
  endpoint = create_tool_endpoint(tool_key)
543
626
  self.custom_route(f"/api/tools/{tool_key}", methods=["POST"])(endpoint)
544
627
 
628
+ # Development endpoints - only if dev runtime set a provider
629
+ provider = os.environ.get("_HUD_DEV_LOGS_PROVIDER")
630
+ if provider == "enabled":
631
+
632
+ @self.custom_route("/logs", methods=["GET"])
633
+ async def get_logs(request: Request) -> Response:
634
+ """Return Docker container logs on demand.
635
+
636
+ Query params:
637
+ - limit: max number of lines to return (default 100)
638
+ - tail: number of lines from end to return (default 100)
639
+ """
640
+ # Get query params
641
+ params = request.query_params
642
+ tail = int(params.get("tail", "100"))
643
+
644
+ # Use helper function to get logs
645
+ result = self._get_docker_logs(tail=tail)
646
+
647
+ # Add 'next' field for compatibility with existing API
648
+ if "error" in result:
649
+ return JSONResponse(result, status_code=500)
650
+ else:
651
+ items = result.get("items", [])
652
+ return JSONResponse(
653
+ {
654
+ "items": items,
655
+ "next": len(items) - 1 if items else None,
656
+ }
657
+ )
658
+
659
+ # Import existing types from the codebase
660
+ from pydantic import BaseModel
661
+
662
+ from hud.types import AgentType
663
+
664
+ class EvalRequest(BaseModel):
665
+ """Request model for /eval endpoint."""
666
+
667
+ tasks: list[dict[str, Any]] = []
668
+ agent: str = "claude"
669
+ model: str | None = None
670
+ max_steps: int = 10
671
+ verbose: bool = False
672
+ group_size: int = 1
673
+ name: str | None = None
674
+
675
+ @self.custom_route("/eval", methods=["POST"])
676
+ async def run_eval(request: Request) -> Response:
677
+ """Run evaluation on tasks using the current Docker environment."""
678
+ import asyncio
679
+ import json
680
+
681
+ try:
682
+ body = await request.body()
683
+ data = json.loads(body)
684
+
685
+ # Validate request using Pydantic model
686
+ try:
687
+ eval_request = EvalRequest(**data)
688
+ except Exception as e:
689
+ return JSONResponse({"error": f"Invalid request: {e!s}"}, status_code=400)
690
+
691
+ # Get the Docker MCP config from environment
692
+ docker_mcp_config = os.environ.get("_HUD_DEV_DOCKER_MCP_CONFIG")
693
+ if not docker_mcp_config:
694
+ return JSONResponse(
695
+ {"error": "Docker MCP config not available"}, status_code=500
696
+ )
697
+
698
+ docker_config = json.loads(docker_mcp_config)
699
+
700
+ # Simplify Docker config for evaluation
701
+ if "docker" in docker_config and "args" in docker_config["docker"]:
702
+ original_args = docker_config["docker"]["args"]
703
+ filtered_args = []
704
+ i = 0
705
+
706
+ while i < len(original_args):
707
+ arg = original_args[i]
708
+
709
+ # Skip volume mounts and their values
710
+ if arg in ["-v", "--volume"]:
711
+ i += 2 # Skip the flag and its value
712
+ continue
713
+
714
+ # Skip combined volume mount args
715
+ if arg.startswith(("-v", "--volume=")):
716
+ i += 1
717
+ continue
718
+
719
+ # Skip explicit container name to avoid collisions
720
+ if arg == "--name" and i + 1 < len(original_args):
721
+ i += 2 # Skip the --name and its value
722
+ continue
723
+
724
+ # Skip dev-specific environment variables
725
+ if arg == "-e" and i + 1 < len(original_args):
726
+ next_arg = original_args[i + 1]
727
+ if next_arg in [
728
+ "PYTHONPATH=/app",
729
+ "HUD_DEV=1",
730
+ "PYTHONUNBUFFERED=1",
731
+ ]:
732
+ i += 2 # Skip the -e and its value
733
+ continue
734
+
735
+ filtered_args.append(arg)
736
+ i += 1
737
+
738
+ # Update the docker args with filtered version
739
+ docker_config["docker"]["args"] = filtered_args
740
+
741
+ try:
742
+ agent_type = AgentType(eval_request.agent.lower())
743
+ except ValueError:
744
+ valid_agents = [
745
+ a.value for a in AgentType if a != AgentType.INTEGRATION_TEST
746
+ ]
747
+ return JSONResponse(
748
+ {
749
+ "error": f"Invalid agent type: {eval_request.agent}",
750
+ "valid_agents": valid_agents,
751
+ },
752
+ status_code=400,
753
+ )
754
+
755
+ # Add MCP config to each task and validate basic structure
756
+ tasks = []
757
+ for task_data in eval_request.tasks:
758
+ task_data["mcp_config"] = docker_config
759
+ tasks.append(Task.model_validate(task_data).model_dump())
760
+
761
+ # Save tasks to temporary file
762
+ import tempfile
763
+
764
+ with tempfile.NamedTemporaryFile(
765
+ mode="w", prefix="hud-eval-", suffix=".json", delete=False
766
+ ) as f:
767
+ json.dump(tasks, f)
768
+ task_file = f.name
769
+
770
+ # Fire and forget - launch evaluation in background
771
+ async def run_eval_background() -> None:
772
+ try:
773
+ await run_full_dataset(
774
+ task_file,
775
+ agent_type=agent_type,
776
+ model=eval_request.model,
777
+ max_steps=eval_request.max_steps,
778
+ verbose=eval_request.verbose,
779
+ group_size=eval_request.group_size,
780
+ )
781
+ except Exception as e:
782
+ raise e
783
+ finally:
784
+ # Clean up temp file
785
+ import os
786
+
787
+ if os.path.exists(task_file):
788
+ os.unlink(task_file)
789
+
790
+ # Start the evaluation in the background (fire and forget)
791
+ asyncio.create_task(run_eval_background()) # noqa: RUF006
792
+
793
+ # Return immediately
794
+ response_data = {
795
+ "status": "started",
796
+ "message": f"Evaluation launched with {len(tasks)} task(s)",
797
+ "agent": eval_request.agent,
798
+ "model": eval_request.model,
799
+ "max_steps": eval_request.max_steps,
800
+ "verbose": eval_request.verbose,
801
+ }
802
+
803
+ # Include group_size if > 1
804
+ if eval_request.group_size > 1:
805
+ response_data["group_size"] = eval_request.group_size
806
+ response_data["total_episodes"] = len(tasks) * eval_request.group_size
807
+
808
+ return JSONResponse(response_data)
809
+
810
+ except json.JSONDecodeError:
811
+ return JSONResponse({"error": "Invalid JSON in request body"}, status_code=400)
812
+ except Exception as e:
813
+ return JSONResponse(
814
+ {"error": f"Failed to run evaluation: {e!s}"}, status_code=500
815
+ )
816
+
545
817
  @self.custom_route("/openapi.json", methods=["GET"])
546
818
  async def openapi_spec(request: Request) -> Response:
547
819
  """Generate OpenAPI spec from MCP tools."""
@@ -597,6 +869,40 @@ class MCPServer(FastMCP):
597
869
 
598
870
  return JSONResponse(spec)
599
871
 
872
+ # Register hud-logs tool when in Docker dev mode
873
+ container_name = os.environ.get("_HUD_DEV_DOCKER_CONTAINER")
874
+ if container_name:
875
+
876
+ @self.tool("hud-logs")
877
+ async def get_docker_logs(
878
+ tail: int = 100,
879
+ since: str | None = None,
880
+ until: str | None = None,
881
+ timestamps: bool = False,
882
+ ) -> dict[str, Any]:
883
+ """Get logs from the Docker container running the HUD environment.
884
+
885
+ Args:
886
+ tail: Number of lines to show from the end of the logs (default: 100)
887
+ since: Show logs since timestamp (e.g. 2013-01-02T13:23:37Z) or relative (42m)
888
+ until: Show logs before timestamp (e.g. 2013-01-02T13:23:37Z) or relative (42m)
889
+ timestamps: Show timestamps in log output
890
+
891
+ Returns:
892
+ Dictionary with:
893
+ - items: List of log entries
894
+ - container_name: Name of the container
895
+ - total_lines: Total number of log lines returned
896
+ - error: Error message if logs could not be retrieved
897
+ """
898
+ # Use helper function to get logs
899
+ return self._get_docker_logs(
900
+ tail=tail,
901
+ since=since,
902
+ until=until,
903
+ timestamps=timestamps,
904
+ )
905
+
600
906
  @self.custom_route("/docs", methods=["GET"])
601
907
  async def docs_page(request: Request) -> Response:
602
908
  """Interactive documentation page."""
hud/shared/hints.py CHANGED
@@ -38,7 +38,7 @@ HUD_API_KEY_MISSING = Hint(
38
38
  message="Missing or invalid HUD_API_KEY.",
39
39
  tips=[
40
40
  "Set HUD_API_KEY in your environment or run: hud set HUD_API_KEY=your-key-here",
41
- "Get a key at https://hud.so",
41
+ "Get a key at https://hud.ai",
42
42
  "Check for whitespace or truncation",
43
43
  ],
44
44
  docs_url=None,
@@ -68,7 +68,7 @@ PRO_PLAN_REQUIRED = Hint(
68
68
  tips=[
69
69
  "Upgrade your plan to continue",
70
70
  ],
71
- docs_url="https://hud.so/project/billing",
71
+ docs_url="https://hud.ai/project/billing",
72
72
  command_examples=None,
73
73
  code="PRO_PLAN_REQUIRED",
74
74
  context=["billing", "plan"],
@@ -80,7 +80,7 @@ CREDITS_EXHAUSTED = Hint(
80
80
  tips=[
81
81
  "Top up credits or upgrade your plan",
82
82
  ],
83
- docs_url="https://hud.so/project/billing",
83
+ docs_url="https://hud.ai/project/billing",
84
84
  command_examples=None,
85
85
  code="CREDITS_EXHAUSTED",
86
86
  context=["billing", "credits"],
hud/telemetry/job.py CHANGED
@@ -170,7 +170,7 @@ def _print_job_url(job_id: str, job_name: str) -> None:
170
170
  if not (settings.telemetry_enabled and settings.api_key):
171
171
  return
172
172
 
173
- url = f"https://hud.so/jobs/{job_id}"
173
+ url = f"https://hud.ai/jobs/{job_id}"
174
174
  header = f"🚀 Job '{job_name}' started:"
175
175
 
176
176
  # ANSI color codes
@@ -209,7 +209,7 @@ def _print_job_complete_url(job_id: str, job_name: str, error_occurred: bool = F
209
209
  if not (settings.telemetry_enabled and settings.api_key):
210
210
  return
211
211
 
212
- url = f"https://hud.so/jobs/{job_id}"
212
+ url = f"https://hud.ai/jobs/{job_id}"
213
213
 
214
214
  # ANSI color codes
215
215
  GREEN = "\033[92m"
hud/tools/playwright.py CHANGED
@@ -225,7 +225,14 @@ class PlaywrightTool(BaseTool):
225
225
  if self._browser_context is None:
226
226
  raise RuntimeError("Browser context failed to initialize")
227
227
 
228
- self.page = await self._browser_context.new_page()
228
+ # Reuse existing page if available (for CDP connections), otherwise create new one
229
+ pages = self._browser_context.pages
230
+ if pages:
231
+ self.page = pages[0]
232
+ logger.info("Reusing existing browser page")
233
+ else:
234
+ self.page = await self._browser_context.new_page()
235
+ logger.info("Created new browser page")
229
236
  logger.info("Playwright browser launched successfully")
230
237
 
231
238
  async def navigate(
hud/types.py CHANGED
@@ -230,7 +230,7 @@ class AgentResponse(BaseModel):
230
230
  tool_calls: list[MCPToolCall] = Field(default_factory=list)
231
231
  done: bool = Field(default=False)
232
232
 
233
- # --- TELEMETRY [hud.so] ---
233
+ # --- TELEMETRY [hud.ai] ---
234
234
  # Responses
235
235
  content: str | None = Field(default=None)
236
236
  reasoning: str | None = Field(default=None)
@@ -5,4 +5,4 @@ def test_import():
5
5
  """Test that the package can be imported."""
6
6
  import hud
7
7
 
8
- assert hud.__version__ == "0.4.56"
8
+ assert hud.__version__ == "0.4.58"
hud/version.py CHANGED
@@ -4,4 +4,4 @@ Version information for the HUD SDK.
4
4
 
5
5
  from __future__ import annotations
6
6
 
7
- __version__ = "0.4.56"
7
+ __version__ = "0.4.58"
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: hud-python
3
- Version: 0.4.56
3
+ Version: 0.4.58
4
4
  Summary: SDK for the HUD platform.
5
5
  Project-URL: Homepage, https://github.com/hud-evals/hud-python
6
6
  Project-URL: Bug Tracker, https://github.com/hud-evals/hud-python/issues
@@ -1,8 +1,8 @@
1
1
  hud/__init__.py,sha256=0LQ9PyuU6yZx7Fxu8YJXKC1i3TTHjg3UrInThh759QE,653
2
2
  hud/__main__.py,sha256=YR8Dq8OhINOsVfQ55PmRXXg4fEK84Rt_-rMtJ5rvhWo,145
3
3
  hud/settings.py,sha256=9SPEZcsZGqplw_LuV8RvJisDRdlsbQgxBqG8ifmjGNc,4117
4
- hud/types.py,sha256=jeC1npyPlno5CYNWBWH06Kxw7VMJld9YLEFBFNtjwoI,11608
5
- hud/version.py,sha256=5r7gUjXhMnfdXi42tFi9IN4DXbsCYx9soTL0r3ID9IE,105
4
+ hud/types.py,sha256=XA15zkH25Kt8IQAjT3xfEPew6oCKsnkERKrrKrYmYbM,11608
5
+ hud/version.py,sha256=7lqYv2fdoclIKiUgO55ISA4NzOcYp9DBF4rdJcsoHYk,105
6
6
  hud/agents/__init__.py,sha256=UoIkljWdbq4bM0LD-mSaw6w826EqdEjOk7r6glNYwYQ,286
7
7
  hud/agents/base.py,sha256=nRRnK_kA_PZDT0fepMMTz3QDTHj0jpqvbTqdgRPKSlg,32514
8
8
  hud/agents/claude.py,sha256=Lf7p_h5H4sd2w16ZNc2ru3xuxNP7IDeFayrcdePOLSE,16030
@@ -22,32 +22,32 @@ hud/agents/tests/test_claude.py,sha256=YsI2TV87Sex2BJsLaO2l99WEL3PL3OhQDlTwUHn04
22
22
  hud/agents/tests/test_client.py,sha256=uikgh6yhjPPX2RBU4XJQMz1mNox9uXjuwsP8t93id18,13337
23
23
  hud/agents/tests/test_grounded_openai_agent.py,sha256=VK8lUvHIjWicMX00VKPE-FZyjiJqTEhb80MuRRa9fVc,5437
24
24
  hud/agents/tests/test_openai.py,sha256=hPkL_ANbkrB_HUwvd4wBONuWomCarhLJQcFRpmwSbEk,8016
25
- hud/cli/__init__.py,sha256=kfCsHOG94qIkWG_qipPJWEDqgNDG_qgqew4nf3pr8CE,43083
25
+ hud/cli/__init__.py,sha256=sb0EyBBGEBKbfu2Ph3Wns42plYmA1Hejne5lLZ1hn4A,43747
26
26
  hud/cli/__main__.py,sha256=fDH7XITyuDITwSDIVwRso06aouADO0CzTHKqp5TOwJE,143
27
27
  hud/cli/analyze.py,sha256=4u5oYfJMquOjT9PzzRTYVcTZDxDi0ilNP_g532_hpOU,14716
28
28
  hud/cli/build.py,sha256=EV6PsJ08p3mZZkfeUFjZ687ithxKGlUZ66yAF9lvtaI,28780
29
29
  hud/cli/clone.py,sha256=AwVDIuhr8mHb1oT2Af2HrD25SiTdwATpE6zd93vzLgA,6099
30
30
  hud/cli/debug.py,sha256=jtFW8J5F_3rhq1Hf1_SkJ7aLS3wjnyIs_LsC8k5cnzc,14200
31
- hud/cli/dev.py,sha256=WXxvhqQ2l5gpplJFWtMKnJYycpLyzNAt6x3y3oLa5mk,25379
32
- hud/cli/eval.py,sha256=1guW_pNQqFLpF1RylZltBKdXt6iFd_jBNV3Rxy36QRE,29024
31
+ hud/cli/dev.py,sha256=Cg9BLUs4mcMR6UQw43vW68Tx548BPpzlawlC8NgR2Fk,30018
32
+ hud/cli/eval.py,sha256=8LC8kS4RNuvgEGGf_sP7lz0LOgD8mVYOtEEQMXN59Bw,29024
33
33
  hud/cli/get.py,sha256=sksKrdzBGZa7ZuSoQkc0haj-CvOGVSSikoVXeaUd3N4,6274
34
- hud/cli/init.py,sha256=D1NS4PBHxNqsl9hz2VsMTj6HSB_teJgCqsyY77T5lLs,10042
34
+ hud/cli/init.py,sha256=bkpby7vBDqRH3GUDunNA5PIkbQ-Jnpas5pEeN1ltK7k,9976
35
35
  hud/cli/list_func.py,sha256=EVi2Vc3Lb3glBNJxFx4MPnZknZ4xmuJz1OFg_dc8a_E,7177
36
36
  hud/cli/pull.py,sha256=XGEZ8n60tbzLQP_8d9h7XYmzyCW0e2-Rkr3_tLG7jvw,12449
37
- hud/cli/push.py,sha256=rWJIqHebvp3DchK-00L6G0olD3-klsobLutRW4PP_ts,19488
37
+ hud/cli/push.py,sha256=y-1xYup2M396wlJ15d_N2jqthofmlWWiqCbtdYfZyGc,19488
38
38
  hud/cli/remove.py,sha256=8vGQyXDqgtjz85_vtusoIG8zurH4RHz6z8UMevQRYM4,6861
39
39
  hud/cli/flows/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
40
- hud/cli/flows/dev.py,sha256=Q6vz9KDfeLHvZNs3Kga7PUTMgt_QEm5J98XP9jRKuhM,5220
40
+ hud/cli/flows/dev.py,sha256=aLF_hzra0MIin2_2jWi3--yIZdHm5wi2o2PoQlpNm6M,4846
41
41
  hud/cli/flows/tasks.py,sha256=SAQzS53g6vBPMvuEaMRsmkYOJMwvy28RQ-miVmVnP_8,18028
42
- hud/cli/rl/__init__.py,sha256=pGx4WGaL-yGdogJNzgEE7BtjFtT4I9CTI_UdCm49h98,5376
43
- hud/cli/rl/celebrate.py,sha256=trGEJn3xebexlHwFVKPJKhRujVVV8sy7TQTJvRd2p9A,5947
42
+ hud/cli/rl/__init__.py,sha256=Tn_dYNrpk0UlKiPx0VZjGlGWlRUYxGj5PThp5PqTWbc,5376
43
+ hud/cli/rl/celebrate.py,sha256=vFex4RtHTgbhdsRpF4qS2vo4gd_W6LRd0ksO1EIv6J4,5947
44
44
  hud/cli/rl/config.py,sha256=A-4WWwAS68GRKx1cP_DJ-NZD_96cFNnGwx0P3pQT1ps,3271
45
45
  hud/cli/rl/display.py,sha256=hqJVGmO9csYinladhZwjF-GMvppYWngxDHajTyIJ_gM,5214
46
46
  hud/cli/rl/gpu.py,sha256=peXS-NdUF5RyuSs0aZoCzGLboneBUpCy8f9f99WMrG0,2009
47
47
  hud/cli/rl/gpu_utils.py,sha256=0nFRrmJZzLOHh_0bjMhIsBj94PAuu95vwxLd_sa4Q5g,11202
48
48
  hud/cli/rl/local_runner.py,sha256=_4_Bs8UXPz5Is6PyVg_DnrG0zL_Mr-6DJ5_6jC9o0qA,23199
49
49
  hud/cli/rl/presets.py,sha256=DzOO82xL5QyzdVtlX-Do1CODMvDz9ILMPapjU92jcZg,3051
50
- hud/cli/rl/remote_runner.py,sha256=fKmOVKSBUWfakunfe9-HAllpUJDxfRNZwL00fPw-QTI,17837
50
+ hud/cli/rl/remote_runner.py,sha256=R8XXVrpO4l87nA8hlCcURmPfGzrszNLPuoi7-ZKPrhs,17837
51
51
  hud/cli/rl/rl_api.py,sha256=fvRMWQXhTSLM2zQaWWDas_u47RreH8erLgtXRKnQGeA,4350
52
52
  hud/cli/rl/viewer.py,sha256=ExQs1IX3T8x_9aBzc4JojZ779jmFvFTh7EjOYIHzYsU,4441
53
53
  hud/cli/rl/vllm.py,sha256=xTRvex9mmdatTnNaqwZFDBwUsX70bJP5pAGTpbWjmvM,6153
@@ -64,6 +64,7 @@ hud/cli/tests/test_cli_main.py,sha256=0wMho9p9NcGjp0jLiUtCQh_FYdbMaCJtSY3sBbSgPw
64
64
  hud/cli/tests/test_cli_more_wrappers.py,sha256=MdcsGXOwPQOSjDhSm4s7FjiVy1ru8YeRiZxIGVLAgnA,847
65
65
  hud/cli/tests/test_cli_root.py,sha256=ifHjb1k9zSRTB3dgOxApmRYulzK_D8cKjI4GPQXNQQI,3972
66
66
  hud/cli/tests/test_clone.py,sha256=oC2mf-41QQVc7ODJkjrWbVPNMB2fDW3nZ6jY6w93gvQ,4458
67
+ hud/cli/tests/test_convert.py,sha256=_-W8wLEADUsS9LjaveERJ1i0v8PLP0Oj5Vu7lNp6a_0,12510
67
68
  hud/cli/tests/test_cursor.py,sha256=ZfxAFKJesJ3UV1JBoASSRlv6BXbpvVEk_pjxUg1jnf4,9821
68
69
  hud/cli/tests/test_debug.py,sha256=bQ76d_0HJfthHBSECmGNv499ZE57CIOKsanMlNfNHGk,18036
69
70
  hud/cli/tests/test_eval.py,sha256=2ExXbxnIP8yamQidDAQBQDzF6Y4ZbYGyeOJ3cx84TQI,22380
@@ -93,7 +94,7 @@ hud/cli/utils/runner.py,sha256=16_dXkSZTvT2JQKWbZBCoIz6iiLMhjqgFXvcWr1WS1M,4439
93
94
  hud/cli/utils/server.py,sha256=EE5DJ0RAmXCEjMcZycpAsAxxCj6sOdIsXqPh38kK2ew,7416
94
95
  hud/cli/utils/source_hash.py,sha256=EDD3KC4pLGBVoSL5UTv1GvF2TAs2ThNHNOhP_5Sbub4,2979
95
96
  hud/cli/utils/tasks.py,sha256=lX9SeM5XekrTBx2HWKMA0BQ7R3Q8jqGgi4G5vIHsnJM,994
96
- hud/cli/utils/version_check.py,sha256=30VgZQqwUb36Fm4dAzKn5HuT0We6OnA-rd0eIqjd5Tc,7271
97
+ hud/cli/utils/version_check.py,sha256=TdsPh7mpPw5giWahiQgpLZVvT6Lex2z2tsMOGCvm0Dc,7268
97
98
  hud/cli/utils/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
98
99
  hud/cli/utils/tests/test_config.py,sha256=dZugvnjXiFNAvcx0nrIp578zmReMBEdupXfxpqHWGAk,1422
99
100
  hud/cli/utils/tests/test_docker.py,sha256=WHYg_la0WfIr47Wu7Fmy8BtQrSyiWUdTYccv_DECBvw,2556
@@ -112,14 +113,14 @@ hud/cli/utils/tests/test_source_hash.py,sha256=GGFklT9xrVPMEpPwgiUzr94An66R-nhNn
112
113
  hud/cli/utils/tests/test_tasks.py,sha256=FT4smFGUHaJpZGIqj-yevBH8l9ARCu03RoedGxiLc2M,2624
113
114
  hud/clients/README.md,sha256=XNE3mch95ozDgVqfwCGcrhlHY9CwT1GKfNANNboowto,3826
114
115
  hud/clients/__init__.py,sha256=N5M_gZv4nP7dLRwpAiaqqaxyaLieGW6397FszeG7JGw,364
115
- hud/clients/base.py,sha256=uvBIjU1K5VZjPtDTG4wk1cV6ysV5gRIAydd5Nke7aqc,14212
116
- hud/clients/fastmcp.py,sha256=1xaAg7DwMcwt_GRx2n3OsZaX-UMEQCZCaLDK4cr2HhQ,9178
117
- hud/clients/mcp_use.py,sha256=2Pb8bhAEmD9TJYKb-2JbxmyIsh4ttE_pP-kldrt6AH0,14750
116
+ hud/clients/base.py,sha256=3U3AVLxKdtH6fw2B4V_CXxLv-J93jzlGsdc3ArxDq2I,15274
117
+ hud/clients/fastmcp.py,sha256=7yNk9SqOw-iBKPFJlt3hLAhR2Cl_QwVEln4OwXRd1Ww,9209
118
+ hud/clients/mcp_use.py,sha256=Zq_NBFPAMb81qoQa_adCbdTm-yUFjDFCMFG7m8tOlr4,14781
118
119
  hud/clients/tests/__init__.py,sha256=sKOtJFFa4mDIXh1U6O8ZUHjigE8CiRMQ2PzJTIBZuVE,33
119
120
  hud/clients/tests/test_client_integration.py,sha256=kohU6jfCNfwSnAushHeB1_CmDlRfQc7VBL0GEdJYSeI,4198
120
121
  hud/clients/tests/test_fastmcp.py,sha256=4q3TzDjuieTZa89taiNJIrzbUncNkYOG4MaubypA21k,13030
121
122
  hud/clients/tests/test_mcp_use_retry.py,sha256=9FxLAz4L5Vv3OTtj4wdhRY23wDYALUpE12TYWl7fbJA,13299
122
- hud/clients/tests/test_protocol.py,sha256=aK4CS4g3j1D5jPo83ykzZuHUvcZFAulYtIq9T9Hb_fQ,6640
123
+ hud/clients/tests/test_protocol.py,sha256=1JD9Ka-OLiQI6e9xBvoCaWsHXJ_iZQdGliWH5HJsaKc,6826
123
124
  hud/clients/utils/__init__.py,sha256=-zZjcKIWGj2tXbVDOW45UgoGghhLJzFQVZ6miKenuA4,595
124
125
  hud/clients/utils/mcp_use_retry.py,sha256=knsgOTR3YFXshmPFfPQE6K6C5GpR1ZBJe2J7ozEMikA,6675
125
126
  hud/clients/utils/retry.py,sha256=mMs2T_mAlb8AYhSqMR4AmCw7838gqCC4mdG3zjMAYM4,5744
@@ -140,8 +141,8 @@ hud/native/tests/test_comparator.py,sha256=pDch3r3xDi2o5YXF_bkoLfIdHcCjse3foAaqy
140
141
  hud/native/tests/test_native_init.py,sha256=Z-2dinbQYEkrbCcfBrBOLGdpXtWWOtkfPzp7ZKri68Y,2839
141
142
  hud/otel/__init__.py,sha256=ii17ayoWiS5vAhA7UAmZ8TkmP52gs2pWyHsD46-uYbE,1003
142
143
  hud/otel/collector.py,sha256=jLZymZ8r7xt2VDuWexfbnT7PY1-0aiyLMgjBy8KDY1M,4497
143
- hud/otel/config.py,sha256=rqw4gaQCqJNEFWO_AfyqwgZVia706qJP0UveNSgDVSg,7037
144
- hud/otel/context.py,sha256=pk73k0-ISpRdAuwp-2RDxvC85USggKlvzYUyxkf6I84,20403
144
+ hud/otel/config.py,sha256=eHim5S4QdtrLKq53hJSiq02ezaYevN7Js2QbZyjHdVo,7037
145
+ hud/otel/context.py,sha256=Lic5T4PFdyeM9xfQ1yqzRoK3jhmT4CsRR78mMmRP8co,20403
145
146
  hud/otel/exporters.py,sha256=k0yfUppMbcJ3IfNH3cc_u1hdR54qnnkT7lQjxO3I06g,21470
146
147
  hud/otel/instrumentation.py,sha256=fsFG9W89RdewFDxWKN9Ft4GUb7WbIKpfucTc16WxaZU,5093
147
148
  hud/otel/processors.py,sha256=-gGRbwifplcExDQBLfx_9tqWreDImULJNcENgO9q7VU,4700
@@ -169,7 +170,7 @@ hud/server/__init__.py,sha256=ZTxwhR7tMtSE14i1sONTz5UaMXURW1AYoFZMbWGBviU,134
169
170
  hud/server/context.py,sha256=6bCdSzv1FGyItu9472HbbYef279H7QuMGJDR8EtYg5Y,3210
170
171
  hud/server/low_level.py,sha256=XYs2pOJ9kN4OcJ6ahDmXM5mWkzq5wJLpKFInUYrWEok,4701
171
172
  hud/server/router.py,sha256=T9hLe08-W8SGvO14RfwY3j2zfcvB3lKWS5sR9h_4awM,5343
172
- hud/server/server.py,sha256=1IRrHar4OUF4llVsqkwwLvIH8EpgpXTN52XbyG-bbBg,28367
173
+ hud/server/server.py,sha256=G_tnVuEBhC5gDNPfXChsPimo8L8ArMjQ9v3c1CSg848,40863
173
174
  hud/server/helper/__init__.py,sha256=ZxO8VP3RZEBBp-q65VixuhzQgqEPSVzW0hEY9J9QqDA,116
174
175
  hud/server/tests/__init__.py,sha256=eEYYkxX5Hz9woXVOBJ2H2_CQoEih0vH6nRt3sH2Z8v8,49
175
176
  hud/server/tests/test_add_tool.py,sha256=9Y59LJpow3BQ31Jg7fowhV7nAeyqude9Tap9tEs_vBE,1863
@@ -182,7 +183,7 @@ hud/server/tests/test_server_extra.py,sha256=blIO0ne4Rq7R40y1-O-P8ANeRHnv2iKFWqS
182
183
  hud/server/tests/test_sigterm_runner.py,sha256=HTM_0DAxA2exGYj7LK4udxMGXHZhY9LDZaKkHhQMu_Y,2610
183
184
  hud/shared/__init__.py,sha256=IPxPCqtPLguryN-nBq78Sakypw2bRiE2iHv3SXG8YRk,139
184
185
  hud/shared/exceptions.py,sha256=9IIqwlGuaNmcshEiFnph1jceZpWKpCnWgoH2OH-NL7I,13260
185
- hud/shared/hints.py,sha256=1UViFu6CwDhaKn66SUvJ-mdFnTVifG6u6Y1n7jufqCg,5717
186
+ hud/shared/hints.py,sha256=aH9iIhGvC3Uo56z0H5H68Mh6HMMBMBqQyK8rvjv1Hc0,5717
186
187
  hud/shared/requests.py,sha256=FbvMU_dKSWu7OzNBKGAXlq-Q34zL1cULhEdGFa6rJyQ,9993
187
188
  hud/shared/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
188
189
  hud/shared/tests/test_exceptions.py,sha256=66k9Z1zQmYK4yPlG2NC7zggabpCQMFpGqRG3_lOWM8U,16376
@@ -191,7 +192,7 @@ hud/shared/tests/test_requests.py,sha256=nKFcSN1sjrOouVU2xik9lE5Wxapy3EWsO8iIXrM
191
192
  hud/telemetry/__init__.py,sha256=oYJ9fiaiwUGzfMH0qBixX74uSpAR_hyhl8Y-REjmNak,1396
192
193
  hud/telemetry/async_context.py,sha256=H3MBt1vi_ogxUB0U0zSkeO8EqjcU5Iv_04LVQWtTO-E,11550
193
194
  hud/telemetry/instrument.py,sha256=m3u6YK02PTk39Jr4L3se7l-cYyKx0maCaqf5Z5JqWNA,14096
194
- hud/telemetry/job.py,sha256=3W9KHLfBR13IYZvll496P9F6a9HUXCthFMY-MJLi7EA,13278
195
+ hud/telemetry/job.py,sha256=fhIWvsGdp1RbwINVPRUC47i4zQj4xGfe3pjft4mu8No,13278
195
196
  hud/telemetry/replay.py,sha256=YW17s314s5Wy6Rl8MXHqg1FU8EF9_XcHBMJI0rrkyS4,2306
196
197
  hud/telemetry/trace.py,sha256=Q8ypSKKjjMOV6BdNH65iMnya8ifd2dcOqA9-38Td15Y,5254
197
198
  hud/telemetry/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -204,7 +205,7 @@ hud/tools/__init__.py,sha256=i6lE0GxYcPnlLLd-55ryCCHo7o9anC4RfqkuYFXvzMQ,1009
204
205
  hud/tools/base.py,sha256=IxpnEHfxUtgz1k_w-09l65KKpDV3tQu4WdF3nZDsdwU,17854
205
206
  hud/tools/bash.py,sha256=1jl7cpB1ApGXn7Hy8zghJ2fXugEol6UeN0aYUSiM2EQ,5189
206
207
  hud/tools/edit.py,sha256=NYQL3coPIaG_-TP6DOpsVWFg1xcaMZwM5LtFye9WgNE,12644
207
- hud/tools/playwright.py,sha256=HY91JsC_6cvIa-9W14wIhjsAkAtkLPaXgUqMizTG-1c,14989
208
+ hud/tools/playwright.py,sha256=7ggBkylR71taQtrPr5UNwdxtQrHNXMFzKcHW8qDOgzA,15330
208
209
  hud/tools/response.py,sha256=t6Oc8NM4u951A1XMCBaIkFyu3VNEQ8dcWURyTygfZmA,2228
209
210
  hud/tools/submit.py,sha256=hJG2G3Oex4fz_3CsAUVhOhAA56UvDMhquB29xCT-C3M,1973
210
211
  hud/tools/types.py,sha256=g-CWnUUDSxxIfUy54S1bpY1nfTzdYO1R_nPKYReABjQ,2734
@@ -265,10 +266,10 @@ hud/utils/tests/test_progress.py,sha256=QSF7Kpi03Ff_l3mAeqW9qs1nhK50j9vBiSobZq7T
265
266
  hud/utils/tests/test_tasks.py,sha256=Rbbm51vZxygyWlhjunFq4IfFPefVB3qevM9_CZSt5w4,5774
266
267
  hud/utils/tests/test_telemetry.py,sha256=5jl7bEx8C8b-FfFUko5pf4UY-mPOR-9HaeL98dGtVHM,2781
267
268
  hud/utils/tests/test_tool_shorthand.py,sha256=1p3j3D0G93OXHqnUXbvTs3G4A8awrPvwhPpLi6YPeOM,5458
268
- hud/utils/tests/test_version.py,sha256=QHrgv-B02epzVPg5ZHHzZOOjcN1W9Ke_8G_eAuDIOGQ,160
269
+ hud/utils/tests/test_version.py,sha256=3eFNjP_ugwRDZqUNNdWr6SX43UcvMw4739huirlrQ1o,160
269
270
  hud/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
270
- hud_python-0.4.56.dist-info/METADATA,sha256=TaKPkp8KGeSYMBAJC85GdqT9liQdn3dcUDHNtl105u4,22338
271
- hud_python-0.4.56.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
272
- hud_python-0.4.56.dist-info/entry_points.txt,sha256=jJbodNFg1m0-CDofe5AHvB4zKBq7sSdP97-ohaQ3ae4,63
273
- hud_python-0.4.56.dist-info/licenses/LICENSE,sha256=yIzBheVUf86FC1bztAcr7RYWWNxyd3B-UJQ3uddg1HA,1078
274
- hud_python-0.4.56.dist-info/RECORD,,
271
+ hud_python-0.4.58.dist-info/METADATA,sha256=XasQ6ALt1lQPCHGOmu7h_bgDmPc3TghvlPP7O9N7Jhs,22338
272
+ hud_python-0.4.58.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
273
+ hud_python-0.4.58.dist-info/entry_points.txt,sha256=jJbodNFg1m0-CDofe5AHvB4zKBq7sSdP97-ohaQ3ae4,63
274
+ hud_python-0.4.58.dist-info/licenses/LICENSE,sha256=yIzBheVUf86FC1bztAcr7RYWWNxyd3B-UJQ3uddg1HA,1078
275
+ hud_python-0.4.58.dist-info/RECORD,,