From qa-llm-evaluation
Authors and runs Giskard LLM scans - adversarial test-case generation for LLM applications via `giskard.scan(model)` covering 7 vulnerability categories (hallucination, harmful_content, prompt_injection, sensitive_information_disclosure, stereotypes, robustness, basic_sycophancy); wraps any callable model behind `giskard.Model(model_predict, model_type="text_generation", ...)`; emits HTML report. Use when the user needs adversarial / red-team coverage on top of functional eval suites.
How this skill is triggered — by the user, by Claude, or both
Slash command
/qa-llm-evaluation:giskard-llmThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
[gk-gh]: https://github.com/Giskard-AI/giskard
Distinct from functional eval frameworks (Promptfoo, DeepEval, Ragas), Giskard's value (per gk-gh) is adversarial test generation - auto-generates inputs designed to break LLMs along documented vulnerability dimensions, then reports findings in a triageable HTML report.
Important version note (2026-05-06): per gk-gh, "Giskard
v2 is no longer actively maintained. The current v3 focus is on
giskard-checks for evaluations, while vulnerability scanning and
RAG evaluation still rely on Giskard v2." This skill targets v2 LLM
scanning; pin >2,<3 per the install command.
Per gk-gh (v2-pinned):
pip install "giskard[llm]>2,<3"
The [llm] extra pulls in the LLM scan dependencies.
Per gk-gh (verbatim quickstart):
import giskard
import pandas as pd
def model_predict(df: pd.DataFrame):
"""The function takes a DataFrame and must return a list of outputs (one per row)."""
return [my_llm_chain.run({"query": question}) for question in df["question"]]
giskard_model = giskard.Model(
model=model_predict,
model_type="text_generation",
name="My LLM Application",
description="A question answering assistant",
feature_names=["question"],
)
The description field steers Giskard's adversarial generator -
make it specific (e.g., "A question answering assistant for medical
guidance" vs the generic "A QA assistant"). Better description ⇒
better-targeted adversarial inputs.
scan_results = giskard.scan(giskard_model)
display(scan_results)
(Per gk-gh.)
In a Jupyter notebook this renders the report inline. To export:
scan_results.to_html("giskard-report.html")
Per gk-gh the v2 LLM scan covers these detector categories:
| Detector | What it tries to surface |
|---|---|
hallucination | Generated content not grounded in inputs / facts |
harmful_content | Toxic, dangerous, or harmful generation |
prompt_injection | Inputs that override system instructions |
sensitive_information_disclosure | PII / credentials / system prompt leakage |
stereotypes | Discriminatory / stereotyped output by protected attribute |
robustness | Brittleness to small input perturbations |
basic_sycophancy | Agreeing with falsehoods to please the user |
Detector selection (subset run):
scan_results = giskard.scan(
giskard_model,
only=["hallucination", "prompt_injection"],
)
(Per the scan() API; consult docs.giskard.ai for the
exact parameter list per Giskard release.)
After a scan surfaces issues, Giskard can synthesize tests for regression coverage:
test_suite = scan_results.generate_test_suite("My LLM Test Suite")
test_suite.run()
This produces deterministic regression tests from the failing adversarial prompts found by the scan - re-run on every PR to prevent regression on previously surfaced vulnerabilities.
Giskard does not ship a first-party CI action; pattern:
python -m my_giskard_scan_script # produces giskard-report.html
Then upload as a CI artifact:
- uses: actions/upload-artifact@v4
with: { name: giskard-report, path: giskard-report.html }
For PR-blocking gating, parse scan_results for severity and
fail CI if any critical findings appear:
critical = [issue for issue in scan_results.issues if issue.level == "major"]
if critical:
sys.exit(1)
| Anti-pattern | Why it fails | Fix |
|---|---|---|
Generic description= field | Adversarial generator produces off-target inputs; many false positives | Specific description (Step 2) |
| Run scan once, never regenerate test suite | Vulnerabilities resurface in new code | Regenerate test suite per release (Step 5) |
| Skip Step 5 - only rely on scans | No regression protection between scans | Always synthesize the test suite |
| Pin Giskard but not the judge-LLM provider | Judge-model drift causes flake | Pin both in CI env |
giskard-checks. Track upstream before
greenlighting new investment.text_generation and text_classification model types
in v2; multi-modal scanning lives elsewhere in the Giskard
ecosystem.promptfoo-evaluation,
deepeval-evaluation,
ragas-evaluation - functional
eval sister tools (use Giskard for adversarial coverage on top)prompt-eval-reviewer -
adversarial reviewer that flags eval suites without adversarial
coveragenpx claudepluginhub testland/qa --plugin qa-llm-evaluationProvides UI/UX resources: 50+ styles, color palettes, font pairings, guidelines, charts for web/mobile across React, Next.js, Vue, Svelte, Tailwind, React Native, Flutter. Aids planning, building, reviewing interfaces.
Fetches up-to-date documentation from Context7 for libraries and frameworks like React, Next.js, Prisma. Use for setup questions, API references, and code examples.