akii 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.
akii/__init__.py ADDED
@@ -0,0 +1 @@
1
+ __version__ = "0.1.0"
@@ -0,0 +1,7 @@
1
+ from .cors import cors_runner
2
+ from .csp import csp_runner
3
+
4
+ CHECKERS = [
5
+ cors_runner,
6
+ csp_runner,
7
+ ]
akii/checks/cache.py ADDED
File without changes
akii/checks/cookie.py ADDED
File without changes
akii/checks/cors.py ADDED
@@ -0,0 +1,43 @@
1
+ from akii.core.template_loader import load_template
2
+
3
+ RULE = load_template("cors")
4
+
5
+
6
+ def cors_detect(config, response):
7
+ findings = {}
8
+
9
+ for check in RULE["checks"]:
10
+ header = check["header"]
11
+
12
+ if header in response.headers:
13
+ findings[header] = response.headers[header]
14
+
15
+ return findings
16
+
17
+
18
+ def cors_analyze(findings):
19
+ results = []
20
+
21
+ for check in RULE["checks"]:
22
+ header = check["header"]
23
+
24
+ if header not in findings:
25
+ continue
26
+
27
+ value = findings[header]
28
+
29
+ for rule in check.get("rules", []):
30
+ if value == rule["value"]:
31
+ results.append({
32
+ "header": header,
33
+ "value": value,
34
+ "severity": rule["severity"],
35
+ "message": rule["message"],
36
+ })
37
+
38
+ return results
39
+
40
+
41
+ def cors_runner(config, response):
42
+ findings = cors_detect(config, response)
43
+ return cors_analyze(findings)
akii/checks/csp.py ADDED
@@ -0,0 +1,49 @@
1
+ from akii.core.template_loader import load_template
2
+
3
+ RULE = load_template("csp")
4
+
5
+
6
+ def csp_detect(config, response):
7
+ findings = {}
8
+
9
+ for check in RULE["checks"]:
10
+ header = check["header"]
11
+
12
+ if header in response.headers:
13
+ findings[header] = response.headers[header]
14
+
15
+ return findings
16
+
17
+
18
+ def csp_analyze(findings):
19
+ results = []
20
+
21
+ for check in RULE["checks"]:
22
+ header = check["header"]
23
+
24
+ if header not in findings:
25
+ if check.get("required", False):
26
+ results.append({
27
+ "header": header,
28
+ "severity": "info",
29
+ "message": f"Missing required header: {header}",
30
+ })
31
+ continue
32
+
33
+ value = findings[header]
34
+
35
+ for rule in check.get("rules", []):
36
+ if rule["value"] in value:
37
+ results.append({
38
+ "header": header,
39
+ "value": rule["value"],
40
+ "severity": rule["severity"],
41
+ "message": rule["message"],
42
+ })
43
+
44
+ return results
45
+
46
+
47
+ def csp_runner(config, response):
48
+ findings = csp_detect(config, response)
49
+ return csp_analyze(findings)
akii/checks/hsts.py ADDED
File without changes
akii/core/__init__.py ADDED
File without changes
File without changes
akii/core/cli/main.py ADDED
@@ -0,0 +1,13 @@
1
+ from akii.core.cli.parser import build_parser
2
+ from akii.core.controller import run
3
+ from akii.ui.output import banner
4
+
5
+ def main():
6
+ banner()
7
+ parser = build_parser()
8
+ args = parser.parse_args()
9
+ config = vars(args)
10
+ run(config)
11
+
12
+ if __name__ == "__main__":
13
+ main()
@@ -0,0 +1,66 @@
1
+ import argparse
2
+
3
+ from akii.core.flags.general import (
4
+ INPUT_FLAGS,
5
+ REQUEST_FLAGS,
6
+ PERFORMANCE_FLAGS,
7
+ OUTPUT_FLAGS,
8
+ MISCELLANEOUS_FLAGS,
9
+ )
10
+
11
+
12
+ FLAG_GROUPS = (
13
+ ("Input", INPUT_FLAGS),
14
+ ("Request", REQUEST_FLAGS),
15
+ ("Performance", PERFORMANCE_FLAGS),
16
+ ("Output", OUTPUT_FLAGS),
17
+ ("Miscellaneous", MISCELLANEOUS_FLAGS),
18
+ )
19
+
20
+
21
+ def build_parser():
22
+ """Create and configure the CLI argument parser."""
23
+
24
+ parser = argparse.ArgumentParser(
25
+ prog="akii",
26
+ description="HTTP header analyzer",
27
+ formatter_class=lambda prog: argparse.HelpFormatter(
28
+ prog,
29
+ max_help_position=50,
30
+ width=130,
31
+ ),
32
+ )
33
+
34
+ # Create and register all argument groups.
35
+ for title, flags in FLAG_GROUPS:
36
+ group = parser.add_argument_group(title)
37
+ register_flags(group, flags)
38
+
39
+ return parser
40
+
41
+
42
+ def register_flags(group, flags):
43
+ """Register a collection of CLI flags to an argument group."""
44
+
45
+ for value in flags.values():
46
+ kwargs = {
47
+ "help": value["help"],
48
+ }
49
+
50
+ # Copy optional keyword arguments if present.
51
+ for key in (
52
+ "action",
53
+ "type",
54
+ "default",
55
+ "choices",
56
+ "nargs",
57
+ "metavar",
58
+ "required",
59
+ ):
60
+ if key in value:
61
+ kwargs[key] = value[key]
62
+
63
+ group.add_argument(
64
+ *value["flags"],
65
+ **kwargs,
66
+ )
@@ -0,0 +1,70 @@
1
+ import re
2
+
3
+ from akii.http.client import request
4
+ from akii.ui.output import display_http, csp_result, cors_result, display_target
5
+ from akii.checks.csp import csp_runner
6
+ from akii.checks.cors import cors_runner
7
+ from akii.core.reporter import txt_output, json_output
8
+
9
+
10
+ URL_RE = re.compile(r"https?://[^\s]+")
11
+
12
+
13
+ def extract_url(line):
14
+ match = URL_RE.search(line)
15
+ return match.group(0) if match else None
16
+
17
+
18
+ def load_input(config):
19
+ if not config.get("wordlist"):
20
+ return [config]
21
+
22
+ configs = []
23
+
24
+ with open(config["wordlist"], encoding="utf-8") as f:
25
+ for line in f:
26
+ url = extract_url(line)
27
+
28
+ if not url:
29
+ continue
30
+
31
+ target_config = config.copy()
32
+ target_config["target"] = url
33
+ configs.append(target_config)
34
+
35
+ return configs
36
+
37
+
38
+ def process_target(config):
39
+ display_target(config)
40
+
41
+ response = request(config)
42
+
43
+ display_http(config, response)
44
+
45
+ cors_results = cors_runner(config, response)
46
+ cors_result(cors_results)
47
+
48
+ csp_results = csp_runner(config, response)
49
+ csp_result(csp_results)
50
+
51
+ return {
52
+ "target": config["target"],
53
+ "cors": cors_results,
54
+ "csp": csp_results,
55
+ }
56
+
57
+
58
+ def run(config):
59
+ inputs = load_input(config)
60
+
61
+ all_results = []
62
+
63
+ for target_config in inputs:
64
+ all_results.append(process_target(target_config))
65
+
66
+ if config.get("output"):
67
+ if config.get("json"):
68
+ json_output(all_results, config["output"])
69
+ else:
70
+ txt_output(all_results, config["output"])
@@ -0,0 +1,109 @@
1
+ INPUT_FLAGS = {
2
+ "Target": {
3
+ "flags": ["-T", "--target"],
4
+ "type": str,
5
+ "default": None,
6
+ "help": "Target URL or host to analyze.",
7
+ "metavar": "",
8
+ },
9
+
10
+ "Wordlist": {
11
+ "flags": ["-w", "--wordlist"],
12
+ "type": str,
13
+ "default": None,
14
+ "help": "Read targets from a wordlist file.",
15
+ "metavar": "",
16
+ }
17
+ }
18
+
19
+ REQUEST_FLAGS = {
20
+ "Method": {
21
+ "flags": ["-X", "--method"],
22
+ "type": str,
23
+ "default": "GET",
24
+ "help": "HTTP request method (default: GET).",
25
+ "metavar": "",
26
+ },
27
+
28
+ "Header": {
29
+ "flags": ["-H", "--header"],
30
+ "type": str,
31
+ "default": None,
32
+ "help": "Add a custom HTTP header (e.g. 'Authorization: Bearer <token>').",
33
+ "metavar": "",
34
+ },
35
+
36
+ "Cookie": {
37
+ "flags": ["-C", "--cookie"],
38
+ "type": str,
39
+ "default": None,
40
+ "help": "Send cookies with the request (e.g. 'session=abc123').",
41
+ "metavar": "",
42
+ },
43
+
44
+ "Data": {
45
+ "flags": ["-D", "--data"],
46
+ "type": str,
47
+ "default": None,
48
+ "help": "Send data in the request body.",
49
+ "metavar": "",
50
+ },
51
+ }
52
+
53
+ PERFORMANCE_FLAGS = {
54
+ "Concurrency": {
55
+ "flags": ["-c", "--concurrency"],
56
+ "type": int,
57
+ "default": 1,
58
+ "help": "Number of concurrent requests.",
59
+ "metavar": "",
60
+ },
61
+ }
62
+
63
+ OUTPUT_FLAGS = {
64
+ "Output": {
65
+ "flags": ["-o", "--output"],
66
+ "type": str,
67
+ "default": None,
68
+ "help": "Write results to the specified file.",
69
+ "metavar": "",
70
+ },
71
+
72
+ "JSON": {
73
+ "flags": ["-j", "--json"],
74
+ "action": "store_true",
75
+ "help": "Output results in JSON format.",
76
+ },
77
+
78
+ "Request_Header": {
79
+ "flags": ["--request"],
80
+ "action": "store_true",
81
+ "help": "Display the HTTP request headers.",
82
+ },
83
+
84
+ "Response_Header": {
85
+ "flags": ["--response"],
86
+ "action": "store_true",
87
+ "help": "Display the HTTP response headers.",
88
+ },
89
+
90
+ "Verbose": {
91
+ "flags": ["--verbose"],
92
+ "action": "store_true",
93
+ "help": "Display both the HTTP request and response.",
94
+ },
95
+ }
96
+
97
+ MISCELLANEOUS_FLAGS = {
98
+ "Version": {
99
+ "flags": ["-v", "--version"],
100
+ "action": "store_true",
101
+ "help": "Show version information.",
102
+ },
103
+
104
+ "Update": {
105
+ "flags": ["--update"],
106
+ "action": "store_true",
107
+ "help": "Update Akii to the latest version.",
108
+ },
109
+ }
akii/core/reporter.py ADDED
@@ -0,0 +1,48 @@
1
+ from pathlib import Path
2
+ import json
3
+
4
+ def txt_output(results, output):
5
+ output_path = Path(output).resolve(strict=False)
6
+
7
+ with output_path.open("w", encoding="utf-8") as f:
8
+ for target in results:
9
+ f.write("=" * 60)
10
+ f.write(f"\nTarget: {target['target']}\n\n")
11
+
12
+ # CORS
13
+ f.write("=== CORS Analysis ===\n")
14
+
15
+ if not target["cors"]:
16
+ f.write("No CORS issues found.\n\n")
17
+ else:
18
+ for count, result in enumerate(target["cors"], start=1):
19
+ f.write(f"({count}> [{result['severity'].upper()}] {result['header']}\n")
20
+
21
+ if "value" in result:
22
+ f.write(f" Value : {result['value']}\n")
23
+
24
+ f.write(f" Message : {result['message']}\n")
25
+
26
+ f.write("\n")
27
+
28
+ # CSP
29
+ f.write("=== CSP Analysis ===\n")
30
+
31
+ if not target["csp"]:
32
+ f.write("No CSP issues found.\n\n")
33
+ else:
34
+ for count, result in enumerate(target["csp"], start=1):
35
+ f.write(f"({count}> [{result['severity'].upper()}] {result['header']}\n")
36
+
37
+ if "value" in result:
38
+ f.write(f" Value : {result['value']}\n")
39
+
40
+ f.write(f" Message : {result['message']}\n")
41
+
42
+ f.write("\n")
43
+
44
+ def json_output(results, output):
45
+ output_path = Path(output).resolve(strict=False)
46
+
47
+ with output_path.open("w", encoding="utf-8") as f:
48
+ json.dump(results, f, indent=4, ensure_ascii=False)
@@ -0,0 +1,10 @@
1
+ from pathlib import Path
2
+ import yaml
3
+
4
+ TEMPLATE_DIR = Path(__file__).parent.parent / "templates"
5
+
6
+ def load_template(name: str) -> dict:
7
+ template_path = TEMPLATE_DIR / f"{name}.yaml"
8
+
9
+ with template_path.open("r", encoding="utf-8") as f:
10
+ return yaml.safe_load(f)
akii/http/__init__.py ADDED
File without changes
akii/http/client.py ADDED
@@ -0,0 +1,28 @@
1
+ import requests
2
+
3
+ from akii import __version__
4
+
5
+ def request(config):
6
+ headers = {
7
+ "User-Agent": f"AkII/{__version__}",
8
+ }
9
+
10
+ cookies = {}
11
+
12
+ if config.get("header"):
13
+ name, value = config["header"].split(":", 1)
14
+ headers[name.strip()] = value.strip()
15
+
16
+ if config.get("cookie"):
17
+ name, value = config["cookie"].split("=", 1)
18
+ cookies[name.strip()] = value.strip()
19
+
20
+ r = requests.request(
21
+ method=config["method"],
22
+ url=config["target"],
23
+ headers=headers or None,
24
+ cookies=cookies or None,
25
+ data=config.get("data"),
26
+ )
27
+
28
+ return r
akii/ui/__init__.py ADDED
File without changes
akii/ui/banner.py ADDED
@@ -0,0 +1,38 @@
1
+ def get_banner():
2
+ # Archived logo
3
+ headerx = r"""
4
+ ::: ::: :::::::::: :::::: ::::::::: :::::::::: ::::::::: ::: :::
5
+ :+: :+: :+: :+: :+: :+: :+: :+: :+: :+: :+: :+:
6
+ +:+ +:+ +:+ +:+ +:+ +:+ +:+ +:+ +:+ +:+ +:+ +:+
7
+ +#++:++#+#+ +#++:++# +#++:++#++: +#+ +:+ +#++:++# +#++:++#: +#++:
8
+ +#+ +#+ +#+ +#+ +#+ +#+ +#+ +#+ +#+ +#+ +#+ +#+
9
+ #+# #+# #+# #+# #+# #+# #+# #+# #+# #+# #+# #+#
10
+ ### ### ######### ### ### ######### ########## ### ### ### ###
11
+ """
12
+
13
+ hdrx = r"""
14
+
15
+ ::: ::: ::::::::: ::::::::: ::: :::
16
+ :+: :+: :+: :+: :+: :+: :+: :+:
17
+ +:+ +:+ +:+ +:+ +:+ +:+ +:+ +:+
18
+ +#++:++#+#+ +#+ +:+ +#++:++#: +#++:
19
+ +#+ +#+ +#+ +#+ +#+ +#+ +#+ +#+
20
+ #+# #+# #+# #+# #+# #+# #+# #+#
21
+ ### ### ######### ### ### ### ###
22
+ """
23
+ # Current logo
24
+ akii = r"""
25
+ _____ ___ ___ ___ ___
26
+ :::::::╗ :::║ :::║ :::║ :::║
27
+ :+:╔══:+:╗ :+:║ :+:║ :+:║ :+:║
28
+ +:+╔╝ +:+╗ +:+║ +:+║ ═══╝ ═══╝
29
+ +++║____+++║ +++║__+++║ ___ ___
30
+ +#++:++#++:║ +#++:+╣__ +#+║ +#+║
31
+ +#+╔════+#+║ +#+╔══+#+║ +#+║ +#+║
32
+ #+#║ #+#║ #+#║ #+#║ #+#║ #+#║ v0.1.0
33
+ ###║ ###║ ###║ ###║ ###║ ###║
34
+ ═══╝ ═══╝ ═══╝ ═══╝ ═══╝ ═══╝
35
+ - MintTester-IO -
36
+ """
37
+
38
+ return akii
akii/ui/output.py ADDED
@@ -0,0 +1,107 @@
1
+ from colorama import Fore, Style, init
2
+
3
+ from akii.ui.banner import get_banner
4
+
5
+ init(autoreset=True)
6
+
7
+
8
+ def severity_color(severity):
9
+ severity = severity.upper()
10
+
11
+ if severity == "CRITICAL":
12
+ return Fore.LIGHTRED_EX
13
+ if severity == "HIGH":
14
+ return Fore.RED
15
+ if severity == "MEDIUM":
16
+ return Fore.YELLOW
17
+ if severity == "LOW":
18
+ return Fore.GREEN
19
+ if severity == "INFO":
20
+ return Fore.BLUE
21
+
22
+ return Fore.WHITE
23
+
24
+
25
+ def banner():
26
+ print(get_banner())
27
+
28
+
29
+ def display_http(config, response):
30
+ if config.get("verbose"):
31
+ print(Fore.CYAN + "=== Request ===")
32
+ print(f"{response.request.method} {response.request.url}\n")
33
+
34
+ for key, value in response.request.headers.items():
35
+ print(f"{Fore.GREEN}{key}{Style.RESET_ALL}: {value}")
36
+
37
+ print(Fore.CYAN + "\n=== Response ===")
38
+ print(f"Status: {response.status_code}\n")
39
+
40
+ for key, value in response.headers.items():
41
+ print(f"{Fore.GREEN}{key}{Style.RESET_ALL}: {value}")
42
+
43
+ print()
44
+ return
45
+
46
+ if config.get("request"):
47
+ print(Fore.CYAN + "=== Request ===")
48
+ print(f"{response.request.method} {response.request.url}\n")
49
+
50
+ for key, value in response.request.headers.items():
51
+ print(f"{Fore.GREEN}{key}{Style.RESET_ALL}: {value}")
52
+
53
+ print()
54
+
55
+ if config.get("response"):
56
+ print(Fore.CYAN + "=== Response ===")
57
+ print(f"Status: {response.status_code}\n")
58
+
59
+ for key, value in response.headers.items():
60
+ print(f"{Fore.GREEN}{key}{Style.RESET_ALL}: {value}")
61
+
62
+ print()
63
+
64
+
65
+ def csp_result(results):
66
+ print(Fore.CYAN + "=== CSP Analysis ===")
67
+
68
+ if not results:
69
+ print(Fore.GREEN + "No CSP issues found.\n")
70
+ return
71
+
72
+ for count, result in enumerate(results, start=1):
73
+ color = severity_color(result["severity"])
74
+
75
+ print(f"({count}> {color}[{result['severity'].upper()}]{Style.RESET_ALL} {result['header']}")
76
+
77
+ if "value" in result:
78
+ print(f" {Fore.GREEN}Value{Style.RESET_ALL} : {result['value']}")
79
+
80
+ print(f" {Fore.GREEN}Message{Style.RESET_ALL} : {result['message']}")
81
+
82
+ print()
83
+
84
+
85
+ def cors_result(results):
86
+ print(Fore.CYAN + "=== CORS Analysis ===")
87
+
88
+ if not results:
89
+ print(Fore.GREEN + "No CORS issues found.\n")
90
+ return
91
+
92
+ for count, result in enumerate(results, start=1):
93
+ color = severity_color(result["severity"])
94
+
95
+ print(f"({count}> {color}[{result['severity'].upper()}]{Style.RESET_ALL} {result['header']}")
96
+
97
+ if "value" in result:
98
+ print(f" {Fore.GREEN}Value{Style.RESET_ALL} : {result['value']}")
99
+
100
+ print(f" {Fore.GREEN}Message{Style.RESET_ALL} : {result['message']}")
101
+
102
+ print()
103
+
104
+
105
+ def display_target(config):
106
+ print("=" * 60)
107
+ print(Fore.YELLOW + f"Target: {config['target']}\n")
@@ -0,0 +1,170 @@
1
+ Metadata-Version: 2.4
2
+ Name: akii
3
+ Version: 0.1.0
4
+ Summary: HTTP header analyzer
5
+ License-Expression: MIT
6
+ Requires-Python: >=3.11
7
+ Description-Content-Type: text/markdown
8
+ Requires-Dist: requests>=2.32.0
9
+ Requires-Dist: PyYAML>=6.0
10
+ Requires-Dist: colorama>=0.4.6
11
+
12
+ # AkII
13
+
14
+ > A fast and lightweight HTTP security header analyzer.
15
+
16
+ AkII is an open-source security tool for analyzing HTTP response headers and identifying common security misconfigurations, such as weak or missing security headers.
17
+
18
+ > **⚠️ Early Development**
19
+ >
20
+ > AkII is in an early stage of development. Some features are still incomplete, and bugs are expected. The project is under active development, and new functionality will be added in future releases.
21
+
22
+ ## Features
23
+
24
+ - Analyze HTTP security headers
25
+ - Detect common CORS misconfigurations
26
+ - Detect missing or insecure Content Security Policy (CSP)
27
+ - Human-readable terminal output
28
+ - JSON output for automation
29
+ - Lightweight and extensible YAML-based rule engine
30
+
31
+ ## Why AkII?
32
+
33
+ AkII is designed for speed, automation, and extensibility.
34
+
35
+ AkII focuses on one task: analyzing HTTP security headers quickly and consistently.
36
+
37
+ It is suitable for:
38
+
39
+ - CI/CD pipelines
40
+ - Security automation
41
+ - Bug bounty workflows
42
+ - Batch scanning with wordlists
43
+ - Integration into custom tools
44
+
45
+ ## Installation
46
+
47
+ ### From PyPI (Recommended)
48
+
49
+ ```bash
50
+ pipx install akii
51
+ ```
52
+
53
+ or
54
+
55
+ ```bash
56
+ pip install akii
57
+ ```
58
+
59
+ ### From Source
60
+
61
+ ```bash
62
+ git clone https://github.com/MintTester-IO/AkII.git
63
+ cd akii
64
+ pip install -e .
65
+ ```
66
+
67
+ ## Uninstallation
68
+
69
+ If you installed AkII with **pipx**:
70
+
71
+ ```bash
72
+ pipx uninstall akii
73
+ ```
74
+
75
+ If you installed AkII with **pip**:
76
+
77
+ ```bash
78
+ pip uninstall akii
79
+ ```
80
+
81
+ If you installed AkII from source using `pip install -e .`:
82
+
83
+ ```bash
84
+ pip uninstall akii
85
+ cd ..
86
+ rm -rf akii
87
+ ```
88
+
89
+ ## Usage
90
+
91
+ Scan a single target:
92
+
93
+ ```bash
94
+ akii -T https://example.com
95
+ ```
96
+
97
+ Scan multiple targets:
98
+
99
+ ```bash
100
+ akii -w targets.txt
101
+ ```
102
+
103
+ Show request headers:
104
+
105
+ ```bash
106
+ akii -T https://example.com --request
107
+ ```
108
+
109
+ Show response headers:
110
+
111
+ ```bash
112
+ akii -T https://example.com --response
113
+ ```
114
+
115
+ Verbose mode:
116
+
117
+ ```bash
118
+ akii -T https://example.com --verbose
119
+ ```
120
+
121
+ Save the report:
122
+
123
+ ```bash
124
+ akii -T https://example.com -o report.txt
125
+ ```
126
+
127
+ Export JSON:
128
+
129
+ ```bash
130
+ akii -T https://example.com -jo report.txt
131
+ ```
132
+
133
+ ## Current Checks
134
+
135
+ - Cross-Origin Resource Sharing (CORS)
136
+ - Content Security Policy (CSP)
137
+
138
+ More security header checks will be added in future releases.
139
+
140
+ ## Project Structure
141
+
142
+ ```
143
+ src/akii/
144
+ ├── checks/ # Detection and analysis modules
145
+ ├── core/ # Controller, CLI, reporting
146
+ ├── http/ # HTTP client
147
+ ├── templates/ # YAML rule definitions
148
+ └── ui/ # Terminal output
149
+ ```
150
+
151
+ ## Roadmap
152
+
153
+ - HSTS analysis
154
+ - Cookie analysis
155
+ - Cache-Control analysis
156
+ - Permissions-Policy analysis
157
+ - Referrer-Policy analysis
158
+ - HTML reports
159
+ - Improved JSON reporting
160
+ - Plugin system
161
+
162
+ ## Contributing
163
+
164
+ Contributions are welcome.
165
+
166
+ If you find a bug, have a feature request, or would like to improve AkII, please open an issue or submit a pull request.
167
+
168
+ ## License
169
+
170
+ This project is licensed under the MIT License.
@@ -0,0 +1,25 @@
1
+ akii/__init__.py,sha256=Pru0BlFBASFCFo7McHdohtKkUtgMPDwbGfyUZlE2_Vw,21
2
+ akii/checks/__init__.py,sha256=rKnJQxLAUKdHGZ9U_AGQ_rUnM-sky0G0Z3m8SFhXDKA,106
3
+ akii/checks/cache.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
4
+ akii/checks/cookie.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
5
+ akii/checks/cors.py,sha256=ZLQeVhy33wkkn7rphqdOv5qFcZeq0IvsZdfStZiaf6s,969
6
+ akii/checks/csp.py,sha256=_Qq_yMFLX7LTSPwXciFN0Ujjn1GEeQ5s4xx5wDUmUnA,1215
7
+ akii/checks/hsts.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
8
+ akii/core/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
9
+ akii/core/controller.py,sha256=tMzGvXROtRJrWBIcI0ch_8gTZEFfVkcWvoNsjvjvI6I,1569
10
+ akii/core/reporter.py,sha256=zDxFcHTZOAt4_PSlKzskhZhNhIJYxSh3jDtrUajisZo,1604
11
+ akii/core/template_loader.py,sha256=2I6PuqnXbEKaio18z5bwoNUzKwprRWRr5YS-PunzQ0M,276
12
+ akii/core/cli/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
13
+ akii/core/cli/main.py,sha256=9ajb1ECik7rSILeFocMe7uwqLGE3um63xbD76ChanWM,280
14
+ akii/core/cli/parser.py,sha256=AePMLO68c2QEldi9b564dI8Kxca6tdXU9h62Did2pcE,1481
15
+ akii/core/flags/general.py,sha256=44HoTx_UEIoDOZu7_qDjx1Yv6YRPnaZXbEk7ZKLJ_aY,2498
16
+ akii/http/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
17
+ akii/http/client.py,sha256=9ixxK_8TsZieRE1EDv3pEmfRQlP2CoQV3aoHawmEPSs,615
18
+ akii/ui/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
19
+ akii/ui/banner.py,sha256=y5XVUAcOVCKZxT6lED8JWEy9aNwXB9Y1MSuDgI8nGiI,1520
20
+ akii/ui/output.py,sha256=QBjSeGowLq1vljrHEYGWFTD8bViqMF9A2N-giSIkCvM,2885
21
+ akii-0.1.0.dist-info/METADATA,sha256=DbGLU81WMa8RDU7Enh9zjbTjrVk4VXO28r1BWXt1qTM,3108
22
+ akii-0.1.0.dist-info/WHEEL,sha256=K260EYznzXsJYBQGqmI8VTxEdiZYNvDZwW9cBh9-_MA,91
23
+ akii-0.1.0.dist-info/entry_points.txt,sha256=-PaisvSUKkbp23Kt7e7SPHgrmgUkrIBm1R6qVDGBvZ8,49
24
+ akii-0.1.0.dist-info/top_level.txt,sha256=jjtw8hsJ0J2yXXwWXSPzapmlne9mPUwnN0gXwtSbeoU,5
25
+ akii-0.1.0.dist-info/RECORD,,
@@ -0,0 +1,5 @@
1
+ Wheel-Version: 1.0
2
+ Generator: setuptools (83.0.0)
3
+ Root-Is-Purelib: true
4
+ Tag: py3-none-any
5
+
@@ -0,0 +1,2 @@
1
+ [console_scripts]
2
+ akii = akii.core.cli.main:main
@@ -0,0 +1 @@
1
+ akii