Repositório de treino de modelos do Dorsal em 3 camadas:
- Camada 1 (
attack_*.onnx): classificador supervisionado global de ataques. - Camada 2 (gateway): baseline comportamental local por cliente.
- Camada 3 (
global_anomaly_*.onnx): modelo global de anomalia com telemetria agregada.
Este repo entrega pipeline pronto para você rodar quando quiser com dados estáticos, DAST, snapshots de agentes e telemetria.
- Linux/macOS com
bash,git,python3.11+. uvinstalado (curl -LsSf https://astral.sh/uv/install.sh | sh).- Opcional:
docker(para Juice Shop e build do gateway).
cd /home/abraham/tools/dorsal-ml
make venv
make install-dev
make bootstrap
STATIC_PROFILE=full make setup-data
make smoke
make testIsso cria .venv, estrutura de diretórios (data/, models/, reports/, keys/, logs/) e prepara fontes estaticas.
STATIC_PROFILE=full inclui a base obrigatoria (UNSW-NB15, CIC-IDS, Juice/DVWA traffic dirs, ModSecurity CRS, NVD snapshot e Common Crawl local).
- Rode bootstrap estatico completo (
STATIC_PROFILE=full make setup-data+make layer1). - Depois suba o lab e gere trafego legitimo + ataques (
LAB_PLAN.md). - Por fim rode
make layer1-realworldpara validacao com distribuicao operacional.
attack-zap-baseline, attack-zap-graphql e attack-ai-simulated nao exigem dataset pre-gerado; exigem apenas lab ativo e labs/.env.lab configurado.
Observacao importante:
attack-ai-simulatedgera artefatos compativeis com Shannon/Strix, mas nao executa os agentes oficiais.- Shannon/Strix oficiais seguem modo manual-first (voce roda os agentes e salva outputs em
data/raw/lab/strixedata/raw/lab/shannon).
make layer1Saídas principais:
data/curated/attack_*.parquetmodels/attack_*.onnxmodels/attack_latest.onnxreports/attack_*.benchmark.json
STATIC_PROFILE=full \
TARGET_APP=lab_multi \
LAB_RUN_ID=static_bootstrap \
ATTACK_RATIO=0.20 \
make layer1Esse fluxo usa as novas fontes estaticas quando os caminhos locais existem:
data/academic/UNSW-NB15data/academic/CIC-IDSdata/raw/static/juiceshopdata/raw/static/dvwadata/corerulesetdata/nvd/nvd_api_snapshot.jsondata/commoncrawl
Coloque exports/snapshots locais (incluindo runs oficiais de Shannon/Strix, quando usados):
data/dast/burp_export.xmldata/dast/zap_report.jsondata/dast/acunetix_export.jsondata/raw/strix/...data/raw/shannon/...
Execute:
BURP_FILE=./data/dast/burp_export.xml \
ZAP_FILE=./data/dast/zap_report.json \
ACUNETIX_FILE=./data/dast/acunetix_export.json \
STRIX_RUNS_DIR=./data/raw/strix \
SHANNON_SESSIONS_DIR=./data/raw/shannon \
make layer1Use o workflow de duas fases:
- treino com distribuicao 80/20 (ataque/legitimo controlado);
- validacao final com distribuicao proxima da operacao (ex.: 98/2).
make layer1-realworldVariaveis principais (opcionais):
TRAIN_ATTACK_RATIO=0.20 \
REALWORLD_ATTACK_RATIO=0.02 \
REALWORLD_MAX_FPR=0.01 \
HARD_NEGATIVES_PATH=./data/raw/hard_negatives \
HARD_NEGATIVE_RATIO=0.25 \
SLICE_GATES_CONFIG=./configs/slice_gates.example.json \
make layer1-realworldSaidas adicionais:
data/curated/attack_rw_*.train.parquetdata/curated/attack_rw_*.realworld.parquetreports/attack_rw_*.realworld_summary.jsonreports/attack_rw_*.promotion_decision.json
Playbook detalhado:
docs/layer1_realworld_playbook.mdLAB_PLAN.md(lab completo com gateway + apps + trafego legitimo + campanhas de ataque)labs/docker-compose.layer1-lab.yml(stack de laboratorio para coleta realista)
O build da Camada 1 agora inclui metadados adicionais no parquet:
scenario_typetarget_appattack_familyattack_techniquevalidation_tierlab_run_ideffect_outcomeis_replay
Campos novos para trilha de benigno dificil:
scenario_type=hard_negativeeffect_outcome=benign_confirmed
Tambem e gerado um manifesto JSON de dataset (audit trail):
- default:
reports/dataset_manifest_<campaign_id>.json - override:
--manifest-pathouDATASET_MANIFEST_PATH
Exemplo com metadados de campanha:
TARGET_APP=crapi \
LAB_RUN_ID=lab_20260313 \
IS_REPLAY=0 \
make layer1Exemplo de uso direto:
.venv/bin/python -m training.build_dataset \
--payloads-dir ./data/PayloadAllTheThings \
--seclists-dir ./data/SecLists \
--unsw-nb15-dir ./data/academic/UNSW-NB15 \
--cic-ids-dir ./data/academic/CIC-IDS \
--juiceshop-traffic-dir ./data/raw/static/juiceshop \
--dvwa-traffic-dir ./data/raw/static/dvwa \
--modsec-crs-dir ./data/coreruleset \
--nvd-snapshot-file ./data/nvd/nvd_api_snapshot.json \
--commoncrawl-dir ./data/commoncrawl \
--require-static-full \
--campaign-id campaign_crapi_v1 \
--target-app crapi \
--lab-run-id lab_20260313 \
--manifest-path ./reports/campaign_crapi_v1.manifest.json \
--output ./data/curated/campaign_crapi_v1.parquetExemplo com hard negatives e perfil de cenario:
.venv/bin/python -m training.build_dataset \
--payloads-dir ./data/PayloadAllTheThings \
--seclists-dir ./data/SecLists \
--hard-negatives-path ./data/raw/hard_negatives \
--hard-negative-ratio 0.25 \
--scenario-profile b2b \
--campaign-id campaign_crapi_v2 \
--output ./data/curated/campaign_crapi_v2.parquetImpacto no gateway nesta fase:
- nenhum ajuste de runtime e necessario;
- o artefato ONNX de inferencia permanece compativel.
Guia detalhado de upgrade:
docs/p0_schema_upgrade.mddocs/p1_dataset_governance.md
TELEMETRY_INPUT=./data/telemetry/telemetry_real.parquet make layer3make layer3Saídas:
data/raw/telemetry_*.parquetmodels/global_anomaly_*.onnx(preferencial)models/global_anomaly_*.pkl(fallback se conversão ONNX falhar)models/global_anomaly_latest.onnxoumodels/global_anomaly_latest.pkl
make allEquivalente a: bootstrap -> Camada 1 -> Camada 3.
Gerar chaves de assinatura:
.venv/bin/python -m training.bundle_packager gen-keys \
--private-key ./keys/model_signing_private.b64 \
--public-key ./keys/model_signing_public.b64Rodar layer1 com bundle automático:
export DORSAL_MODEL_SIGNING_PRIVATE_KEY=./keys/model_signing_private.b64
export DORSAL_MODEL_KEK='troque-por-segredo-forte'
make layer1Bundle gerado em models/bundles/<model_name>/ com:
model.encmanifest.jsonsignature.sigfeature_map.jsonbundle.meta.json
make weeklyComportamento:
- prepara workspace;
- atualiza fontes públicas;
- executa Camada 1 e Camada 3;
- opcionalmente build/push de gateway se
ENABLE_GATEWAY_BUILD=1.
Logs ficam em logs/weekly_retrain_*.log.
Use configs/pipeline.env.example:
cp configs/pipeline.env.example .env
set -a; source .env; set +aDepois rode qualquer target (make layer1, make layer3, make weekly).
.venv/bin/python -m training.build_dataset --help
.venv/bin/python -m training.train_attack_model --help
.venv/bin/python -m training.validate_model --help
.venv/bin/python -m training.benchmark_inference --help
.venv/bin/python -m training.train_anomaly_model --help
.venv/bin/python -m training.promotion_gate --help
.venv/bin/python scripts/fetch_telemetry.py --help- Camada 1:
precision >= 0.92,recall >= 0.85,fpr <= 0.03. - Camada 1 (slice gates): aplicar thresholds por
scenario_type,validation_tier,target_appeattack_family. - Benchmark ONNX: validar P50/P95/P99 com lote 1 e 32.
- Camada 3: usar holdout por tenant quando houver labels reais.
- Nunca usar
dorsal_scorecomo label de treino.
data/
raw/
intermediate/
curated/
dast/
models/
attack_*.onnx
global_anomaly_*.onnx
bundles/
reports/
keys/
logs/