Skip to content

[llm-d] Add dry-run capability#132

Merged
kpouget merged 4 commits into
openshift-psap:mainfrom
kpouget:llmd-dry-run
Jul 20, 2026
Merged

[llm-d] Add dry-run capability#132
kpouget merged 4 commits into
openshift-psap:mainfrom
kpouget:llmd-dry-run

Conversation

@kpouget

@kpouget kpouget commented Jul 17, 2026

Copy link
Copy Markdown
Contributor

First step to be able to compare LLMISVCs with reference files

Summary by CodeRabbit

  • New Features

    • Added a KServe dry-run mode that prepares deployment manifests without deploying services or contacting the cluster.
    • Added runtime configuration to enable or disable dry-run behavior.
  • Bug Fixes

    • Improved consistency when deriving service and selector information from deployment manifests.
    • Simplified pod diagnostic capture and direct file output handling.
  • Tests

    • Updated test workflows to skip deployment, benchmarking, endpoint checks, and cleanup during dry runs.

@coderabbitai

coderabbitai Bot commented Jul 17, 2026

Copy link
Copy Markdown

Review Change Stack

📝 Walkthrough

Walkthrough

The deployment and test orchestration flows now support KServe dry-run execution, propagate manifest-derived service metadata through task context, and skip cluster-dependent operations. Smoke pod diagnostics write command output directly through the oc wrapper.

Changes

KServe dry-run orchestration

Layer / File(s) Summary
Manifest metadata and deployment context
projects/kserve/toolbox/deploy_llmisvc/main.py
Manifest metadata now populates service name and selector context used by deployment, readiness, diagnostics, and endpoint resolution tasks.
Dry-run deployment short circuit
projects/kserve/toolbox/deploy_llmisvc/main.py
Dry-run mode exits deployment and diagnostic tasks early and returns the prepared manifest path.
Runtime dry-run test flow
projects/llm_d/orchestration/config.d/runtime.yaml, projects/llm_d/orchestration/test_phase.py
The runtime flag controls test execution, skipping namespace creation, deployment-dependent work, post-processing, finalizers, and cleanup in dry-run mode.

Smoke pod debug capture

Layer / File(s) Summary
Direct pod debug output capture
projects/guidellm/toolbox/run_smoke_request/main.py
Pod YAML retrieval no longer uses an intermediate result, and pod description output is written directly through stdout_dest.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Sequence Diagram(s)

sequenceDiagram
  participant TestPhase
  participant DeployInferenceService
  participant DeployLLMISVC
  participant CheckDryRun
  TestPhase->>DeployInferenceService: start with runtime.kserve_dry_run
  DeployInferenceService->>DeployLLMISVC: pass dry_run and manifest
  DeployLLMISVC->>CheckDryRun: evaluate dry-run flag
  CheckDryRun-->>DeployLLMISVC: return prepared manifest path
  DeployLLMISVC-->>DeployInferenceService: manifest path
  DeployInferenceService-->>TestPhase: skip endpoint-dependent steps
Loading

Possibly related PRs

Suggested reviewers: albertoperdomo2

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly summarizes the primary change: adding dry-run capability to llm-d.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@kpouget

kpouget commented Jul 17, 2026

Copy link
Copy Markdown
Contributor Author

/test fournos llm_d smoke
/cluster forge-smoke-testing
/pipeline forge-full

@psap-forge-bot

Copy link
Copy Markdown
🔴 Submission of llm_d smoke failed after 1 hour, 6 minutes, 33 seconds 🔴

Error: RetryFailure: All 360 attempts failed for task wait_for_job_completion : Wait for FOURNOS job to complete (last result: False)

/test fournos llm_d smoke
/cluster forge-smoke-testing
/pipeline forge-full

@kpouget

kpouget commented Jul 17, 2026

Copy link
Copy Markdown
Contributor Author

/test fournos llm_d smoke
/cluster forge-smoke-testing
/pipeline forge-full

@psap-forge-bot

Copy link
Copy Markdown

🔴 Execution of llm_d smoke 🔴

Execution Engine Configuration

forge:
  args:
  - smoke
  configOverrides: {}
  project: llm_d

Artifact Links

Test Logs

00 Pre-Cleanup 16 seconds

01 Prepare 19 minutes, 24 seconds

Failure Review 015 Wait Datasciencecluster Ready

015__wait_datasciencecluster_ready

The test failed because the wait_for_datasciencecluster_ready task exhausted its 90-retry limit after 15 minutes while waiting for the default-dsc DataScienceCluster to transition to a Ready phase. The definitive root cause is that the kserve component failed to reconcile and become ready, as the cluster's status.conditions consistently reported Some components are not ready: kserve throughout the execution window.

04 Post-Cleanup 19 seconds

🔄 05 Export-Artifacts

@psap-forge-bot

Copy link
Copy Markdown
🔴 Submission of llm_d smoke failed after 21 minutes, 55 seconds 🔴

Error: FournosJobFailureError: FOURNOS Job 'forge-llm-d-20260717-193659' failed: Tasks Completed: 4 (Failed: 1, Cancelled 0), Skipped: 2

/test fournos llm_d smoke
/cluster forge-smoke-testing
/pipeline forge-full

@kpouget

kpouget commented Jul 17, 2026

Copy link
Copy Markdown
Contributor Author

/test fournos llm_d smoke
/cluster forge-smoke-testing
/pipeline forge-prepare-test

@psap-forge-bot

Copy link
Copy Markdown

🟢 Execution of llm_d smoke 🟢

Execution Engine Configuration

forge:
  args:
  - smoke
  configOverrides: {}
  project: llm_d

Artifact Links

Test Logs

001 Prepare 3 minutes, 32 seconds

02 Preflight 1 second

03 Test 23 minutes, 52 seconds

Test Description

This test validates the llm_d project's approximate prefix caching deployment profile by running a lightweight smoke benchmark using the Qwen/Qwen3-0.6B model. It specifically verifies inference gateway connectivity and baseline throughput under a short concurrent workload (rates 1, 4, and 8) alongside a basic text completion request.

🔄 04 Export-Artifacts

Post-processing Status

@psap-forge-bot

Copy link
Copy Markdown
🟢 Submission of llm_d smoke succeeded after 30 minutes, 6 seconds 🟢
/test fournos llm_d smoke
/cluster forge-smoke-testing
/pipeline forge-prepare-test

@kpouget

kpouget commented Jul 18, 2026

Copy link
Copy Markdown
Contributor Author

/test fournos llm_d smoke
/cluster forge-smoke-testing
/pipeline forge-prepare-test
/var runtime.kserve_dry_run: true

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
projects/guidellm/toolbox/run_smoke_request/main.py (1)

241-250: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Preserve the pod YAML artifact and failure status.

The oc get pod -o yaml result is now discarded. Because check=False, command failures also do not raise, so this path neither writes the YAML artifact nor reports capture failure. Retain the result/write logic or pass a supported artifact destination and inspect returncode.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@projects/guidellm/toolbox/run_smoke_request/main.py` around lines 241 - 250,
Update the oc("get", "pod", ...) call in the smoke-request flow to retain its
result, write the pod YAML artifact as before, and inspect returncode when
check=False. Preserve failure reporting so unsuccessful capture is surfaced
instead of silently discarded.
🧹 Nitpick comments (1)
projects/llm_d/orchestration/test_phase.py (1)

56-56: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Consider extracting the dry-run config lookup to a helper.

The configuration value for runtime.kserve_dry_run is retrieved individually in four different functions across this file (here, do_test, deploy_inference_service, and cleanup_test_resources). Consider abstracting it into a module-level helper function to reduce duplication and centralize the fallback logic.

♻️ Proposed refactor
+def _is_dry_run() -> bool:
+    return config.project.get_config("runtime.kserve_dry_run", False)
+
 def run() -> int:
     """Main test function that wraps do_test() with outcome postprocessing."""
 
-    dry_run = config.project.get_config("runtime.kserve_dry_run", False)
+    dry_run = _is_dry_run()
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@projects/llm_d/orchestration/test_phase.py` at line 56, Extract the repeated
runtime.kserve_dry_run lookup into a module-level helper and update do_test,
deploy_inference_service, and cleanup_test_resources to use it. Preserve the
existing False fallback and configuration behavior while centralizing this
logic.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@projects/guidellm/toolbox/run_smoke_request/main.py`:
- Around line 253-260: Update the oc invocation in the debug-info task to ensure
stdout_dest reaches the underlying command runner: either extend oc to accept
and forward stdout_dest, or call shell.run directly with the existing arguments.
Preserve writing the pod description artifact to artifacts_dir and avoid the
current TypeError.

---

Outside diff comments:
In `@projects/guidellm/toolbox/run_smoke_request/main.py`:
- Around line 241-250: Update the oc("get", "pod", ...) call in the
smoke-request flow to retain its result, write the pod YAML artifact as before,
and inspect returncode when check=False. Preserve failure reporting so
unsuccessful capture is surfaced instead of silently discarded.

---

Nitpick comments:
In `@projects/llm_d/orchestration/test_phase.py`:
- Line 56: Extract the repeated runtime.kserve_dry_run lookup into a
module-level helper and update do_test, deploy_inference_service, and
cleanup_test_resources to use it. Preserve the existing False fallback and
configuration behavior while centralizing this logic.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 500dd02a-7e8b-4cbe-a501-f807242783a1

📥 Commits

Reviewing files that changed from the base of the PR and between 41ad8ab and 9b6ab21.

📒 Files selected for processing (4)
  • projects/guidellm/toolbox/run_smoke_request/main.py
  • projects/kserve/toolbox/deploy_llmisvc/main.py
  • projects/llm_d/orchestration/config.d/runtime.yaml
  • projects/llm_d/orchestration/test_phase.py

Comment on lines +253 to +260
oc(
"describe",
"pod",
ctx.pod_name,
"-n",
args.namespace,
check=False,
stdout_dest=artifacts_dir / f"{ctx.pod_name}.description.txt",

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
rg -n -A30 'def oc\(' projects/core/dsl/utils/k8s.py
rg -n 'stdout_dest' projects/core/dsl/utils/k8s.py projects/guidellm/toolbox/run_smoke_request/main.py

Repository: openshift-psap/forge

Length of output: 1204


🏁 Script executed:

#!/bin/bash
sed -n '220,290p' projects/guidellm/toolbox/run_smoke_request/main.py
printf '\n---\n'
sed -n '1,120p' projects/core/dsl/utils/k8s.py
printf '\n---\n'
rg -n "except .*TypeError|TypeError|stdout_dest" projects/guidellm/toolbox/run_smoke_request/main.py projects/core/dsl/utils/k8s.py projects/core/dsl/utils -g '!**/__pycache__/**'

Repository: openshift-psap/forge

Length of output: 5114


Pass stdout_dest through oc or call shell.run directly projects/guidellm/toolbox/run_smoke_request/main.py:253-260 passes stdout_dest into oc, but projects/core/dsl/utils/k8s.py:19-48 doesn’t accept or forward that keyword, so this raises TypeError and the debug-info task silently skips writing the pod description artifact.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@projects/guidellm/toolbox/run_smoke_request/main.py` around lines 253 - 260,
Update the oc invocation in the debug-info task to ensure stdout_dest reaches
the underlying command runner: either extend oc to accept and forward
stdout_dest, or call shell.run directly with the existing arguments. Preserve
writing the pod description artifact to artifacts_dir and avoid the current
TypeError.

@psap-forge-bot

Copy link
Copy Markdown

🟢 Execution of llm_d smoke 🟢

Execution Engine Configuration

forge:
  args:
  - smoke
  configOverrides:
    runtime.kserve_dry_run: true
  project: llm_d

Artifact Links

Test Logs

001 Prepare 2 minutes, 25 seconds

02 Preflight 2 seconds

03 Test 1 second

🔄 04 Export-Artifacts

@psap-forge-bot

Copy link
Copy Markdown
🟢 Submission of llm_d smoke succeeded after 6 minutes, 37 seconds 🟢
/test fournos llm_d smoke
/var runtime.kserve_dry_run: true
/cluster forge-smoke-testing
/pipeline forge-prepare-test

@kpouget kpouget changed the title [llm-d] Add drun-run capability [llm-d] Add dry-run capability Jul 20, 2026
@albertoperdomo2

Copy link
Copy Markdown
Collaborator

/lgtm
/approve

@openshift-ci openshift-ci Bot added the lgtm Indicates that a PR is ready to be merged. label Jul 20, 2026
@openshift-ci

openshift-ci Bot commented Jul 20, 2026

Copy link
Copy Markdown

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: albertoperdomo2

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@openshift-ci openshift-ci Bot added the approved Indicates a PR has been approved by an approver from all required OWNERS files. label Jul 20, 2026
@kpouget
kpouget merged commit 7c237f6 into openshift-psap:main Jul 20, 2026
7 checks passed
@kpouget
kpouget deleted the llmd-dry-run branch July 20, 2026 09:26
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

approved Indicates a PR has been approved by an approver from all required OWNERS files. lgtm Indicates that a PR is ready to be merged.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants