-
Notifications
You must be signed in to change notification settings - Fork 96
Expand file tree
/
Copy pathpyproject.toml
More file actions
190 lines (183 loc) · 8.35 KB
/
Copy pathpyproject.toml
File metadata and controls
190 lines (183 loc) · 8.35 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
[build-system]
requires = ["setuptools>=61.0", "wheel"]
build-backend = "setuptools.build_meta"
[project]
name = "adscan"
version = "13.1.0"
description = "Free Active Directory pentesting CLI for AD enumeration, attack paths, Kerberoasting, AS-REP roasting, ADCS, DCSync, password spraying, and CTF labs."
readme = "README.md"
authors = [{ name = "ADscan" }]
requires-python = ">=3.10"
keywords = [
"active-directory",
"activedirectory",
"pentesting",
"penetration-testing",
"enumeration",
"kerberoasting",
"as-rep-roasting",
"adcs",
"dcsync",
"password-spraying",
"red-team",
"ctf",
]
classifiers = [
"Programming Language :: Python :: 3",
"Operating System :: POSIX :: Linux",
"Environment :: Console",
"Intended Audience :: Information Technology",
"Topic :: Security",
"Topic :: System :: Networking",
]
dependencies = [
"rich>=13.0,<16.0",
"requests>=2.31.0,<3.0",
"packaging>=23.0,<27.0",
"certifi>=2023.0.0",
"credsweeper==1.18.3",
"sentry-sdk>=1.40.0,<3.0",
]
[project.optional-dependencies]
dev = [
# badauth + asysocks are foundational to the native stack (badauth: NTLM/
# SPNEGO/credential primitives consumed by aiosmb/badldap/aardwolf/kerbad;
# asysocks: the async network layer). They are declared here as DIRECT deps
# — not just transitively via their consumers — so the vendor path overrides
# in [tool.uv.sources] actually take effect. uv only applies a source
# override to a package the project directly depends on; without these two
# lines uv resolved badauth/asysocks from PyPI, so the LOCALLY_MAINTAINED
# vendor/ patches (e.g. the NetNTLMv1-downgrade crack fix in badauth) were
# dead in the uv-managed venv + CI even though production Docker installs
# vendor/ directly. Keep in lockstep with the [cli] extra.
"badauth>=0.1.6",
"asysocks>=0.2.18",
"badldap>=0.7.5,<0.8",
"kerbad>=0.5.9",
"impacket==0.13.1",
"pytest>=8.0,<10.0",
# pytest-timeout converts hung tests into explicit failures with a
# stack trace at the deadline instead of letting them stall CI for
# hours. Configured in pytest.ini with a 60s default per test plus
# ``thread`` method so the timeout works regardless of whether the
# test is blocked on Python or in a C-level call.
"pytest-timeout>=2.3,<3.0",
# pytest-xdist distributes the unit suite across worker processes. The
# suite is ~13k tests and takes about ten minutes in one process, which is
# too long to run before every commit and far too long to run on every
# push to an active branch. Across the cores of a normal dev machine it is
# about a hundred seconds, which is short enough to be both. See
# pytest.ini for why the split is `--dist loadfile` and why it is a default.
"pytest-xdist>=3.6,<4.0",
"PyYAML>=6.0,<7.0",
"ruff>=0.9.0,<1.0",
"build>=1.2.0,<2.0",
"twine>=6.0.0,<7.0",
"mypy>=1.8.0",
"types-requests",
"pytest-html",
"jinja2",
"winacl==0.1.9",
# Pure-Python forensic stack for offline VM disk-image credential extraction
# (vm_artifact_service): dissect.target follows VMware sparse / Hyper-V VHDX
# chains and walks NTFS in userspace (no root, no mount, no subprocess).
"dissect.target>=3.20,<4.0",
# Offline VM MEMORY-image credential extraction (vm_artifact_service): Volatility 3
# carves raw guest RAM (.vmem/.vmrs) for SAM/LSA/cached creds. pycryptodome is
# REQUIRED or vol3's credential plugins silently fail to register.
"volatility3>=2.5.0",
"pycryptodome>=3.20",
]
cli = [
# Direct declarations so the vendor/ path overrides in [tool.uv.sources]
# take effect for the native stack's foundational libs (see the [dev] note).
"badauth>=0.1.6",
"asysocks>=0.2.18",
"badldap>=0.7.5,<0.8",
"kerbad>=0.5.9",
"impacket==0.13.1",
"aiosmb>=0.4.9",
"aardwolf>=0.2.13",
"pypykatz>=0.6.10",
"psutil",
"python-docx",
# PDF table extraction for the document credential table-reconstruction layer
# (services/document_table_credentials.py). MIT-licensed; deliberately NOT
# pymupdf/fitz, which is AGPL and license-incompatible with our commercial
# source-available license. openpyxl (XLSX) and python-docx (DOCX) cover the
# other two formats and are already present.
"pdfplumber>=0.11,<0.12",
"playwright==1.62.0",
"jinja2>=3.0",
"graphviz>=0.20",
"python-magic>=0.4.27,<0.5; platform_system == 'Linux'",
"markitdown>=0.1.5,<0.2",
"dnspython>=2.7.0,<3.0",
# `pydantic-ai-slim` (not full `pydantic-ai`, which drags xai-sdk and pins
# `packaging<26` — incompatible with packaging>=26 needed elsewhere). Only
# the three provider extras the code can actually reach are installed: the
# `AIProvider` enum (services/llm/config.py) routes to openai:/anthropic:/
# google-gla: model strings (OLLAMA + OPENAI_COMPATIBLE also go via openai);
# the *_CLI providers are external subprocesses, not pydantic-ai extras. The
# other provider SDKs (bedrock/vertexai/huggingface/cohere/groq/mistral/…)
# are unreachable and were dropped to shrink the image. Add an extra here if
# a new AIProvider that needs it is introduced.
"pydantic-ai-slim[anthropic,google,openai]>=0.8.1",
"netifaces",
"scapy>=2.5.0,<3.0",
"prompt_toolkit",
"questionary",
"pypsrp[kerberos]==0.9.1",
"pydantic-settings>=2.4.0",
"selenium>=4.28.0,<5.0",
"textual>=0.80.0",
"redis>=5.0.0,<8.2.0",
"winacl==0.1.9",
# Offline VM disk-image credential extraction (vm_artifact_service): dissect
# reads VMware/Hyper-V disk-image containers + NTFS in pure Python (userspace,
# no root/mount/subprocess) to pull ntds.dit + registry hives out of a guest.
"dissect.target>=3.20,<4.0",
# Offline VM MEMORY-image credential extraction (vm_artifact_service): Volatility 3
# carves raw guest RAM (.vmem/.vmrs) for SAM/LSA/cached creds (the HTB-Checkpoint
# root step). pycryptodome is REQUIRED or vol3's credential plugins don't register.
"volatility3>=2.5.0",
"pycryptodome>=3.20",
]
[project.urls]
homepage = "https://adscanpro.com"
documentation = "https://adscanpro.com/docs"
repository = "https://github.com/ADscanPro/adscan"
issues = "https://github.com/ADscanPro/adscan/issues"
changelog = "https://github.com/ADscanPro/adscan/releases"
[project.scripts]
adscan = "adscan_launcher.cli:main"
[tool.uv.sources]
# Vendored skelsec native AD stack — committed under vendor/ as the single
# source of truth for the entire skelsec ecosystem. We pin to the local
# checkout (not PyPI) so the code we read in vendor/<lib>/ is exactly what
# runs in production. The stack is LOCALLY_MAINTAINED (forked); track upstream
# drift read-only via scripts/check_vendor_drift.sh + vendor/UPSTREAM_SHAS.txt.
#
# Why this exists: PyPI releases of these libraries lag the upstream
# repositories by months and ship known protocol bugs (e.g., aiosmb 0.4.14
# on PyPI rejects cross-principal SchRpcRegisterTask with
# rpc_s_access_denied — fixed in main but unreleased). Vendoring eliminates
# the drift, satisfies the CLAUDE.md "Read source before calling" rule, and
# keeps the entire skelsec stack version-coherent.
# editable = true → vendor/ source is the live import; any patch to vendor/<lib>/
# is reflected immediately without `uv sync`. Required for
# LOCALLY_MAINTAINED libs that carry ADscan-specific edits.
# editable = false → wheel snapshot; safe for libs we never patch.
aardwolf = { path = "vendor/aardwolf", editable = true }
aiosmb = { path = "vendor/aiosmb", editable = true }
asysocks = { path = "vendor/asysocks", editable = false }
badauth = { path = "vendor/badauth", editable = true }
badldap = { path = "vendor/badldap", editable = true }
kerbad = { path = "vendor/kerbad", editable = true }
winacl = { path = "vendor/winacl", editable = false }
pypykatz = { path = "vendor/pypykatz", editable = false }
[tool.setuptools.packages.find]
include = ["adscan_core*", "adscan_launcher*"]
[tool.setuptools.package-data]
adscan_launcher = ["assets/**/*.yml", "assets/**/*.yaml"]
adscan_internal = ["pro/reporting/templates/*.html", "pro/reporting/themes/*/theme.css", "services/report_design/_css/*.css", "assets/demo_workspace/*.json", "assets/report_samples/*.pdf", "assets/rules/*.rule"]