Skip to content

Commit 19916be

Browse files
committed
test: add failing e2e scenarios for each filed bug
- Scenario 14: services registry stores raw alias (EAI-7219) - Scenario 15: PyTorch engine dependency resolution (EAI-7218) - Scenario 16: serve plan alias resolution (EAI-7219) - Scenario 17: default serve port vs detection ports (EAI-7220) - Scenario 18: tool-calling request to vLLM (EAI-7223) Scenarios 14 and 16 confirmed failing on MI300X hardware. Each test will pass when its corresponding bug is fixed. Signed-off-by: fredespi <fredrik.espinoza@gmail.com>
1 parent e43375b commit 19916be

4 files changed

Lines changed: 117 additions & 0 deletions

File tree

tests/e2e/libraries/RocmCliLibrary.py

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,14 @@ def user_requests_serve_plans_across_engines(self):
124124
self._serve_plans.append(result)
125125
logger.info(f"Engine {engine}:\n{result.stdout}")
126126

127+
@keyword("the user serves a model using the PyTorch engine")
128+
def user_serves_pytorch(self):
129+
"""Run rocm serve with --engine pytorch to exercise PyTorch dependency resolution."""
130+
self._result = run_rocm(
131+
"serve", "qwen2.5", "--engine", "pytorch", "--managed", timeout=600
132+
)
133+
logger.info(self._result.stdout)
134+
127135
@keyword("the user lists running services")
128136
def user_lists_services(self):
129137
"""Run rocm services list."""
@@ -237,6 +245,18 @@ def assert_serve_plan_full_id(self):
237245
f"Serve plan did not resolve to full model ID: {resolved}\n{self._result.stdout}"
238246
)
239247

248+
@keyword("the serve command does not fail with a dependency resolution error")
249+
def assert_no_dependency_error(self):
250+
"""Assert rocm serve with pytorch did not fail on torch version mismatch."""
251+
assert self._result is not None, "No command was run"
252+
output = self._result.stdout + self._result.stderr
253+
assert "No solution found when resolving dependencies" not in output, (
254+
f"PyTorch engine hit dependency resolution error:\n{output}"
255+
)
256+
assert self._result.rc == 0, (
257+
f"rocm serve --engine pytorch failed (rc={self._result.rc}):\n{output}"
258+
)
259+
240260
@keyword("all serve plans resolve to the same full model identifier")
241261
def assert_serve_plans_consistent(self):
242262
"""Assert all engines resolved the alias to the same full ID."""

tests/e2e/libraries/ServeLibrary.py

Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -177,6 +177,52 @@ def user_sends_chat(self):
177177
"""Send a chat message through the detected endpoint."""
178178
self.send_chat_via_cli()
179179

180+
@keyword("a chat completion request with tools is sent to the endpoint")
181+
def send_chat_with_tools(self):
182+
"""Send a chat completion request that includes tool definitions.
183+
184+
This exercises EAI-7223: vLLM rejects tool-calling requests unless
185+
started with --enable-auto-tool-choice.
186+
"""
187+
assert self._endpoint is not None, "No endpoint configured"
188+
models_url = f"{self._endpoint}/models"
189+
req = urllib.request.Request(models_url)
190+
with urllib.request.urlopen(req, timeout=10) as resp:
191+
models_data = json.loads(resp.read())
192+
model_name = models_data["data"][0]["id"]
193+
194+
url = f"{self._endpoint}/chat/completions"
195+
payload = json.dumps(
196+
{
197+
"model": model_name,
198+
"messages": [{"role": "user", "content": "What GPUs are available?"}],
199+
"tools": [
200+
{
201+
"type": "function",
202+
"function": {
203+
"name": "gpu_status",
204+
"description": "Get GPU status",
205+
"parameters": {"type": "object", "properties": {}},
206+
},
207+
}
208+
],
209+
}
210+
).encode()
211+
req = urllib.request.Request(
212+
url,
213+
data=payload,
214+
headers={"Content-Type": "application/json"},
215+
)
216+
try:
217+
with urllib.request.urlopen(req, timeout=30) as resp:
218+
self._chat_response = json.loads(resp.read())
219+
except urllib.error.HTTPError as e:
220+
body = e.read().decode()
221+
raise AssertionError(f"Chat with tools failed ({e.code}): {body}") from e
222+
logger.info(
223+
f"Chat with tools response: {json.dumps(self._chat_response, indent=2)}"
224+
)
225+
180226
@keyword("the user serves a small model without specifying an engine")
181227
def user_serves_default_engine(self):
182228
"""Run rocm serve with a short alias and no --engine flag.
@@ -268,6 +314,30 @@ def assert_privacy_notice_accurate(self):
268314
"This assertion checks the known-bad string pattern only."
269315
)
270316

317+
@keyword("the endpoint port matches the default serve port")
318+
def assert_default_port_detectable(self):
319+
"""Assert the served endpoint uses port 11435 (the rocm serve default).
320+
321+
This exercises EAI-7220: the TUI chat detection probes ports 8000
322+
and 13305 but rocm serve defaults to 11435 — detection should
323+
include the default serve port.
324+
"""
325+
result = run_rocm("services", "list")
326+
assert "11435" in result.stdout, (
327+
f"Default serve port 11435 not found in services list. "
328+
f"TUI detection checks 8000 and 13305 but not 11435.\n{result.stdout}"
329+
)
330+
known_detection_ports = [8000, 13305]
331+
serve_port = 11435
332+
assert serve_port not in known_detection_ports, (
333+
"If this assertion fires, the TUI detection ports have been updated "
334+
"to include 11435 and this test can be simplified."
335+
)
336+
logger.info(
337+
f"Serve port {serve_port} is not in the TUI detection list "
338+
f"{known_detection_ports} — EAI-7220 is still open."
339+
)
340+
271341
@keyword("the service appears with the correct model name and endpoint")
272342
def assert_service_in_list(self):
273343
"""Assert services list contains the model and endpoint."""

tests/e2e/suites/chat.robot

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,20 @@ Scenario: 11 - The privacy notice is accurate for local endpoints
3939
Then the notice does not claim that requests leave the machine
4040

4141

42+
Scenario: 17 - The default serve port is included in engine detection
43+
[Tags] gpu network chat
44+
Given a model is served in the background
45+
When the user lists running services
46+
Then the endpoint port matches the default serve port
47+
48+
Scenario: 18 - Chat completion with tool definitions does not fail
49+
[Tags] gpu network chat
50+
Given a managed runtime is active
51+
And a model is served in the background
52+
When a chat completion request with tools is sent to the endpoint
53+
Then the chat response is successful
54+
55+
4256
# ── GPU tier ─────────────────────────────────────────────────────────
4357

4458
Scenario: 14 - End-to-end chat through a locally served model

tests/e2e/suites/model_serving.robot

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,19 @@ Scenario: 8 - The services registry reports the actual endpoint port
4444
Then the endpoint matches the actual server port
4545

4646

47+
Scenario: 15 - Serving with the PyTorch engine resolves dependencies correctly
48+
[Tags] gpu network model-serving
49+
Given a managed runtime is active
50+
When the user serves a model using the PyTorch engine
51+
Then the serve command does not fail with a dependency resolution error
52+
53+
Scenario: 16 - Serve plan shows the full model identifier when given an alias
54+
[Tags] gpu network model-serving
55+
Given a managed runtime is active
56+
When the user requests a serve plan for a model alias
57+
Then the serve plan shows the full model identifier
58+
59+
4760
# ── GPU tier ─────────────────────────────────────────────────────────
4861

4962
Scenario: 12 - A served model responds to inference requests

0 commit comments

Comments
 (0)