К основному содержанию
скилл CX Codex

ai-security-hardening — скилл для Claude Code: защита LLM-систем

Защищает приложения на базе LLM от prompt injection, утечек данных и атак на цепочку поставок. Пригодится при выводе моделей в прод и подготовке к аудитам SOC2 или ISO 27001.

Установить в Claude Code · Через Skills CLI (Vercel) Все способы и платформы ↓
npx skills add BagelHole/DevOps-Security-Agent-Skills --skill ai-security-hardening -a claude-code
Открыть на GitHub

Что делает ai-security-hardening

Скилл содержит паттерны и код для блокировки инъекций в промпты, санитизации ввода и фильтрации вывода. Для выявления персональных данных (PII) используются библиотеки presidio-analyzer и presidio-anonymizer, а для контроля диалоговых сценариев — конфигурации nemoguardrails. Они отсекают типовые обходы.

В кодовой базе также представлены примеры эндпоинтов на FastAPI с ограничением частоты запросов по JWT и проверка целостности весов моделей в формате .safetensors через хеши SHA-256. Внедрение этих фильтров неизбежно увеличивает время ответа модели, поэтому регулярные выражения и DLP-сканирование требуют замера задержек в вашей инфраструктуре.

Какие задачи решает

  • перехватывать prompt injection и попытки подмены системного контекста
  • вырезать персональные данные (PII) из ответов нейросети перед отправкой клиенту
  • настроить ограничение запросов к API модели по токенам JWT
  • проверять целостность скачанных весов safetensors по контрольным суммам SHA-256

Примеры запросов агенту

  • Проверь эндпоинты чата на уязвимость к prompt injection и настрой санитизацию входящего текста.
  • Добавь анонимизацию PII в ответы модели с помощью presidio-analyzer.
  • Настрой лимиты запросов к API модели в FastAPI на основе ai-security-hardening.

Как установить ai-security-hardening

1Через Skills CLI (Vercel)

npx skills add BagelHole/DevOps-Security-Agent-Skills --skill ai-security-hardening -a claude-code

2Вручную: положить файлы

~/.claude/skills/ai-security-hardening/SKILL.md

Папка скилла целиком; для одного проекта — .claude/skills/ai-security-hardening/

По шагам, с командами для каждой платформы: Как установить скилл в Claude Code: пять способов

Вопросы о ai-security-hardening

Как установить ai-security-hardening в Claude Code?

Выполните в терминале команду npx skills add BagelHole/DevOps-Security-Agent-Skills --skill ai-security-hardening -a claude-code.

Что делает скилл ai-security-hardening?

Он предоставляет готовые шаблоны и код для защиты LLM-приложений от внедрения промптов, кражи весов, утечки конфиденциальных данных и уязвимостей вывода вроде XSS или SQLi.

Какие внешние библиотеки требуются для работы фильтров?

Для маскирования персональных данных нужны presidio-analyzer и presidio-anonymizer, а для сценариев контроля диалога используется пакет nemoguardrails.

Исходный текст

SKILL.md · MIT
---
name: ai-security-hardening
description: Harden AI/LLM deployments against prompt injection, data exfiltration, model theft, and supply chain attacks. Covers input validation, output filtering, access control, model API security, and compliance controls for production AI systems.
license: MIT
metadata:
  author: devops-skills
  version: "1.0"
---

# AI Security Hardening

Secure LLM and AI systems against prompt injection, jailbreaks, data leakage, and supply chain threats in production environments.

## When to Use This Skill

Use this skill when:
- Deploying an LLM-powered application handling sensitive user data
- Protecting against prompt injection attacks in AI agents
- Implementing output filtering and content moderation
- Securing model weights and API endpoints from theft
- Achieving SOC2 or ISO 27001 compliance for AI systems

## AI-Specific Threat Model

```
Threat                    Risk                          Control
─────────────────────────────────────────────────────────────────────
Prompt injection          System prompt override         Input sanitization, separate context
Data exfiltration         PII in model outputs           Output filtering, DLP scanning
Jailbreaking             Policy bypass                  Content moderation, guardrails
Model theft               Weight extraction via API      Rate limiting, access controls
Training data poisoning   Backdoored fine-tuned model    Dataset validation, provenance
Supply chain attack       Malicious model weights        Signature verification, scanning
Insecure output           XSS/SQLi from LLM response     Output encoding, parameterized queries
```

## Prompt Injection Defense

```python
import re
from typing import Optional

INJECTION_PATTERNS = [
    r"ignore\s+(all\s+)?(previous|prior|above)\s+instructions",
    r"you\s+are\s+now\s+",
    r"new\s+instructions?:",
    r"system\s+prompt",
    r"forget\s+everything",
    r"act\s+as\s+",
    r"jailbreak",
    r"dan\s+mode",
    r"<\s*system\s*>",
    r"\[INST\]",
]

def detect_prompt_injection(user_input: str) -> tuple[bool, Optional[str]]:
    """Return (is_suspicious, matched_pattern)."""
    normalized = user_input.lower().strip()
    for pattern in INJECTION_PATTERNS:
        if re.search(pattern, normalized, re.IGNORECASE):
            return True, pattern
    return False, None

def sanitize_user_input(user_input: str, max_length: int = 4000) -> str:
    """Sanitize input before passing to LLM."""
    # Truncate
    user_input = user_input[:max_length]

    # Remove null bytes and control characters
    user_input = re.sub(r'[\x00-\x08\x0b\x0c\x0e-\x1f\x7f]', '', user_input)

    # Check for injection
    suspicious, pattern = detect_prompt_injection(user_input)
    if suspicious:
        raise ValueError(f"Potential prompt injection detected: {pattern}")

    return user_input
```

## Guardrails with NeMo Guardrails

```python
# guardrails.yaml
from nemoguardrails import RailsConfig, LLMRails

config = RailsConfig.from_path("./guardrails-config")
rails = LLMRails(config)

async def safe_llm_call(user_message: str) -> str:
    response = await rails.generate_async(
        messages=[{"role": "user", "content": user_message}]
    )
    return response["content"]
```

```yaml
# guardrails-config/config.yml
models:
  - type: main
    engine: openai
    model: gpt-4o-mini

rails:
  input:
    flows:
      - check jailbreak
      - check sensitive data
  output:
    flows:
      - check output for PII
      - check output for harmful content
```

## Output Filtering & PII Scrubbing

```python
import re
from presidio_analyzer import AnalyzerEngine
from presidio_anonymizer import AnonymizerEngine

analyzer = AnalyzerEngine()
anonymizer = AnonymizerEngine()

PII_ENTITIES = ["PERSON", "EMAIL_ADDRESS", "PHONE_NUMBER", "CREDIT_CARD",
                "US_SSN", "IBAN_CODE", "IP_ADDRESS", "LOCATION"]

def scrub_pii_from_output(text: str) -> str:
    """Remove PII from LLM output before returning to user."""
    results = analyzer.analyze(text=text, entities=PII_ENTITIES, language="en")
    if not results:
        return text
    anonymized = anonymizer.anonymize(text=text, analyzer_results=results)
    return anonymized.text

def validate_output_safety(output: str) -> bool:
    """Check output doesn't contain prompt injection artifacts."""
    dangerous_patterns = [
        r"<\s*script\s*>",         # XSS
        r"javascript:",             # XSS
        r";\s*(DROP|DELETE|INSERT)",# SQLi
        r"\$\{.*\}",               # template injection
        r"`.*`",                   # command injection in some contexts
    ]
    for pattern in dangerous_patterns:
        if re.search(pattern, output, re.IGNORECASE):
            return False
    return True
```

## API Security for LLM Endpoints

```python
from fastapi import FastAPI, HTTPException, Depends, Request
from fastapi.security import HTTPBearer, HTTPAuthorizationCredentials
import jwt
import time
from collections import defaultdict

app = FastAPI()
security = HTTPBearer()

# Rate limiting (per API key)
request_counts = defaultdict(list)

def rate_limit(api_key: str, max_requests: int = 100, window_seconds: int = 60):
    now = time.time()
    requests = request_counts[api_key]
    # Remove old requests outside window
    request_counts[api_key] = [t for t in requests if now - t < window_seconds]
    if len(request_counts[api_key]) >= max_requests:
        raise HTTPException(status_code=429, detail="Rate limit exceeded")
    request_counts[api_key].append(now)

async def verify_token(
    credentials: HTTPAuthorizationCredentials = Depends(security)
) -> dict:
    try:
        payload = jwt.decode(credentials.credentials, SECRET_KEY, algorithms=["HS256"])
        rate_limit(payload["sub"])
        return payload
    except jwt.ExpiredSignatureError:
        raise HTTPException(status_code=401, detail="Token expired")
    except jwt.InvalidTokenError:
        raise HTTPException(status_code=401, detail="Invalid token")

@app.post("/v1/chat/completions")
async def chat(request: Request, token: dict = Depends(verify_token)):
    body = await request.json()

    # Input validation
    user_msg = body.get("messages", [{}])[-1].get("content", "")
    try:
        safe_input = sanitize_user_input(user_msg)
    except ValueError as e:
        raise HTTPException(status_code=400, detail=str(e))

    # Call LLM and scrub output
    response = await call_llm(safe_input, token["scope"])
    response["choices"][0]["message"]["content"] = scrub_pii_from_output(
        response["choices"][0]["message"]["content"]
    )
    return response
```

## Model Weight Security

```bash
# Verify model weights with SHA-256 hash before loading
MODEL_DIR="./models/llama-3.1-8b"
EXPECTED_HASH="sha256:abc123..."

# Generate hash of downloaded model
actual_hash=$(find "$MODEL_DIR" -name "*.safetensors" | sort | xargs sha256sum | sha256sum)
echo "Model hash: $actual_hash"

# Compare (automate in CI/CD)
if [ "$actual_hash" != "$EXPECTED_HASH" ]; then
  echo "ERROR: Model hash mismatch — possible tampering!"
  exit 1
fi

# Scan model files for embedded malware (ModelScan)
pip install modelscan
modelscan scan -p "$MODEL_DIR"
```

## Network Isolation for AI Services

```yaml
# Kubernetes NetworkPolicy — isolate LLM API
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: llm-api-isolation
  namespace: ai-services
spec:
  podSelector:
    matchLabels:
      app: vllm
  policyTypes:
  - Ingress
  - Egress
  ingress:
  - from:
    - namespaceSelector:
        matchLabels:
          name: backend           # only backend can call LLM
    ports:
    - protocol: TCP
      port: 8000
  egress:
  - to:
    - namespaceSelector:
        matchLabels:
          name: monitoring        # metrics only
    ports:
    - protocol: TCP
      port: 9090
  # Block egress to internet — prevent data exfiltration
  # (allow only internal cluster traffic)
```

## Audit Logging

```python
import structlog
from datetime import datetime, timezone

audit_log = structlog.get_logger("ai.audit")

def log_llm_interaction(
    user_id: str,
    session_id: str,
    model: str,
    prompt_tokens: int,
    completion_tokens: int,
    was_filtered: bool,
    injection_detected: bool,
):
    audit_log.info(
        "llm_interaction",
        timestamp=datetime.now(timezone.utc).isoformat(),
        user_id=user_id,
        session_id=session_id,
        model=model,
        prompt_tokens=prompt_tokens,
        completion_tokens=completion_tokens,
        was_filtered=was_filtered,
        injection_detected=injection_detected,
        # DO NOT log prompt/completion content — PII risk
    )
```

## Common Issues

| Issue | Cause | Fix |
|-------|-------|-----|
| False positive injection blocks | Overly broad regex | Tune patterns; use ML-based classifier for high-traffic |
| PII in model outputs | Model trained on PII data | Add Presidio scrubbing to output layer |
| API key leakage | Keys in logs or responses | Mask keys in logging; use vault for key storage |
| Model weight tampering | Unverified downloads | Always verify SHA-256; use `modelscan` |
| Rate limit bypass | Per-IP not per-user | Rate limit on authenticated user ID, not IP |

## Best Practices

- Never log raw prompts or completions — they may contain PII or sensitive data.
- Treat LLM output as untrusted input — always encode before rendering in HTML.
- Use network policies to prevent LLM pods from making outbound internet calls.
- Rotate API keys quarterly; use short-lived JWT tokens for service-to-service auth.
- Run `modelscan` on any model downloaded from the internet before serving.

## Related Skills

- [hashicorp-vault](../../secrets/hashicorp-vault/) - Secrets management for API keys
- [network-security](../../network/) - Network-level controls
- [linux-hardening](../../hardening/linux-hardening/) - Host hardening
- [agent-observability](../../../devops/ai/agent-observability/) - AI audit logging
- [llm-gateway](../../../infrastructure/networking/llm-gateway/) - Centralized access control

© devops-skills · MIT · BagelHole/DevOps-Security-Agent-Skills

Похожие скиллы

Всё по теме «Безопасность» →
skill-security-auditor Alireza Rezvani Сканирует скиллы на вредоносный код перед установкой: ищет eval(), os.system(), утечку данных, prompt injection и уязвимые зависимости. 785установок Python Security Scan sugarforever Скилл проверяет код на Python, Flask, Django и FastAPI на уязвимости OWASP Top 10, утечки секретов и уязвимые зависимости. Пригодится перед релизом и во время аудита безопасности. CX Codex +1 540установок powershell-security-hardening VoltAgent Community Субагент проверяет и ужесточает безопасность PowerShell-скриптов, удалённого доступа и Windows-настроек. Подойдёт для аудита автоматизации и security gates в CI/CD. 194установок security-and-hardening addyosmani Помогает проектировать защиту и проверять код на уязвимости при работе с вводом, авторизацией, сессиями и внешними сервисами. Подойдёт перед релизом и при создании функций, которые обрабатывают недоверенные данные. CX Codex +1 70 200установок Large Language Models Security Specialist majevva Промпт, который превращает чат в разбор безопасности LLM: ищет слабые места в ответах на тестовые запросы и предлагает, как закрыть риски. GP ChatGPT ★ 174 597звёзд репо security-hardening Seth Hobson Команда проводит аудит безопасности по этапам: сканирует уязвимости, строит threat model и проверяет архитектуру. Подходит для поэтапного hardening проекта. CX Codex 437установок

Из того же набора127

llm-app-security Набор проверок и правил для защиты чат-ботов, RAG-систем и AI-функций от инъекций промптов, утечек данных и атак по классификации OWASP LLM Top 10. CX Codex +1 327установок nfs-storage Скилл для настройки NFS: экспорт каталогов на сервере, монтирование на клиентах, autofs и правка параметров. CX Codex +1 328установок model-serving-kubernetes Разворачивает ML-модели и LLM в Kubernetes через KServe или NVIDIA Triton Inference Server. Помогает настроить канареечный релиз, сплит трафика и автоскейлинг. CX Codex +1 327установок ai-sre-incident-response Скилл для SRE-практик вокруг LLM: падения провайдера, просадка качества, всплеск расходов на токены и срабатывания гардрейлов. CX Codex +1 328установок block-storage Скилл для работы с блочными устройствами: разметка дисков, LVM, файловые системы, снапшоты и тома AWS EBS. Пригодится, когда нужно расширить раздел на живом сервере. CX Codex +1 327установок pci-dss-compliance Скилл помогает разложить требования PCI DSS v4.0 по вашему проекту: выбрать SAQ, очертить CDE и настроить контроль доступа. CX Codex +1 327установок cloudflare-zero-trust Скилл помогает закрыть внутренние сервисы через Cloudflare Zero Trust без VPN. Настраивает туннели cloudflared, политики доступа по IdP и проверки устройств. CX Codex +1 325установок ai-pipeline-orchestration Скилл помогает агенту собирать пайплайны для загрузки данных, обучения моделей, батч-инференса и индексации RAG на Prefect, Airflow или Dagster. CX Codex +1 325установок

Спонсоры проекта

Компании, которые помогают держать аналитику открытой