linux-security-audit-tool 0.1.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,125 @@
1
+ Metadata-Version: 2.4
2
+ Name: linux-security-audit-tool
3
+ Version: 0.1.0
4
+ Summary: Comprehensive Linux security auditing and hardening tool
5
+ Project-URL: Homepage, https://github.com/daedalus/linux-security-audit-tool
6
+ Project-URL: Repository, https://github.com/daedalus/linux-security-audit-tool
7
+ Project-URL: Issues, https://github.com/daedalus/linux-security-audit-tool/issues
8
+ Author-email: Dario Clavijo <clavijodario@gmail.com>
9
+ License: MIT
10
+ License-File: LICENSE
11
+ Requires-Python: >=3.11
12
+ Requires-Dist: jinja2>=3.0.0
13
+ Requires-Dist: tabulate>=0.9.0
14
+ Provides-Extra: all
15
+ Requires-Dist: click>=8.0; extra == 'all'
16
+ Requires-Dist: hatch; extra == 'all'
17
+ Requires-Dist: hypothesis; extra == 'all'
18
+ Requires-Dist: mypy; extra == 'all'
19
+ Requires-Dist: pytest; extra == 'all'
20
+ Requires-Dist: pytest-asyncio; extra == 'all'
21
+ Requires-Dist: pytest-cov; extra == 'all'
22
+ Requires-Dist: pytest-mock; extra == 'all'
23
+ Requires-Dist: rich>=13.0; extra == 'all'
24
+ Requires-Dist: ruff; extra == 'all'
25
+ Provides-Extra: cli
26
+ Requires-Dist: click>=8.0; extra == 'cli'
27
+ Requires-Dist: rich>=13.0; extra == 'cli'
28
+ Provides-Extra: dev
29
+ Requires-Dist: hatch; extra == 'dev'
30
+ Requires-Dist: mypy; extra == 'dev'
31
+ Requires-Dist: ruff; extra == 'dev'
32
+ Provides-Extra: lint
33
+ Requires-Dist: mypy; extra == 'lint'
34
+ Requires-Dist: ruff; extra == 'lint'
35
+ Provides-Extra: test
36
+ Requires-Dist: hypothesis; extra == 'test'
37
+ Requires-Dist: pytest; extra == 'test'
38
+ Requires-Dist: pytest-asyncio; extra == 'test'
39
+ Requires-Dist: pytest-cov; extra == 'test'
40
+ Requires-Dist: pytest-mock; extra == 'test'
41
+ Description-Content-Type: text/markdown
42
+
43
+ # Linux Security Audit Tool
44
+
45
+ A comprehensive CLI tool for auditing Linux system security posture.
46
+
47
+ [![PyPI](https://img.shields.io/pypi/v/linux-security-audit-tool.svg)](https://pypi.org/project/linux-security-audit-tool/)
48
+ [![Python](https://img.shields.io/pypi/pyversions/linux-security-audit-tool.svg)](https://pypi.org/project/linux-security-audit-tool/)
49
+ [![Ruff](https://img.shields.io/endpoint?url=https://raw.githubusercontent.com/astral-sh/ruff/main/assets/badge/v2.json)](https://github.com/astral-sh/ruff)
50
+
51
+ ## Install
52
+
53
+ ```bash
54
+ pip install linux-security-audit-tool
55
+ ```
56
+
57
+ ## Usage
58
+
59
+ ```bash
60
+ security-audit --help
61
+ security-audit audit
62
+ security-audit audit -p 0 -1 # Run specific phases
63
+ security-audit audit -o report.md # Save markdown report
64
+ security-audit audit --quiet # Summary only
65
+ ```
66
+
67
+ ## CLI
68
+
69
+ ```bash
70
+ security-audit [OPTIONS] COMMAND [ARGS]...
71
+
72
+ Options:
73
+ --version Show the version and exit.
74
+ --help Show this message and exit.
75
+
76
+ Commands:
77
+ audit Run a full security audit.
78
+ version Show version information.
79
+ ```
80
+
81
+ ## Development
82
+
83
+ ```bash
84
+ git clone https://github.com/daedalus/linux-security-audit-tool.git
85
+ cd linux-security-audit-tool
86
+ pip install -e ".[test]"
87
+
88
+ # run tests
89
+ pytest
90
+
91
+ # format
92
+ ruff format src/ tests/
93
+
94
+ # lint
95
+ ruff check src/ tests/
96
+
97
+ # type check
98
+ mypy src/
99
+ ```
100
+
101
+ ## API
102
+
103
+ ```python
104
+ from security_audit import gather_context, run_identity_checks, calculate_security_score
105
+ from security_audit.core import Finding, Severity
106
+
107
+ # Run a full audit
108
+ context = gather_context()
109
+ findings = run_identity_checks()
110
+ score = calculate_security_score(findings)
111
+ ```
112
+
113
+ ## Audit Phases
114
+
115
+ The tool performs security checks across 9 phases:
116
+
117
+ - **Phase 0**: Context Gathering (hostname, OS, kernel)
118
+ - **Phase 1**: Identity & Access Control (users, sudo, SSH)
119
+ - **Phase 2**: Network Exposure (listening services, firewall)
120
+ - **Phase 3**: File System & Permissions (SUID, world-writable)
121
+ - **Phase 4**: Process & Service Posture (running services)
122
+ - **Phase 5**: Kernel & OS Hardening (sysctl, ASLR)
123
+ - **Phase 6**: Logging & Monitoring (auditd, logs)
124
+ - **Phase 7**: Package & Update Hygiene (updates, repos)
125
+ - **Phase 8**: Cryptographic Posture (SSH keys, TLS)
@@ -0,0 +1,21 @@
1
+ security_audit/__init__.py,sha256=_maE3U_JAAByrzXf8MxLJ0V9pH_1m8mfQAwsXE0NM_g,1112
2
+ security_audit/__main__.py,sha256=9DionsgeprlP9eLdwbEkFW_PZFQEKSQRa--EZbpfoNU,145
3
+ security_audit/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
4
+ security_audit/cli/__init__.py,sha256=60dLiSwrobV5BOv6MDu17QJ5vSvf4-ArDn3UgRaSf94,7263
5
+ security_audit/core/__init__.py,sha256=DB5FOJ5dicLnt1QhpjPh29kBe4eu044LrSLT7rtHTzg,2742
6
+ security_audit/phases/__init__.py,sha256=tXhP7AFle7Tp9XaiugI85GHl4iST6S47QpHc6K7b9sE,1083
7
+ security_audit/phases/context.py,sha256=G5GvyiXSRNz2_FaLFMtQfX6rSpcSfEibxuklHlcmuLk,1586
8
+ security_audit/phases/crypto.py,sha256=78vpEHxBw9gUhMbXCHInXoVELanbf9CwElhz9vqUxyg,6435
9
+ security_audit/phases/filesystem.py,sha256=EXCt9R_FcUPtmSBkPIVMBcS0IFdifHuBxhtq5Inf6mQ,8018
10
+ security_audit/phases/identity.py,sha256=Zc2ylcVb4qnHJs_KHt_DFGwmN3OT-_iZo7Lh3yKU5KU,9313
11
+ security_audit/phases/kernel.py,sha256=GPAWPaCbkCFGS_Fl0wD-axfcnYhBPlrjSGdsq4NTQ50,7804
12
+ security_audit/phases/logging.py,sha256=Rdf8Kzif-Gbl6Gu8SBKKWB1TGXM6wBGfthxL5Qo-jaU,6463
13
+ security_audit/phases/network.py,sha256=ZaetoYOUEcFetCoOp_Lw2HWpVbLjGAtn3f4O72u_ROI,5146
14
+ security_audit/phases/packages.py,sha256=jvb9hksu0R1HDuaSWh6SbDdAgFYwcCL_-VQtTxh3HaE,5141
15
+ security_audit/phases/process.py,sha256=6INIP5LtM9uk1omj-ltqsbeWMewzOPT3q_BbRzI2FNM,6481
16
+ security_audit/phases/reporting.py,sha256=qZpbI0gmlktzfaLRUpLz57DU1UrHAVbBjV7qWv9W62k,4710
17
+ linux_security_audit_tool-0.1.0.dist-info/METADATA,sha256=xplomD4mn2FTj9lGMjyDWmQ6EDLpyzUzk9DLoQBuZ14,3763
18
+ linux_security_audit_tool-0.1.0.dist-info/WHEEL,sha256=QccIxa26bgl1E6uMy58deGWi-0aeIkkangHcxk2kWfw,87
19
+ linux_security_audit_tool-0.1.0.dist-info/entry_points.txt,sha256=BbrtNuPOwSVGye_e_CEA3Ehh2uZiwj6vZq752-_IvQ8,59
20
+ linux_security_audit_tool-0.1.0.dist-info/licenses/LICENSE,sha256=C2rA6vc6sz_Yf8oDFseNTefVHM0AL4_Wq4MTgElzy0U,1069
21
+ linux_security_audit_tool-0.1.0.dist-info/RECORD,,
@@ -0,0 +1,4 @@
1
+ Wheel-Version: 1.0
2
+ Generator: hatchling 1.29.0
3
+ Root-Is-Purelib: true
4
+ Tag: py3-none-any
@@ -0,0 +1,2 @@
1
+ [console_scripts]
2
+ security-audit = security_audit.cli:main
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Dario Clavijo
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,49 @@
1
+ """Linux Security Audit Tool - Comprehensive security auditing and hardening."""
2
+
3
+ __version__ = "0.1.0"
4
+
5
+ from typing import TYPE_CHECKING
6
+
7
+ from .core import AuditContext, Finding, Severity
8
+ from .phases import (
9
+ calculate_security_score,
10
+ classify_severity,
11
+ gather_context,
12
+ generate_markdown_report,
13
+ generate_remediation_script,
14
+ get_system_info,
15
+ run_crypto_checks,
16
+ run_filesystem_checks,
17
+ run_identity_checks,
18
+ run_kernel_checks,
19
+ run_logging_checks,
20
+ run_network_checks,
21
+ run_package_checks,
22
+ run_process_checks,
23
+ run_reporting,
24
+ )
25
+
26
+ if TYPE_CHECKING:
27
+ from .cli import cli
28
+
29
+ __all__ = [
30
+ "__version__",
31
+ "AuditContext",
32
+ "Finding",
33
+ "Severity",
34
+ "calculate_security_score",
35
+ "classify_severity",
36
+ "gather_context",
37
+ "generate_markdown_report",
38
+ "generate_remediation_script",
39
+ "get_system_info",
40
+ "run_crypto_checks",
41
+ "run_filesystem_checks",
42
+ "run_identity_checks",
43
+ "run_kernel_checks",
44
+ "run_logging_checks",
45
+ "run_network_checks",
46
+ "run_package_checks",
47
+ "run_process_checks",
48
+ "run_reporting",
49
+ ]
@@ -0,0 +1,6 @@
1
+ """CLI entry point for the security audit tool."""
2
+
3
+ from security_audit.cli import main
4
+
5
+ if __name__ == "__main__":
6
+ raise SystemExit(main())
@@ -0,0 +1,241 @@
1
+ """Command-line interface for the Linux Security Audit Tool."""
2
+
3
+ import sys
4
+ from typing import Optional
5
+
6
+ import click
7
+ from rich import print as rprint
8
+ from rich.console import Console
9
+ from rich.progress import Progress, SpinnerColumn, TextColumn
10
+
11
+ from security_audit.core import Finding, Severity
12
+ from security_audit.phases import (
13
+ calculate_security_score,
14
+ gather_context,
15
+ generate_markdown_report,
16
+ run_crypto_checks,
17
+ run_filesystem_checks,
18
+ run_identity_checks,
19
+ run_kernel_checks,
20
+ run_logging_checks,
21
+ run_network_checks,
22
+ run_package_checks,
23
+ run_process_checks,
24
+ )
25
+
26
+ console = Console()
27
+
28
+
29
+ def print_finding(finding: Finding) -> None:
30
+ """Print a single finding with severity color.
31
+
32
+ Args:
33
+ finding: The Finding object to print.
34
+ """
35
+ colors = {
36
+ Severity.CRITICAL: "red bold",
37
+ Severity.HIGH: "red",
38
+ Severity.MEDIUM: "yellow",
39
+ Severity.LOW: "cyan",
40
+ Severity.INFO: "blue",
41
+ }
42
+ color = colors.get(finding.severity, "white")
43
+ rprint(
44
+ f"[{color}]{finding.severity.value}[/{color}] [{color}]{finding.check_id}[/{color}]: {finding.title}"
45
+ )
46
+
47
+
48
+ def print_summary(findings: list[Finding]) -> None:
49
+ """Print a summary table of findings.
50
+
51
+ Args:
52
+ findings: List of Finding objects.
53
+ """
54
+ from rich.table import Table
55
+
56
+ counts = {
57
+ Severity.CRITICAL: 0,
58
+ Severity.HIGH: 0,
59
+ Severity.MEDIUM: 0,
60
+ Severity.LOW: 0,
61
+ Severity.INFO: 0,
62
+ }
63
+ for f in findings:
64
+ counts[f.severity] += 1
65
+
66
+ table = Table(title="Audit Summary")
67
+ table.add_column("Severity", style="bold")
68
+ table.add_column("Count", justify="right")
69
+
70
+ table.add_row("[red bold]CRITICAL[/red bold]", str(counts[Severity.CRITICAL]))
71
+ table.add_row("[red]HIGH[/red]", str(counts[Severity.HIGH]))
72
+ table.add_row("[yellow]MEDIUM[/yellow]", str(counts[Severity.MEDIUM]))
73
+ table.add_row("[cyan]LOW[/cyan]", str(counts[Severity.LOW]))
74
+ table.add_row("[blue]INFO[/blue]", str(counts[Severity.INFO]))
75
+
76
+ console.print(table)
77
+
78
+
79
+ @click.group()
80
+ @click.version_option(version="0.1.0")
81
+ def cli() -> None:
82
+ """Linux Security Audit Tool - Comprehensive security auditing and hardening."""
83
+ pass
84
+
85
+
86
+ @cli.command()
87
+ @click.option(
88
+ "--output",
89
+ "-o",
90
+ type=click.Path(),
91
+ default=None,
92
+ help="Output file for report",
93
+ )
94
+ @click.option(
95
+ "--phases",
96
+ "-p",
97
+ multiple=True,
98
+ help="Specific phases to run (0-9)",
99
+ )
100
+ @click.option(
101
+ "--quiet",
102
+ "-q",
103
+ is_flag=True,
104
+ help="Suppress detailed output",
105
+ )
106
+ def audit(
107
+ output: str | None,
108
+ phases: tuple,
109
+ quiet: bool,
110
+ ) -> None:
111
+ """Run a full security audit."""
112
+ console.print("[bold blue]Linux Security Audit Tool v0.1.0[/bold blue]")
113
+ console.print()
114
+
115
+ all_findings = []
116
+ context = None
117
+
118
+ selected_phases = list(range(10)) if not phases else [int(p) for p in phases]
119
+
120
+ with Progress(
121
+ SpinnerColumn(),
122
+ TextColumn("[progress.description]{task.description}"),
123
+ console=console,
124
+ ) as progress:
125
+ if 0 in selected_phases:
126
+ task = progress.add_task("Gathering context...", total=None)
127
+ context = gather_context()
128
+ if not quiet:
129
+ console.print(f" Hostname: {context.hostname}")
130
+ console.print(f" Kernel: {context.kernel}")
131
+ progress.update(task, completed=True)
132
+
133
+ if 1 in selected_phases:
134
+ task = progress.add_task(
135
+ "Checking identity & access control...", total=None
136
+ )
137
+ findings = run_identity_checks()
138
+ all_findings.extend(findings)
139
+ if not quiet:
140
+ for f in findings:
141
+ print_finding(f)
142
+ progress.update(task, completed=True)
143
+
144
+ if 2 in selected_phases:
145
+ task = progress.add_task("Checking network exposure...", total=None)
146
+ findings = run_network_checks()
147
+ all_findings.extend(findings)
148
+ if not quiet:
149
+ for f in findings:
150
+ print_finding(f)
151
+ progress.update(task, completed=True)
152
+
153
+ if 3 in selected_phases:
154
+ task = progress.add_task(
155
+ "Checking file system & permissions...", total=None
156
+ )
157
+ findings = run_filesystem_checks()
158
+ all_findings.extend(findings)
159
+ if not quiet:
160
+ for f in findings:
161
+ print_finding(f)
162
+ progress.update(task, completed=True)
163
+
164
+ if 4 in selected_phases:
165
+ task = progress.add_task(
166
+ "Checking process & service posture...", total=None
167
+ )
168
+ findings = run_process_checks()
169
+ all_findings.extend(findings)
170
+ if not quiet:
171
+ for f in findings:
172
+ print_finding(f)
173
+ progress.update(task, completed=True)
174
+
175
+ if 5 in selected_phases:
176
+ task = progress.add_task("Checking kernel & OS hardening...", total=None)
177
+ findings = run_kernel_checks()
178
+ all_findings.extend(findings)
179
+ if not quiet:
180
+ for f in findings:
181
+ print_finding(f)
182
+ progress.update(task, completed=True)
183
+
184
+ if 6 in selected_phases:
185
+ task = progress.add_task("Checking logging & monitoring...", total=None)
186
+ findings = run_logging_checks()
187
+ all_findings.extend(findings)
188
+ if not quiet:
189
+ for f in findings:
190
+ print_finding(f)
191
+ progress.update(task, completed=True)
192
+
193
+ if 7 in selected_phases:
194
+ task = progress.add_task("Checking package hygiene...", total=None)
195
+ findings = run_package_checks()
196
+ all_findings.extend(findings)
197
+ if not quiet:
198
+ for f in findings:
199
+ print_finding(f)
200
+ progress.update(task, completed=True)
201
+
202
+ if 8 in selected_phases:
203
+ task = progress.add_task("Checking cryptographic posture...", total=None)
204
+ findings = run_crypto_checks()
205
+ all_findings.extend(findings)
206
+ if not quiet:
207
+ for f in findings:
208
+ print_finding(f)
209
+ progress.update(task, completed=True)
210
+
211
+ if 9 in selected_phases:
212
+ task = progress.add_task("Generating report...", total=None)
213
+ if context is None:
214
+ context = gather_context()
215
+ score = calculate_security_score(all_findings)
216
+ console.print(f"\n[bold]Security Score: {score}/100[/bold]")
217
+ progress.update(task, completed=True)
218
+
219
+ console.print()
220
+ print_summary(all_findings)
221
+
222
+ if output:
223
+ report = generate_markdown_report(context, all_findings)
224
+ with open(output, "w", encoding="utf-8") as f:
225
+ f.write(report)
226
+ console.print(f"\n[green]Report saved to {output}[/green]")
227
+
228
+
229
+ @cli.command()
230
+ def version() -> None:
231
+ """Show version information."""
232
+ console.print("Linux Security Audit Tool v0.1.0")
233
+
234
+
235
+ def main() -> int:
236
+ """Main entry point for the CLI."""
237
+ return cli()
238
+
239
+
240
+ if __name__ == "__main__":
241
+ raise SystemExit(main())
@@ -0,0 +1,106 @@
1
+ """Security audit core models and utilities."""
2
+
3
+ from dataclasses import dataclass, field
4
+ from enum import Enum
5
+ from typing import Optional
6
+
7
+
8
+ class Severity(Enum):
9
+ """Security finding severity levels."""
10
+
11
+ CRITICAL = "CRITICAL"
12
+ HIGH = "HIGH"
13
+ MEDIUM = "MEDIUM"
14
+ LOW = "LOW"
15
+ INFO = "INFO"
16
+
17
+
18
+ @dataclass
19
+ class Finding:
20
+ """Represents a security finding from an audit check.
21
+
22
+ Attributes:
23
+ severity: The severity level of the finding.
24
+ check_id: Unique identifier for the check (e.g., "IDENT-001").
25
+ title: Short descriptive title of the finding.
26
+ description: Detailed description of what was found.
27
+ evidence: Command output or evidence supporting the finding.
28
+ impact: Description of the security impact.
29
+ remediation: Recommended remediation steps.
30
+ phase: The audit phase where this finding was generated.
31
+ """
32
+
33
+ severity: Severity
34
+ check_id: str
35
+ title: str
36
+ description: str
37
+ evidence: str
38
+ impact: str
39
+ remediation: str
40
+ phase: str
41
+
42
+
43
+ @dataclass
44
+ class AuditContext:
45
+ """Context gathered during the audit.
46
+
47
+ Attributes:
48
+ hostname: System hostname.
49
+ os_release: OS release information.
50
+ kernel: Kernel version.
51
+ uptime: System uptime.
52
+ virtualization: Virtualization technology detected.
53
+ is_container: Whether running in a container.
54
+ is_server: Whether system is a server (vs workstation).
55
+ findings: List of findings collected during audit.
56
+ """
57
+
58
+ hostname: str = ""
59
+ os_release: str = ""
60
+ kernel: str = ""
61
+ uptime: str = ""
62
+ virtualization: str = ""
63
+ is_container: bool = False
64
+ is_server: bool = True
65
+ findings: list = field(default_factory=list)
66
+
67
+
68
+ def run_command(
69
+ cmd: str,
70
+ timeout: int = 30,
71
+ ) -> tuple[str, str, int]:
72
+ """Run a shell command and return stdout, stderr, and return code.
73
+
74
+ Args:
75
+ cmd: The command to execute.
76
+ timeout: Maximum time to wait for command completion in seconds.
77
+
78
+ Returns:
79
+ A tuple of (stdout, stderr, returncode).
80
+ """
81
+ import subprocess
82
+
83
+ try:
84
+ result = subprocess.run(
85
+ cmd,
86
+ shell=True,
87
+ capture_output=True,
88
+ text=True,
89
+ timeout=timeout,
90
+ )
91
+ return result.stdout.strip(), result.stderr.strip(), result.returncode
92
+ except subprocess.TimeoutExpired:
93
+ return "", f"Command timed out after {timeout}s", -1
94
+ except Exception as e:
95
+ return "", str(e), -1
96
+
97
+
98
+ def check_root() -> bool:
99
+ """Check if the current process is running as root.
100
+
101
+ Returns:
102
+ True if running as root (UID 0), False otherwise.
103
+ """
104
+ import os
105
+
106
+ return os.geteuid() == 0
@@ -0,0 +1,41 @@
1
+ """Security audit phases."""
2
+
3
+ from typing import TYPE_CHECKING
4
+
5
+ from .context import gather_context, get_system_info
6
+ from .crypto import run_crypto_checks
7
+ from .filesystem import run_filesystem_checks
8
+ from .identity import run_identity_checks
9
+ from .kernel import run_kernel_checks
10
+ from .logging import run_logging_checks
11
+ from .network import run_network_checks
12
+ from .packages import run_package_checks
13
+ from .process import run_process_checks
14
+ from .reporting import (
15
+ calculate_security_score,
16
+ classify_severity,
17
+ generate_markdown_report,
18
+ generate_remediation_script,
19
+ run_reporting,
20
+ )
21
+
22
+ if TYPE_CHECKING:
23
+ from ..core import AuditContext, Finding
24
+
25
+ __all__ = [
26
+ "gather_context",
27
+ "get_system_info",
28
+ "run_identity_checks",
29
+ "run_network_checks",
30
+ "run_filesystem_checks",
31
+ "run_process_checks",
32
+ "run_kernel_checks",
33
+ "run_logging_checks",
34
+ "run_package_checks",
35
+ "run_crypto_checks",
36
+ "run_reporting",
37
+ "generate_markdown_report",
38
+ "generate_remediation_script",
39
+ "calculate_security_score",
40
+ "classify_severity",
41
+ ]
@@ -0,0 +1,60 @@
1
+ """Phase 0 - Context Gathering module."""
2
+
3
+ from ..core import AuditContext, run_command
4
+
5
+
6
+ def gather_context() -> AuditContext:
7
+ """Gather basic system context for the audit."""
8
+ context = AuditContext()
9
+
10
+ stdout, _, rc = run_command("hostname")
11
+ if rc == 0:
12
+ context.hostname = stdout
13
+
14
+ stdout, _, rc = run_command("uname -r")
15
+ if rc == 0:
16
+ context.kernel = stdout
17
+
18
+ stdout, _, rc = run_command("cat /etc/os-release")
19
+ if rc == 0:
20
+ context.os_release = stdout
21
+
22
+ stdout, _, rc = run_command("uptime")
23
+ if rc == 0:
24
+ context.uptime = stdout
25
+
26
+ stdout, _, rc = run_command(
27
+ "systemd-detect-virt 2>/dev/null || virt-what 2>/dev/null || echo 'none'"
28
+ )
29
+ if rc == 0 and stdout:
30
+ context.virtualization = stdout
31
+ context.is_container = stdout.strip() in ["docker", "lxc", "podman"]
32
+
33
+ stdout, _, rc = run_command("systemd-detect-virt -c 2>/dev/null")
34
+ context.is_container = rc == 0
35
+
36
+ return context
37
+
38
+
39
+ def get_system_info() -> dict:
40
+ """Get detailed system information."""
41
+ info = {}
42
+
43
+ cmds = {
44
+ "hostname": "hostname",
45
+ "os_release": "cat /etc/os-release",
46
+ "kernel": "uname -r",
47
+ "architecture": "uname -m",
48
+ "uptime": "uptime",
49
+ "last_boot": "who -b",
50
+ }
51
+
52
+ for key, cmd in cmds.items():
53
+ stdout, _, rc = run_command(cmd)
54
+ if rc == 0:
55
+ info[key] = stdout
56
+
57
+ virt, _, rc = run_command("systemd-detect-virt 2>/dev/null || echo 'none'")
58
+ info["virtualization"] = virt if rc == 0 else "unknown"
59
+
60
+ return info