Merge dev into main: resolve conflicts, keep tests out of main
Some checks failed
Release / Auto-tag release (push) Successful in 14s
Release / Build, scan & push cowrie (push) Failing after 6m9s
Release / Build, scan & push docker_api (push) Failing after 31s
Release / Build, scan & push elasticsearch (push) Failing after 30s
Release / Build, scan & push ftp (push) Failing after 30s
Release / Build, scan & push http (push) Failing after 33s
Release / Build, scan & push imap (push) Failing after 30s
Release / Build, scan & push k8s (push) Failing after 30s
Release / Build, scan & push ldap (push) Failing after 33s
Release / Build, scan & push llmnr (push) Failing after 29s
Release / Build, scan & push mongodb (push) Failing after 30s
Release / Build, scan & push mqtt (push) Failing after 30s
Release / Build, scan & push mssql (push) Failing after 30s
Release / Build, scan & push mysql (push) Failing after 30s
Release / Build, scan & push pop3 (push) Failing after 32s
Release / Build, scan & push postgres (push) Failing after 29s
Release / Build, scan & push rdp (push) Failing after 29s
Release / Build, scan & push real_ssh (push) Failing after 31s
Release / Build, scan & push redis (push) Failing after 29s
Release / Build, scan & push sip (push) Failing after 30s
Release / Build, scan & push smb (push) Failing after 32s
Release / Build, scan & push smtp (push) Failing after 31s
Release / Build, scan & push snmp (push) Failing after 29s
Release / Build, scan & push tftp (push) Failing after 29s
Release / Build, scan & push vnc (push) Failing after 30s
Some checks failed
Release / Auto-tag release (push) Successful in 14s
Release / Build, scan & push cowrie (push) Failing after 6m9s
Release / Build, scan & push docker_api (push) Failing after 31s
Release / Build, scan & push elasticsearch (push) Failing after 30s
Release / Build, scan & push ftp (push) Failing after 30s
Release / Build, scan & push http (push) Failing after 33s
Release / Build, scan & push imap (push) Failing after 30s
Release / Build, scan & push k8s (push) Failing after 30s
Release / Build, scan & push ldap (push) Failing after 33s
Release / Build, scan & push llmnr (push) Failing after 29s
Release / Build, scan & push mongodb (push) Failing after 30s
Release / Build, scan & push mqtt (push) Failing after 30s
Release / Build, scan & push mssql (push) Failing after 30s
Release / Build, scan & push mysql (push) Failing after 30s
Release / Build, scan & push pop3 (push) Failing after 32s
Release / Build, scan & push postgres (push) Failing after 29s
Release / Build, scan & push rdp (push) Failing after 29s
Release / Build, scan & push real_ssh (push) Failing after 31s
Release / Build, scan & push redis (push) Failing after 29s
Release / Build, scan & push sip (push) Failing after 30s
Release / Build, scan & push smb (push) Failing after 32s
Release / Build, scan & push smtp (push) Failing after 31s
Release / Build, scan & push snmp (push) Failing after 29s
Release / Build, scan & push tftp (push) Failing after 29s
Release / Build, scan & push vnc (push) Failing after 30s
This commit is contained in:
86
.gitea/workflows/ci.yml
Normal file
86
.gitea/workflows/ci.yml
Normal file
@@ -0,0 +1,86 @@
|
|||||||
|
name: CI
|
||||||
|
|
||||||
|
on:
|
||||||
|
push:
|
||||||
|
branches: [dev, testing]
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
lint:
|
||||||
|
name: Lint (ruff)
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v4
|
||||||
|
- uses: actions/setup-python@v5
|
||||||
|
with:
|
||||||
|
python-version: "3.11"
|
||||||
|
- run: pip install ruff
|
||||||
|
- run: ruff check .
|
||||||
|
|
||||||
|
test:
|
||||||
|
name: Test (pytest)
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
strategy:
|
||||||
|
matrix:
|
||||||
|
python-version: ["3.11", "3.12"]
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v4
|
||||||
|
- uses: actions/setup-python@v5
|
||||||
|
with:
|
||||||
|
python-version: ${{ matrix.python-version }}
|
||||||
|
- run: pip install -e .
|
||||||
|
- run: pytest tests/ -v --tb=short
|
||||||
|
|
||||||
|
bandit:
|
||||||
|
name: SAST (bandit)
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v4
|
||||||
|
- uses: actions/setup-python@v5
|
||||||
|
with:
|
||||||
|
python-version: "3.11"
|
||||||
|
- run: pip install bandit
|
||||||
|
- run: bandit -r decnet/ -ll -x decnet/services/registry.py
|
||||||
|
|
||||||
|
pip-audit:
|
||||||
|
name: Dependency audit (pip-audit)
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v4
|
||||||
|
- uses: actions/setup-python@v5
|
||||||
|
with:
|
||||||
|
python-version: "3.11"
|
||||||
|
- run: pip install pip-audit
|
||||||
|
- run: pip install -e .
|
||||||
|
- run: pip-audit --skip-editable
|
||||||
|
|
||||||
|
open-pr:
|
||||||
|
name: Open PR to main
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
needs: [lint, test, bandit, pip-audit]
|
||||||
|
if: github.ref == 'refs/heads/dev'
|
||||||
|
steps:
|
||||||
|
- name: Open PR via Gitea API
|
||||||
|
run: |
|
||||||
|
echo "--- Checking for existing open PRs ---"
|
||||||
|
LIST_RESPONSE=$(curl -s \
|
||||||
|
-H "Authorization: token ${{ secrets.DECNET_PR_TOKEN }}" \
|
||||||
|
"https://git.resacachile.cl/api/v1/repos/anti/DECNET/pulls?state=open&head=anti:dev&base=main&limit=5")
|
||||||
|
echo "$LIST_RESPONSE"
|
||||||
|
EXISTING=$(echo "$LIST_RESPONSE" | python3 -c "import sys, json; print(len(json.load(sys.stdin)))")
|
||||||
|
echo "Open PRs found: $EXISTING"
|
||||||
|
if [ "$EXISTING" -gt "0" ]; then
|
||||||
|
echo "PR already open, skipping."
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
echo "--- Creating PR ---"
|
||||||
|
CREATE_RESPONSE=$(curl -s -X POST \
|
||||||
|
-H "Authorization: token ${{ secrets.DECNET_PR_TOKEN }}" \
|
||||||
|
-H "Content-Type: application/json" \
|
||||||
|
-d '{
|
||||||
|
"title": "Auto PR: dev → main",
|
||||||
|
"head": "dev",
|
||||||
|
"base": "main",
|
||||||
|
"body": "All CI and security checks passed. Review and merge when ready."
|
||||||
|
}' \
|
||||||
|
"https://git.resacachile.cl/api/v1/repos/anti/DECNET/pulls")
|
||||||
|
echo "$CREATE_RESPONSE"
|
||||||
31
.gitea/workflows/pr.yml
Normal file
31
.gitea/workflows/pr.yml
Normal file
@@ -0,0 +1,31 @@
|
|||||||
|
name: PR Gate
|
||||||
|
|
||||||
|
on:
|
||||||
|
pull_request:
|
||||||
|
branches: [main]
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
lint:
|
||||||
|
name: Lint (ruff)
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v4
|
||||||
|
- uses: actions/setup-python@v5
|
||||||
|
with:
|
||||||
|
python-version: "3.11"
|
||||||
|
- run: pip install ruff
|
||||||
|
- run: ruff check .
|
||||||
|
|
||||||
|
test:
|
||||||
|
name: Test (pytest)
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
strategy:
|
||||||
|
matrix:
|
||||||
|
python-version: ["3.11", "3.12"]
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v4
|
||||||
|
- uses: actions/setup-python@v5
|
||||||
|
with:
|
||||||
|
python-version: ${{ matrix.python-version }}
|
||||||
|
- run: pip install -e .
|
||||||
|
- run: pytest tests/ -v --tb=short
|
||||||
@@ -42,7 +42,7 @@ jobs:
|
|||||||
fi
|
fi
|
||||||
|
|
||||||
docker:
|
docker:
|
||||||
name: Build & push ${{ matrix.service }}
|
name: Build, scan & push ${{ matrix.service }}
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
needs: tag
|
needs: tag
|
||||||
strategy:
|
strategy:
|
||||||
@@ -76,6 +76,9 @@ jobs:
|
|||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v4
|
- uses: actions/checkout@v4
|
||||||
|
|
||||||
|
- name: Set up Docker Buildx
|
||||||
|
uses: docker/setup-buildx-action@v3
|
||||||
|
|
||||||
- name: Log in to Gitea container registry
|
- name: Log in to Gitea container registry
|
||||||
uses: docker/login-action@v3
|
uses: docker/login-action@v3
|
||||||
with:
|
with:
|
||||||
@@ -83,7 +86,26 @@ jobs:
|
|||||||
username: ${{ secrets.REGISTRY_USER }}
|
username: ${{ secrets.REGISTRY_USER }}
|
||||||
password: ${{ secrets.REGISTRY_TOKEN }}
|
password: ${{ secrets.REGISTRY_TOKEN }}
|
||||||
|
|
||||||
- name: Build and push
|
- name: Build image locally
|
||||||
|
uses: docker/build-push-action@v5
|
||||||
|
with:
|
||||||
|
context: templates/${{ matrix.service }}
|
||||||
|
load: true
|
||||||
|
push: false
|
||||||
|
tags: decnet-${{ matrix.service }}:scan
|
||||||
|
cache-from: type=gha
|
||||||
|
cache-to: type=gha,mode=max
|
||||||
|
|
||||||
|
- name: Scan with Trivy
|
||||||
|
uses: aquasecurity/trivy-action@master
|
||||||
|
with:
|
||||||
|
image-ref: decnet-${{ matrix.service }}:scan
|
||||||
|
exit-code: "1"
|
||||||
|
severity: CRITICAL
|
||||||
|
ignore-unfixed: true
|
||||||
|
|
||||||
|
- name: Push image
|
||||||
|
if: success()
|
||||||
uses: docker/build-push-action@v5
|
uses: docker/build-push-action@v5
|
||||||
with:
|
with:
|
||||||
context: templates/${{ matrix.service }}
|
context: templates/${{ matrix.service }}
|
||||||
@@ -91,3 +113,4 @@ jobs:
|
|||||||
tags: |
|
tags: |
|
||||||
${{ env.REGISTRY }}/${{ env.OWNER }}/decnet-${{ matrix.service }}:latest
|
${{ env.REGISTRY }}/${{ env.OWNER }}/decnet-${{ matrix.service }}:latest
|
||||||
${{ env.REGISTRY }}/${{ env.OWNER }}/decnet-${{ matrix.service }}:v${{ needs.tag.outputs.version }}
|
${{ env.REGISTRY }}/${{ env.OWNER }}/decnet-${{ matrix.service }}:v${{ needs.tag.outputs.version }}
|
||||||
|
cache-from: type=gha
|
||||||
|
|||||||
7
.gitignore
vendored
7
.gitignore
vendored
@@ -9,3 +9,10 @@ decnet-compose.yml
|
|||||||
decnet-state.json
|
decnet-state.json
|
||||||
*.ini
|
*.ini
|
||||||
.env
|
.env
|
||||||
|
decnet.log*
|
||||||
|
*.loggy
|
||||||
|
*.nmap
|
||||||
|
linterfails.log
|
||||||
|
test-scan
|
||||||
|
webmail
|
||||||
|
windows1
|
||||||
|
|||||||
@@ -54,3 +54,4 @@ DECNET is a honeypot/deception network framework. It deploys fake machines (call
|
|||||||
- NEVER pass broken code to the user.
|
- NEVER pass broken code to the user.
|
||||||
- Broken means: not running, not passing 100% tests, etc.
|
- Broken means: not running, not passing 100% tests, etc.
|
||||||
- After tests pass with 100%, always git commit your changes.
|
- After tests pass with 100%, always git commit your changes.
|
||||||
|
- NEVER add "Co-Authored-By" or any Claude attribution lines to git commit messages.
|
||||||
|
|||||||
1
DEVELOPMENT.md
Normal file
1
DEVELOPMENT.md
Normal file
@@ -0,0 +1 @@
|
|||||||
|
CI/CD TEST 2
|
||||||
60
NOTES.md
60
NOTES.md
@@ -51,3 +51,63 @@ docker network create -d macvlan \
|
|||||||
#### Issues
|
#### Issues
|
||||||
|
|
||||||
This initial test doesn't seem to be working. Might be that I'm using WSL, so I downloaded a Ubuntu 22.04 Server ISO. I'll try the MACVLAN network on it. Now, if that doesn't work, I don't see how the 802.1q would work, at least on _my network_. Perhaps if I had a switch I could make it work, but currently I don't have one :c
|
This initial test doesn't seem to be working. Might be that I'm using WSL, so I downloaded a Ubuntu 22.04 Server ISO. I'll try the MACVLAN network on it. Now, if that doesn't work, I don't see how the 802.1q would work, at least on _my network_. Perhaps if I had a switch I could make it work, but currently I don't have one :c
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
# TODO
|
||||||
|
|
||||||
|
## Core / Hardening
|
||||||
|
|
||||||
|
- [ ] **Attacker fingerprinting** — Beyond IP logging: capture TLS JA3/JA4 hashes, TCP window sizes, User-Agent strings, SSH client banners, and tool signatures (nmap, masscan, Metasploit, Cobalt Strike). Build attacker profiles across sessions.
|
||||||
|
- [ ] **Canary tokens** — Embed canary URLs, fake AWS keys, fake API tokens, and honeydocs (PDF/DOCX with phone-home URLs) into decky filesystems. Fire an alert the moment one is used.
|
||||||
|
- [ ] **Tarpit mode** — Slow down attackers by making services respond extremely slowly (e.g., SSH that takes 60s to reject, HTTP that drip-feeds bytes). Wastes attacker time and resources.
|
||||||
|
- [ ] **Dynamic decky mutation** — Deckies that change their exposed services or OS fingerprint over time to confuse port-scan caching and appear more "alive."
|
||||||
|
- [ ] **Credential harvesting DB** — Every username/password attempt across all services lands in a queryable database. Expose via CLI (`decnet creds`) and flag reuse across deckies.
|
||||||
|
- [ ] **Session recording** — Full session capture for SSH/Telnet (keystroke logs, commands run, files downloaded). Cowrie already does this — surface it better in the CLI and correlation engine.
|
||||||
|
- [ ] **Payload capture** — Store every file uploaded or command executed by an attacker. Hash and auto-submit to VirusTotal or a local sandbox.
|
||||||
|
|
||||||
|
## Detection & Intelligence
|
||||||
|
|
||||||
|
- [ ] **Real-time alerting** — Webhook/Slack/Telegram notifications when an attacker hits a decky for the first time, crosses N deckies (lateral movement), or uses a known bad IP.
|
||||||
|
- [ ] **Threat intel enrichment** — Auto-lookup attacker IPs against AbuseIPDB, Shodan, GreyNoise, and AlienVault OTX. Tag known scanners vs. targeted attackers.
|
||||||
|
- [ ] **Attack campaign clustering** — Group attacker sessions by tooling signatures, timing patterns, and credential sets. Identify coordinated campaigns hitting multiple deckies.
|
||||||
|
- [ ] **GeoIP mapping** — Attacker origin on a world map. Correlate with ASN data to identify cloud exit nodes, VPNs, and Tor exits.
|
||||||
|
- [ ] **TTPs tagging** — Map observed attacker behaviors to MITRE ATT&CK techniques automatically. Tag events in the correlation engine.
|
||||||
|
- [ ] **Honeypot interaction scoring** — Score attackers on a scale: casual scanner vs. persistent targeted attacker, based on depth of interaction and commands run.
|
||||||
|
|
||||||
|
## Dashboard & Visibility
|
||||||
|
|
||||||
|
- [ ] **Web dashboard** — Real-time web UI showing live decky status, attacker activity, traversal graphs, and credential stats. Could be a simple FastAPI + HTMX or a full React app.
|
||||||
|
- [ ] **Pre-built Kibana/Grafana dashboards** — Ship dashboard JSON exports out of the box so ELK/Grafana deployments are plug-and-play.
|
||||||
|
- [ ] **CLI live feed** — `decnet watch` command: tail all decky logs in a unified, colored terminal stream (like `docker-compose logs -f` but prettier).
|
||||||
|
- [ ] **Traversal graph export** — Export attacker traversal graphs as DOT/Graphviz or JSON for visualization in external tools.
|
||||||
|
- [ ] **Daily digest** — Automated daily summary email/report: new attackers, top credentials tried, most-hit services.
|
||||||
|
|
||||||
|
## Deployment & Infrastructure
|
||||||
|
|
||||||
|
- [ ] **SWARM / multihost mode** — Full Ansible-based orchestration for deploying deckies across N real hosts.
|
||||||
|
- [ ] **Terraform/Pulumi provider** — Spin up cloud-hosted deckies on AWS/GCP/Azure with one command. Useful for internet-facing honeynets.
|
||||||
|
- [ ] **Auto-scaling** — When attack traffic increases, automatically spawn more deckies to absorb and log more activity.
|
||||||
|
- [ ] **Kubernetes deployment mode** — Run deckies as Kubernetes pods for environments already running k8s.
|
||||||
|
- [ ] **Proxmox/libvirt backend** — Full VM-based deckies instead of containers, for even more realistic OS fingerprints and behavior. Docker for speed; VMs for realism.
|
||||||
|
- [ ] **Raspberry Pi / ARM support** — Low-cost physical honeynets using RPis. Validate ARM image builds.
|
||||||
|
- [ ] **Decky health monitoring** — Watchdog that auto-restarts crashed deckies and alerts if a service goes dark.
|
||||||
|
|
||||||
|
## Services & Realism
|
||||||
|
|
||||||
|
- [ ] **HTTPS/TLS support** — HTTP honeypot with a self-signed or Let's Encrypt cert. Many real-world services use HTTPS; plain HTTP stands out.
|
||||||
|
- [ ] **Fake Active Directory** — A convincing fake AD/LDAP with fake users, groups, and GPOs. Attacker tools like BloodHound should get juicy (fake) data.
|
||||||
|
- [ ] **Fake file shares** — SMB/NFS shares pre-populated with enticing but fake files: "passwords.xlsx", "vpn_config.ovpn", "backup_keys.tar.gz". All instrumented to detect access.
|
||||||
|
- [ ] **Realistic web apps** — HTTP honeypot serving convincing fake apps: a fake WordPress, a fake phpMyAdmin, a fake Grafana login — all logging every interaction.
|
||||||
|
- [ ] **OT/ICS profiles** — Expand Conpot support: Modbus, DNP3, BACnet, EtherNet/IP. Convincing industrial control system decoys.
|
||||||
|
- [ ] **Printer/IoT archetypes** — Expand existing printer/camera archetypes with actual service emulation (IPP, ONVIF, WS-Discovery).
|
||||||
|
- [ ] **Service interaction depth** — Some services currently just log the connection. Deepen interaction: fake MySQL that accepts queries and returns realistic fake data, fake Redis that stores and retrieves dummy keys.
|
||||||
|
|
||||||
|
## Developer Experience
|
||||||
|
|
||||||
|
- [ ] **Plugin SDK docs** — Full documentation and an example plugin for adding custom services. Lower the barrier for community contributions.
|
||||||
|
- [ ] **Integration tests** — Full deploy/teardown cycle tests against a real Docker daemon (not just unit tests).
|
||||||
|
- [ ] **Per-service tests** — Each of the 29 service implementations deserves its own test coverage.
|
||||||
|
- [ ] **CI/CD pipeline** — GitHub/Gitea Actions: run tests on push, lint, build Docker images, publish releases.
|
||||||
|
- [ ] **Config validation CLI** — `decnet validate my.ini` to dry-check an INI config before deploying.
|
||||||
|
- [ ] **Config generator wizard** — `decnet wizard` interactive prompt to generate an INI config without writing one by hand.
|
||||||
|
|||||||
@@ -22,7 +22,6 @@ Usage
|
|||||||
|
|
||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
import json
|
|
||||||
from collections import defaultdict
|
from collections import defaultdict
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ The attacker IP may appear under several field names depending on service:
|
|||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
import re
|
import re
|
||||||
from dataclasses import dataclass, field
|
from dataclasses import dataclass
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
|
|
||||||
# RFC 5424 line structure
|
# RFC 5424 line structure
|
||||||
|
|||||||
@@ -14,11 +14,8 @@ from decnet.config import DecnetConfig, clear_state, load_state, save_state
|
|||||||
from decnet.composer import write_compose
|
from decnet.composer import write_compose
|
||||||
from decnet.network import (
|
from decnet.network import (
|
||||||
MACVLAN_NETWORK_NAME,
|
MACVLAN_NETWORK_NAME,
|
||||||
allocate_ips,
|
|
||||||
create_ipvlan_network,
|
create_ipvlan_network,
|
||||||
create_macvlan_network,
|
create_macvlan_network,
|
||||||
detect_interface,
|
|
||||||
detect_subnet,
|
|
||||||
get_host_ip,
|
get_host_ip,
|
||||||
ips_to_range,
|
ips_to_range,
|
||||||
remove_macvlan_network,
|
remove_macvlan_network,
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Rotating file handler for DECNET syslog output.
|
Rotating file handler for DECNET syslog output.
|
||||||
|
|
||||||
@@ -7,6 +6,8 @@ Path is controlled by the DECNET_LOG_FILE environment variable
|
|||||||
(default: /var/log/decnet/decnet.log).
|
(default: /var/log/decnet/decnet.log).
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
from __future__ import annotations
|
||||||
|
|
||||||
import logging
|
import logging
|
||||||
import logging.handlers
|
import logging.handlers
|
||||||
import os
|
import os
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
RFC 5424 syslog formatter for DECNET.
|
RFC 5424 syslog formatter for DECNET.
|
||||||
|
|
||||||
@@ -9,6 +8,8 @@ Facility: local0 (16)
|
|||||||
PEN for structured data: decnet@55555
|
PEN for structured data: decnet@55555
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
from __future__ import annotations
|
||||||
|
|
||||||
from datetime import datetime, timezone
|
from datetime import datetime, timezone
|
||||||
from typing import Any
|
from typing import Any
|
||||||
|
|
||||||
|
|||||||
@@ -8,10 +8,7 @@ Handles:
|
|||||||
- IP allocation (sequential, skipping reserved addresses)
|
- IP allocation (sequential, skipping reserved addresses)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import ipaddress
|
|
||||||
import os
|
import os
|
||||||
import shutil
|
|
||||||
import socket
|
|
||||||
import subprocess
|
import subprocess
|
||||||
from ipaddress import IPv4Address, IPv4Interface, IPv4Network
|
from ipaddress import IPv4Address, IPv4Interface, IPv4Network
|
||||||
|
|
||||||
|
|||||||
@@ -26,6 +26,8 @@ def _load_plugins() -> None:
|
|||||||
continue
|
continue
|
||||||
importlib.import_module(f"decnet.services.{module_info.name}")
|
importlib.import_module(f"decnet.services.{module_info.name}")
|
||||||
for cls in BaseService.__subclasses__():
|
for cls in BaseService.__subclasses__():
|
||||||
|
if not cls.__module__.startswith("decnet.services."):
|
||||||
|
continue
|
||||||
instance = cls()
|
instance = cls()
|
||||||
_registry[instance.name] = instance
|
_registry[instance.name] = instance
|
||||||
_loaded = True
|
_loaded = True
|
||||||
|
|||||||
@@ -13,6 +13,10 @@ dependencies = [
|
|||||||
"docker>=7.0",
|
"docker>=7.0",
|
||||||
"pyyaml>=6.0",
|
"pyyaml>=6.0",
|
||||||
"jinja2>=3.1",
|
"jinja2>=3.1",
|
||||||
|
"pytest>=8.0",
|
||||||
|
"ruff>=0.4",
|
||||||
|
"bandit>=1.7",
|
||||||
|
"pip-audit>=2.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
[project.scripts]
|
[project.scripts]
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -8,8 +8,6 @@ but fake data. Logs all requests as JSON.
|
|||||||
|
|
||||||
import json
|
import json
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
|
|
||||||
from flask import Flask, request
|
from flask import Flask, request
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,8 +7,6 @@ as JSON. Designed to attract automated scanners and credential stuffers.
|
|||||||
|
|
||||||
import json
|
import json
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
from http.server import BaseHTTPRequestHandler, HTTPServer
|
from http.server import BaseHTTPRequestHandler, HTTPServer
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -5,13 +5,10 @@ Accepts any credentials, logs all commands and file requests,
|
|||||||
forwards events as JSON to LOG_TARGET if set.
|
forwards events as JSON to LOG_TARGET if set.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import sys
|
import sys
|
||||||
from datetime import datetime, timezone
|
|
||||||
|
|
||||||
from twisted.internet import defer, protocol, reactor
|
from twisted.internet import defer, reactor
|
||||||
from twisted.protocols.ftp import FTP, FTPFactory
|
from twisted.protocols.ftp import FTP, FTPFactory
|
||||||
from twisted.python import log as twisted_log
|
from twisted.python import log as twisted_log
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,8 +7,6 @@ and responds with configurable pages. Forwards events as JSON to LOG_TARGET if s
|
|||||||
|
|
||||||
import json
|
import json
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
|
||||||
from flask import Flask, request, send_from_directory
|
from flask import Flask, request, send_from_directory
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -6,10 +6,7 @@ AUTHENTICATE), then returns a NO response. Logs all commands as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "mailserver")
|
NODE_NAME = os.environ.get("NODE_NAME", "mailserver")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -8,8 +8,6 @@ Responds to recon endpoints (/version, /api, /apis, /api/v1/namespaces,
|
|||||||
|
|
||||||
import json
|
import json
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
|
|
||||||
from flask import Flask, request
|
from flask import Flask, request
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -6,10 +6,7 @@ invalidCredentials error. Logs all interactions as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "ldapserver")
|
NODE_NAME = os.environ.get("NODE_NAME", "ldapserver")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,11 +7,8 @@ Logs every packet with source IP and decoded query name where possible.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import struct
|
import struct
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "lan-host")
|
NODE_NAME = os.environ.get("NODE_NAME", "lan-host")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,11 +7,8 @@ received messages as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import struct
|
import struct
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "mongodb")
|
NODE_NAME = os.environ.get("NODE_NAME", "mongodb")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,11 +7,8 @@ interactions as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import struct
|
import struct
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "mqtt-broker")
|
NODE_NAME = os.environ.get("NODE_NAME", "mqtt-broker")
|
||||||
@@ -48,11 +45,13 @@ def _parse_connect(payload: bytes):
|
|||||||
# Protocol level (1 byte)
|
# Protocol level (1 byte)
|
||||||
if pos >= len(payload):
|
if pos >= len(payload):
|
||||||
return {}, pos
|
return {}, pos
|
||||||
_proto_level = payload[pos]; pos += 1
|
_proto_level = payload[pos]
|
||||||
|
pos += 1
|
||||||
# Connect flags (1 byte)
|
# Connect flags (1 byte)
|
||||||
if pos >= len(payload):
|
if pos >= len(payload):
|
||||||
return {}, pos
|
return {}, pos
|
||||||
flags = payload[pos]; pos += 1
|
flags = payload[pos]
|
||||||
|
pos += 1
|
||||||
# Keep alive (2 bytes)
|
# Keep alive (2 bytes)
|
||||||
pos += 2
|
pos += 2
|
||||||
# Client ID
|
# Client ID
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -6,11 +6,8 @@ a login failed error. Logs auth attempts as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import struct
|
import struct
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "dbserver")
|
NODE_NAME = os.environ.get("NODE_NAME", "dbserver")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,11 +7,8 @@ attempts as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import struct
|
import struct
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "dbserver")
|
NODE_NAME = os.environ.get("NODE_NAME", "dbserver")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,10 +7,7 @@ to LOG_TARGET if set.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "mailserver")
|
NODE_NAME = os.environ.get("NODE_NAME", "mailserver")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,11 +7,8 @@ returns an error. Logs all interactions as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import struct
|
import struct
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "pgserver")
|
NODE_NAME = os.environ.get("NODE_NAME", "pgserver")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -6,11 +6,8 @@ in the initial RDP negotiation request. Forwards events as JSON to
|
|||||||
LOG_TARGET if set.
|
LOG_TARGET if set.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import sys
|
import sys
|
||||||
from datetime import datetime, timezone
|
|
||||||
|
|
||||||
from twisted.internet import protocol, reactor
|
from twisted.internet import protocol, reactor
|
||||||
from twisted.python import log as twisted_log
|
from twisted.python import log as twisted_log
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -6,10 +6,7 @@ KEYS, and arbitrary commands. Logs every command and argument as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "cache-server")
|
NODE_NAME = os.environ.get("NODE_NAME", "cache-server")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -6,11 +6,8 @@ Authorization header and call metadata, then responds with 401 Unauthorized.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import re
|
import re
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "pbx")
|
NODE_NAME = os.environ.get("NODE_NAME", "pbx")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -4,10 +4,7 @@ Minimal SMB server using Impacket's SimpleSMBServer.
|
|||||||
Logs all connection attempts, optionally forwarding them as JSON to LOG_TARGET.
|
Logs all connection attempts, optionally forwarding them as JSON to LOG_TARGET.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
|
|
||||||
from impacket import smbserver
|
from impacket import smbserver
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -5,10 +5,7 @@ Logs EHLO/AUTH/MAIL FROM/RCPT TO attempts as JSON, then denies auth.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "mailserver")
|
NODE_NAME = os.environ.get("NODE_NAME", "mailserver")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,11 +7,8 @@ Logs all requests as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import struct
|
import struct
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "switch")
|
NODE_NAME = os.environ.get("NODE_NAME", "switch")
|
||||||
@@ -94,35 +91,46 @@ def _ber_tlv(tag: int, value: bytes) -> bytes:
|
|||||||
def _parse_snmp(data: bytes):
|
def _parse_snmp(data: bytes):
|
||||||
"""Return (version, community, request_id, oids) or raise."""
|
"""Return (version, community, request_id, oids) or raise."""
|
||||||
pos = 0
|
pos = 0
|
||||||
assert data[pos] == 0x30; pos += 1
|
assert data[pos] == 0x30
|
||||||
|
pos += 1
|
||||||
_, pos = _read_ber_length(data, pos)
|
_, pos = _read_ber_length(data, pos)
|
||||||
# version
|
# version
|
||||||
assert data[pos] == 0x02; pos += 1
|
assert data[pos] == 0x02
|
||||||
|
pos += 1
|
||||||
v_len, pos = _read_ber_length(data, pos)
|
v_len, pos = _read_ber_length(data, pos)
|
||||||
version = int.from_bytes(data[pos:pos + v_len], "big"); pos += v_len
|
version = int.from_bytes(data[pos:pos + v_len], "big")
|
||||||
|
pos += v_len
|
||||||
# community
|
# community
|
||||||
assert data[pos] == 0x04; pos += 1
|
assert data[pos] == 0x04
|
||||||
|
pos += 1
|
||||||
c_len, pos = _read_ber_length(data, pos)
|
c_len, pos = _read_ber_length(data, pos)
|
||||||
community = data[pos:pos + c_len].decode(errors="replace"); pos += c_len
|
community = data[pos:pos + c_len].decode(errors="replace")
|
||||||
|
pos += c_len
|
||||||
# PDU type (0xa0 = GetRequest, 0xa1 = GetNextRequest)
|
# PDU type (0xa0 = GetRequest, 0xa1 = GetNextRequest)
|
||||||
pdu_type = data[pos]; pos += 1
|
pos += 1
|
||||||
_, pos = _read_ber_length(data, pos)
|
_, pos = _read_ber_length(data, pos)
|
||||||
# request-id
|
# request-id
|
||||||
assert data[pos] == 0x02; pos += 1
|
assert data[pos] == 0x02
|
||||||
|
pos += 1
|
||||||
r_len, pos = _read_ber_length(data, pos)
|
r_len, pos = _read_ber_length(data, pos)
|
||||||
request_id = int.from_bytes(data[pos:pos + r_len], "big"); pos += r_len
|
request_id = int.from_bytes(data[pos:pos + r_len], "big")
|
||||||
|
pos += r_len
|
||||||
pos += 4 # skip error-status and error-index
|
pos += 4 # skip error-status and error-index
|
||||||
# varbind list
|
# varbind list
|
||||||
assert data[pos] == 0x30; pos += 1
|
assert data[pos] == 0x30
|
||||||
|
pos += 1
|
||||||
vbl_len, pos = _read_ber_length(data, pos)
|
vbl_len, pos = _read_ber_length(data, pos)
|
||||||
end = pos + vbl_len
|
end = pos + vbl_len
|
||||||
oids = []
|
oids = []
|
||||||
while pos < end:
|
while pos < end:
|
||||||
assert data[pos] == 0x30; pos += 1
|
assert data[pos] == 0x30
|
||||||
|
pos += 1
|
||||||
vb_len, pos = _read_ber_length(data, pos)
|
vb_len, pos = _read_ber_length(data, pos)
|
||||||
assert data[pos] == 0x06; pos += 1
|
assert data[pos] == 0x06
|
||||||
|
pos += 1
|
||||||
oid_len, pos = _read_ber_length(data, pos)
|
oid_len, pos = _read_ber_length(data, pos)
|
||||||
oid = _decode_oid(data[pos:pos + oid_len]); pos += oid_len
|
oid = _decode_oid(data[pos:pos + oid_len])
|
||||||
|
pos += oid_len
|
||||||
oids.append(oid)
|
oids.append(oid)
|
||||||
pos += vb_len - oid_len - 2 # skip value
|
pos += vb_len - oid_len - 2 # skip value
|
||||||
return version, community, request_id, oids
|
return version, community, request_id, oids
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -6,11 +6,8 @@ then responds with an error packet. Logs all requests as JSON.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
import struct
|
import struct
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "tftpserver")
|
NODE_NAME = os.environ.get("NODE_NAME", "tftpserver")
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
from __future__ import annotations
|
|
||||||
"""
|
"""
|
||||||
Shared RFC 5424 syslog helper for DECNET service templates.
|
Shared RFC 5424 syslog helper for DECNET service templates.
|
||||||
|
|
||||||
|
|||||||
@@ -7,10 +7,7 @@ failed". Logs the raw response for offline cracking.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import json
|
|
||||||
import os
|
import os
|
||||||
import socket
|
|
||||||
from datetime import datetime, timezone
|
|
||||||
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
from decnet_logging import syslog_line, write_syslog_file, forward_syslog
|
||||||
|
|
||||||
NODE_NAME = os.environ.get("NODE_NAME", "desktop")
|
NODE_NAME = os.environ.get("NODE_NAME", "desktop")
|
||||||
|
|||||||
98
test-scan
98
test-scan
@@ -1,98 +0,0 @@
|
|||||||
# Nmap 7.92 scan initiated Sat Apr 4 04:41:05 2026 as: nmap -sS -sV -O -A -oN test-scan 192.168.1.110-119
|
|
||||||
Nmap scan report for 192.168.1.110
|
|
||||||
Host is up (0.000035s latency).
|
|
||||||
Not shown: 996 closed tcp ports (reset)
|
|
||||||
PORT STATE SERVICE VERSION
|
|
||||||
25/tcp open smtp Postfix smtpd
|
|
||||||
|_smtp-commands: decky-webmail, PIPELINING, SIZE 10240000, VRFY, ETRN, AUTH PLAIN LOGIN, ENHANCEDSTATUSCODES, 8BITMIME, DSN
|
|
||||||
80/tcp open http Apache httpd 2.4.54 ((Debian))
|
|
||||||
|_http-title: WordPress › Error
|
|
||||||
|_http-server-header: Werkzeug/3.1.8 Python/3.11.2
|
|
||||||
110/tcp open pop3
|
|
||||||
| fingerprint-strings:
|
|
||||||
| GenericLines, HTTPOptions:
|
|
||||||
| +OK decky-webmail POP3 server ready
|
|
||||||
| -ERR Unknown command
|
|
||||||
| -ERR Unknown command
|
|
||||||
| NULL:
|
|
||||||
|_ +OK decky-webmail POP3 server ready
|
|
||||||
|_pop3-capabilities: USER
|
|
||||||
143/tcp open imap
|
|
||||||
| fingerprint-strings:
|
|
||||||
| GenericLines, NULL:
|
|
||||||
| * OK [decky-webmail] IMAP4rev1 Service Ready
|
|
||||||
| GetRequest:
|
|
||||||
| * OK [decky-webmail] IMAP4rev1 Service Ready
|
|
||||||
|_ Command not recognized
|
|
||||||
|_imap-capabilities: OK CAPABILITY AUTH=LOGINA0001 IMAP4rev1 completed AUTH=PLAIN
|
|
||||||
2 services unrecognized despite returning data. If you know the service/version, please submit the following fingerprints at https://nmap.org/cgi-bin/submit.cgi?new-service :
|
|
||||||
==============NEXT SERVICE FINGERPRINT (SUBMIT INDIVIDUALLY)==============
|
|
||||||
SF-Port110-TCP:V=7.92%I=7%D=4/4%Time=69D0C099%P=x86_64-redhat-linux-gnu%r(
|
|
||||||
SF:NULL,25,"\+OK\x20decky-webmail\x20POP3\x20server\x20ready\r\n")%r(Gener
|
|
||||||
SF:icLines,51,"\+OK\x20decky-webmail\x20POP3\x20server\x20ready\r\n-ERR\x2
|
|
||||||
SF:0Unknown\x20command\r\n-ERR\x20Unknown\x20command\r\n")%r(HTTPOptions,5
|
|
||||||
SF:1,"\+OK\x20decky-webmail\x20POP3\x20server\x20ready\r\n-ERR\x20Unknown\
|
|
||||||
SF:x20command\r\n-ERR\x20Unknown\x20command\r\n");
|
|
||||||
==============NEXT SERVICE FINGERPRINT (SUBMIT INDIVIDUALLY)==============
|
|
||||||
SF-Port143-TCP:V=7.92%I=7%D=4/4%Time=69D0C099%P=x86_64-redhat-linux-gnu%r(
|
|
||||||
SF:NULL,2E,"\*\x20OK\x20\[decky-webmail\]\x20IMAP4rev1\x20Service\x20Ready
|
|
||||||
SF:\r\n")%r(GetRequest,4E,"\*\x20OK\x20\[decky-webmail\]\x20IMAP4rev1\x20S
|
|
||||||
SF:ervice\x20Ready\r\nGET\x20BAD\x20Command\x20not\x20recognized\r\n")%r(G
|
|
||||||
SF:enericLines,2E,"\*\x20OK\x20\[decky-webmail\]\x20IMAP4rev1\x20Service\x
|
|
||||||
SF:20Ready\r\n");
|
|
||||||
MAC Address: D2:55:C7:0D:B4:FC (Unknown)
|
|
||||||
Device type: general purpose
|
|
||||||
Running: Linux 5.X
|
|
||||||
OS CPE: cpe:/o:linux:linux_kernel:5
|
|
||||||
OS details: Linux 5.3 - 5.4
|
|
||||||
Network Distance: 1 hop
|
|
||||||
Service Info: Host: decky-webmail
|
|
||||||
|
|
||||||
TRACEROUTE
|
|
||||||
HOP RTT ADDRESS
|
|
||||||
1 0.04 ms 192.168.1.110
|
|
||||||
|
|
||||||
Nmap scan report for 192.168.1.111
|
|
||||||
Host is up (0.000016s latency).
|
|
||||||
Not shown: 998 closed tcp ports (reset)
|
|
||||||
PORT STATE SERVICE VERSION
|
|
||||||
21/tcp open ftp vsftpd (before 2.0.8) or WU-FTPD
|
|
||||||
445/tcp open microsoft-ds
|
|
||||||
| fingerprint-strings:
|
|
||||||
| SMBProgNeg:
|
|
||||||
| SMBr
|
|
||||||
|_ "3DUfw
|
|
||||||
1 service unrecognized despite returning data. If you know the service/version, please submit the following fingerprint at https://nmap.org/cgi-bin/submit.cgi?new-service :
|
|
||||||
SF-Port445-TCP:V=7.92%I=7%D=4/4%Time=69D0C09E%P=x86_64-redhat-linux-gnu%r(
|
|
||||||
SF:SMBProgNeg,51,"\0\0\0M\xffSMBr\0\0\0\0\x80\0\xc0\0\0\0\0\0\0\0\0\0\0\0\
|
|
||||||
SF:0\0\0@\x06\0\0\x01\0\x11\x07\0\x03\x01\0\x01\0\0\xfa\0\0\0\0\x01\0\0\0\
|
|
||||||
SF:0\0p\0\0\0\0\0\0\0\0\0\0\0\0\0\x08\x08\0\x11\"3DUfw\x88");
|
|
||||||
MAC Address: 92:44:B7:6C:F6:D0 (Unknown)
|
|
||||||
Device type: general purpose
|
|
||||||
Running: Linux 5.X
|
|
||||||
OS CPE: cpe:/o:linux:linux_kernel:5
|
|
||||||
OS details: Linux 5.3 - 5.4
|
|
||||||
Network Distance: 1 hop
|
|
||||||
Service Info: Host: Twisted
|
|
||||||
|
|
||||||
Host script results:
|
|
||||||
| smb-security-mode:
|
|
||||||
| account_used: guest
|
|
||||||
| authentication_level: user
|
|
||||||
| challenge_response: supported
|
|
||||||
|_ message_signing: disabled (dangerous, but default)
|
|
||||||
| smb2-time:
|
|
||||||
| date: 2026-04-04T07:41:24
|
|
||||||
|_ start_date: 2026-04-04T07:41:24
|
|
||||||
| smb2-security-mode:
|
|
||||||
| 2.0.2:
|
|
||||||
|_ Message signing enabled but not required
|
|
||||||
|_ms-sql-info: ERROR: Script execution failed (use -d to debug)
|
|
||||||
|_clock-skew: mean: -77660d15h50m42s, deviation: 109828d18h12m51s, median: -155321d07h41m24s
|
|
||||||
|
|
||||||
TRACEROUTE
|
|
||||||
HOP RTT ADDRESS
|
|
||||||
1 0.02 ms 192.168.1.111
|
|
||||||
|
|
||||||
OS and Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
|
|
||||||
# Nmap done at Sat Apr 4 04:41:33 2026 -- 10 IP addresses (2 hosts up) scanned in 28.27 seconds
|
|
||||||
61
tests/test_build.py
Normal file
61
tests/test_build.py
Normal file
@@ -0,0 +1,61 @@
|
|||||||
|
"""Smoke test: verify the package and all submodules import cleanly."""
|
||||||
|
import importlib
|
||||||
|
import pytest
|
||||||
|
|
||||||
|
|
||||||
|
MODULES = [
|
||||||
|
"decnet",
|
||||||
|
"decnet.cli",
|
||||||
|
"decnet.config",
|
||||||
|
"decnet.composer",
|
||||||
|
"decnet.deployer",
|
||||||
|
"decnet.network",
|
||||||
|
"decnet.archetypes",
|
||||||
|
"decnet.distros",
|
||||||
|
"decnet.os_fingerprint",
|
||||||
|
"decnet.ini_loader",
|
||||||
|
"decnet.custom_service",
|
||||||
|
"decnet.correlation",
|
||||||
|
"decnet.correlation.engine",
|
||||||
|
"decnet.correlation.graph",
|
||||||
|
"decnet.correlation.parser",
|
||||||
|
"decnet.logging",
|
||||||
|
"decnet.logging.file_handler",
|
||||||
|
"decnet.logging.forwarder",
|
||||||
|
"decnet.logging.syslog_formatter",
|
||||||
|
"decnet.services",
|
||||||
|
"decnet.services.registry",
|
||||||
|
"decnet.services.base",
|
||||||
|
"decnet.services.ssh",
|
||||||
|
"decnet.services.ftp",
|
||||||
|
"decnet.services.http",
|
||||||
|
"decnet.services.smb",
|
||||||
|
"decnet.services.rdp",
|
||||||
|
"decnet.services.smtp",
|
||||||
|
"decnet.services.mysql",
|
||||||
|
"decnet.services.postgres",
|
||||||
|
"decnet.services.redis",
|
||||||
|
"decnet.services.mongodb",
|
||||||
|
"decnet.services.mssql",
|
||||||
|
"decnet.services.elasticsearch",
|
||||||
|
"decnet.services.ldap",
|
||||||
|
"decnet.services.k8s",
|
||||||
|
"decnet.services.docker_api",
|
||||||
|
"decnet.services.vnc",
|
||||||
|
"decnet.services.telnet",
|
||||||
|
"decnet.services.tftp",
|
||||||
|
"decnet.services.snmp",
|
||||||
|
"decnet.services.sip",
|
||||||
|
"decnet.services.mqtt",
|
||||||
|
"decnet.services.llmnr",
|
||||||
|
"decnet.services.imap",
|
||||||
|
"decnet.services.pop3",
|
||||||
|
"decnet.services.conpot",
|
||||||
|
"decnet.services.real_ssh",
|
||||||
|
"decnet.services.registry",
|
||||||
|
]
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.parametrize("module", MODULES)
|
||||||
|
def test_module_imports(module):
|
||||||
|
importlib.import_module(module)
|
||||||
Reference in New Issue
Block a user