scythe-ttp 0.13.0__tar.gz → 0.15.0__tar.gz
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.
Potentially problematic release.
This version of scythe-ttp might be problematic. Click here for more details.
- {scythe_ttp-0.13.0/scythe_ttp.egg-info → scythe_ttp-0.15.0}/PKG-INFO +83 -17
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/README.md +76 -0
- scythe_ttp-0.15.0/VERSION +1 -0
- scythe_ttp-0.15.0/pyproject.toml +56 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/requirements.txt +5 -3
- scythe_ttp-0.15.0/scythe/cli/__init__.py +3 -0
- scythe_ttp-0.15.0/scythe/cli/main.py +601 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/core/headers.py +69 -9
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/journeys/actions.py +172 -61
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/journeys/base.py +121 -5
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/journeys/executor.py +40 -1
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0/scythe_ttp.egg-info}/PKG-INFO +83 -17
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe_ttp.egg-info/SOURCES.txt +5 -1
- scythe_ttp-0.15.0/scythe_ttp.egg-info/entry_points.txt +2 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe_ttp.egg-info/requires.txt +4 -3
- scythe_ttp-0.15.0/scythe_ttp.egg-info/top_level.txt +5 -0
- scythe_ttp-0.15.0/tests/test_cli.py +152 -0
- scythe_ttp-0.13.0/VERSION +0 -1
- scythe_ttp-0.13.0/scythe_ttp.egg-info/top_level.txt +0 -1
- scythe_ttp-0.13.0/setup.py +0 -43
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/LICENSE +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/MANIFEST.in +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/__init__.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/auth/__init__.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/auth/base.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/auth/basic.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/auth/bearer.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/auth/cookie_jwt.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/behaviors/__init__.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/behaviors/base.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/behaviors/default.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/behaviors/human.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/behaviors/machine.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/behaviors/stealth.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/core/__init__.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/core/executor.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/core/ttp.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/journeys/__init__.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/orchestrators/__init__.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/orchestrators/base.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/orchestrators/batch.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/orchestrators/distributed.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/orchestrators/scale.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/payloads/__init__.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/payloads/generators.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/ttps/__init__.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/ttps/web/__init__.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/ttps/web/login_bruteforce.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/ttps/web/sql_injection.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe/ttps/web/uuid_guessing.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/scythe_ttp.egg-info/dependency_links.txt +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/setup.cfg +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/tests/test_api_models.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/tests/test_authentication.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/tests/test_behaviors.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/tests/test_cookie_jwt_auth.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/tests/test_expected_results.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/tests/test_feature_completeness.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/tests/test_header_extraction.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/tests/test_journeys.py +0 -0
- {scythe_ttp-0.13.0 → scythe_ttp-0.15.0}/tests/test_orchestrators.py +0 -0
|
@@ -1,10 +1,8 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: scythe-ttp
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.15.0
|
|
4
4
|
Summary: An extensible framework for emulating attacker TTPs with Selenium.
|
|
5
|
-
|
|
6
|
-
Author: EpykLab
|
|
7
|
-
Author-email: cyber@epyklab.com
|
|
5
|
+
Author-email: EpykLab <cyber@epyklab.com>
|
|
8
6
|
Classifier: Programming Language :: Python :: 3
|
|
9
7
|
Classifier: License :: OSI Approved :: MIT License
|
|
10
8
|
Classifier: Operating System :: OS Independent
|
|
@@ -13,39 +11,31 @@ Classifier: Intended Audience :: Developers
|
|
|
13
11
|
Classifier: Intended Audience :: Information Technology
|
|
14
12
|
Classifier: Topic :: Security
|
|
15
13
|
Classifier: Framework :: Pytest
|
|
16
|
-
Requires-Python:
|
|
14
|
+
Requires-Python: <=3.13,>=3.8
|
|
17
15
|
Description-Content-Type: text/markdown
|
|
18
16
|
License-File: LICENSE
|
|
17
|
+
Requires-Dist: PySocks==1.7.1
|
|
19
18
|
Requires-Dist: attrs==25.3.0
|
|
20
19
|
Requires-Dist: certifi==2025.6.15
|
|
21
20
|
Requires-Dist: charset-normalizer==3.4.2
|
|
22
21
|
Requires-Dist: h11==0.16.0
|
|
23
22
|
Requires-Dist: idna==3.10
|
|
24
23
|
Requires-Dist: outcome==1.3.0.post0
|
|
25
|
-
Requires-Dist: PySocks==1.7.1
|
|
26
|
-
Requires-Dist: pydantic==2.7.1
|
|
27
24
|
Requires-Dist: pydantic-core==2.18.2
|
|
25
|
+
Requires-Dist: pydantic==2.7.1
|
|
28
26
|
Requires-Dist: requests==2.32.4
|
|
29
27
|
Requires-Dist: selenium==4.34.0
|
|
30
28
|
Requires-Dist: setuptools==80.9.0
|
|
31
29
|
Requires-Dist: sniffio==1.3.1
|
|
32
30
|
Requires-Dist: sortedcontainers==2.4.0
|
|
33
|
-
Requires-Dist: trio==0.30.0
|
|
34
31
|
Requires-Dist: trio-websocket==0.12.2
|
|
32
|
+
Requires-Dist: trio==0.30.0
|
|
35
33
|
Requires-Dist: typing_extensions==4.14.0
|
|
36
34
|
Requires-Dist: urllib3==2.4.0
|
|
37
35
|
Requires-Dist: websocket-client==1.8.0
|
|
38
36
|
Requires-Dist: wsproto==1.2.0
|
|
39
|
-
|
|
40
|
-
Dynamic: author-email
|
|
41
|
-
Dynamic: classifier
|
|
42
|
-
Dynamic: description
|
|
43
|
-
Dynamic: description-content-type
|
|
44
|
-
Dynamic: home-page
|
|
37
|
+
Requires-Dist: typer
|
|
45
38
|
Dynamic: license-file
|
|
46
|
-
Dynamic: requires-dist
|
|
47
|
-
Dynamic: requires-python
|
|
48
|
-
Dynamic: summary
|
|
49
39
|
|
|
50
40
|
<h1 align="center">Scythe</h1>
|
|
51
41
|
|
|
@@ -794,3 +784,79 @@ This architecture supports testing scenarios from simple security checks to comp
|
|
|
794
784
|
---
|
|
795
785
|
|
|
796
786
|
**Scythe**: Comprehensive adverse conditions testing for robust, reliable systems.
|
|
787
|
+
|
|
788
|
+
|
|
789
|
+
|
|
790
|
+
## Scythe CLI (embedded)
|
|
791
|
+
|
|
792
|
+
Scythe now ships with a lightweight CLI that helps you bootstrap and manage your local Scythe testing workspace. After installing the package (pipx recommended), a `scythe` command is available.
|
|
793
|
+
|
|
794
|
+
Note: The CLI is implemented with Typer, so `scythe --help` and per-command help (e.g., `scythe run --help`) are available. Command names and options remain the same as before.
|
|
795
|
+
|
|
796
|
+
- Install with pipx:
|
|
797
|
+
- pipx install scythe-ttp
|
|
798
|
+
- Or install locally in editable mode for development:
|
|
799
|
+
- pip install -e .
|
|
800
|
+
|
|
801
|
+
### Commands
|
|
802
|
+
|
|
803
|
+
- scythe init [--path PATH]
|
|
804
|
+
- Initializes a Scythe project at PATH (default: current directory).
|
|
805
|
+
- Creates:
|
|
806
|
+
- ./.scythe/scythe.db (SQLite DB with tests and runs tables)
|
|
807
|
+
- ./.scythe/scythe_tests/ (where your test scripts live)
|
|
808
|
+
|
|
809
|
+
- scythe new <name>
|
|
810
|
+
- Creates a new test template at ./.scythe/scythe_tests/<name>.py and registers it in the DB (tests table).
|
|
811
|
+
|
|
812
|
+
- scythe run <name or name.py>
|
|
813
|
+
- Runs the specified test from ./.scythe/scythe_tests and records the run into the DB (runs table). Exit code reflects success (0) or failure (non-zero).
|
|
814
|
+
|
|
815
|
+
- scythe db dump
|
|
816
|
+
- Prints a JSON dump of the tests and runs tables from ./.scythe/scythe.db.
|
|
817
|
+
|
|
818
|
+
- scythe db sync-compat <name>
|
|
819
|
+
- Reads COMPATIBLE_VERSIONS from ./.scythe/scythe_tests/<name>.py (if present) and updates the `tests.compatible_versions` field in the DB. If the variable is missing, the DB entry is set to empty and the command exits successfully.
|
|
820
|
+
|
|
821
|
+
### Test template
|
|
822
|
+
|
|
823
|
+
Created tests use a minimal template so you can start quickly:
|
|
824
|
+
|
|
825
|
+
```python
|
|
826
|
+
#!/usr/bin/env python3
|
|
827
|
+
|
|
828
|
+
# scythe test initial template
|
|
829
|
+
|
|
830
|
+
import argparse
|
|
831
|
+
import os
|
|
832
|
+
import sys
|
|
833
|
+
import time
|
|
834
|
+
from typing import List, Tuple
|
|
835
|
+
|
|
836
|
+
# Scythe framework imports
|
|
837
|
+
from scythe.core.executor import TTPExecutor
|
|
838
|
+
from scythe.behaviors import HumanBehavior
|
|
839
|
+
|
|
840
|
+
|
|
841
|
+
def scythe_test_definition(args):
|
|
842
|
+
# TODO: implement your test using Scythe primitives.
|
|
843
|
+
return True
|
|
844
|
+
|
|
845
|
+
|
|
846
|
+
def main():
|
|
847
|
+
parser = argparse.ArgumentParser(description="Scythe test script")
|
|
848
|
+
parser.add_argument('--url', help='Target URL (overridden by localhost unless FORCE_USE_CLI_URL=1)')
|
|
849
|
+
args = parser.parse_args()
|
|
850
|
+
|
|
851
|
+
ok = scythe_test_definition(args)
|
|
852
|
+
sys.exit(0 if ok else 1)
|
|
853
|
+
|
|
854
|
+
|
|
855
|
+
if __name__ == "__main__":
|
|
856
|
+
main()
|
|
857
|
+
```
|
|
858
|
+
|
|
859
|
+
Notes:
|
|
860
|
+
- The CLI looks for tests in ./.scythe/scythe_tests.
|
|
861
|
+
- Each `run` creates a record in the `runs` table with datetime, name_of_test, x_scythe_target_version (best-effort parsed from output), result, raw_output.
|
|
862
|
+
- Each `new` creates a record in the `tests` table with name, path, created_date, compatible_versions.
|
|
@@ -745,3 +745,79 @@ This architecture supports testing scenarios from simple security checks to comp
|
|
|
745
745
|
---
|
|
746
746
|
|
|
747
747
|
**Scythe**: Comprehensive adverse conditions testing for robust, reliable systems.
|
|
748
|
+
|
|
749
|
+
|
|
750
|
+
|
|
751
|
+
## Scythe CLI (embedded)
|
|
752
|
+
|
|
753
|
+
Scythe now ships with a lightweight CLI that helps you bootstrap and manage your local Scythe testing workspace. After installing the package (pipx recommended), a `scythe` command is available.
|
|
754
|
+
|
|
755
|
+
Note: The CLI is implemented with Typer, so `scythe --help` and per-command help (e.g., `scythe run --help`) are available. Command names and options remain the same as before.
|
|
756
|
+
|
|
757
|
+
- Install with pipx:
|
|
758
|
+
- pipx install scythe-ttp
|
|
759
|
+
- Or install locally in editable mode for development:
|
|
760
|
+
- pip install -e .
|
|
761
|
+
|
|
762
|
+
### Commands
|
|
763
|
+
|
|
764
|
+
- scythe init [--path PATH]
|
|
765
|
+
- Initializes a Scythe project at PATH (default: current directory).
|
|
766
|
+
- Creates:
|
|
767
|
+
- ./.scythe/scythe.db (SQLite DB with tests and runs tables)
|
|
768
|
+
- ./.scythe/scythe_tests/ (where your test scripts live)
|
|
769
|
+
|
|
770
|
+
- scythe new <name>
|
|
771
|
+
- Creates a new test template at ./.scythe/scythe_tests/<name>.py and registers it in the DB (tests table).
|
|
772
|
+
|
|
773
|
+
- scythe run <name or name.py>
|
|
774
|
+
- Runs the specified test from ./.scythe/scythe_tests and records the run into the DB (runs table). Exit code reflects success (0) or failure (non-zero).
|
|
775
|
+
|
|
776
|
+
- scythe db dump
|
|
777
|
+
- Prints a JSON dump of the tests and runs tables from ./.scythe/scythe.db.
|
|
778
|
+
|
|
779
|
+
- scythe db sync-compat <name>
|
|
780
|
+
- Reads COMPATIBLE_VERSIONS from ./.scythe/scythe_tests/<name>.py (if present) and updates the `tests.compatible_versions` field in the DB. If the variable is missing, the DB entry is set to empty and the command exits successfully.
|
|
781
|
+
|
|
782
|
+
### Test template
|
|
783
|
+
|
|
784
|
+
Created tests use a minimal template so you can start quickly:
|
|
785
|
+
|
|
786
|
+
```python
|
|
787
|
+
#!/usr/bin/env python3
|
|
788
|
+
|
|
789
|
+
# scythe test initial template
|
|
790
|
+
|
|
791
|
+
import argparse
|
|
792
|
+
import os
|
|
793
|
+
import sys
|
|
794
|
+
import time
|
|
795
|
+
from typing import List, Tuple
|
|
796
|
+
|
|
797
|
+
# Scythe framework imports
|
|
798
|
+
from scythe.core.executor import TTPExecutor
|
|
799
|
+
from scythe.behaviors import HumanBehavior
|
|
800
|
+
|
|
801
|
+
|
|
802
|
+
def scythe_test_definition(args):
|
|
803
|
+
# TODO: implement your test using Scythe primitives.
|
|
804
|
+
return True
|
|
805
|
+
|
|
806
|
+
|
|
807
|
+
def main():
|
|
808
|
+
parser = argparse.ArgumentParser(description="Scythe test script")
|
|
809
|
+
parser.add_argument('--url', help='Target URL (overridden by localhost unless FORCE_USE_CLI_URL=1)')
|
|
810
|
+
args = parser.parse_args()
|
|
811
|
+
|
|
812
|
+
ok = scythe_test_definition(args)
|
|
813
|
+
sys.exit(0 if ok else 1)
|
|
814
|
+
|
|
815
|
+
|
|
816
|
+
if __name__ == "__main__":
|
|
817
|
+
main()
|
|
818
|
+
```
|
|
819
|
+
|
|
820
|
+
Notes:
|
|
821
|
+
- The CLI looks for tests in ./.scythe/scythe_tests.
|
|
822
|
+
- Each `run` creates a record in the `runs` table with datetime, name_of_test, x_scythe_target_version (best-effort parsed from output), result, raw_output.
|
|
823
|
+
- Each `new` creates a record in the `tests` table with name, path, created_date, compatible_versions.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
0.15.1
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
[build-system]
|
|
2
|
+
requires = ["setuptools>=61.0"]
|
|
3
|
+
build-backend = "setuptools.build_meta"
|
|
4
|
+
|
|
5
|
+
[project]
|
|
6
|
+
name = "scythe-ttp"
|
|
7
|
+
description = "An extensible framework for emulating attacker TTPs with Selenium."
|
|
8
|
+
readme = {file = "README.md", content-type = "text/markdown"}
|
|
9
|
+
authors = [{name = "EpykLab", email = "cyber@epyklab.com"}]
|
|
10
|
+
requires-python = ">=3.8,<=3.13"
|
|
11
|
+
version = "0.15.0"
|
|
12
|
+
classifiers = [
|
|
13
|
+
"Programming Language :: Python :: 3",
|
|
14
|
+
"License :: OSI Approved :: MIT License",
|
|
15
|
+
"Operating System :: OS Independent",
|
|
16
|
+
"Development Status :: 3 - Alpha",
|
|
17
|
+
"Intended Audience :: Developers",
|
|
18
|
+
"Intended Audience :: Information Technology",
|
|
19
|
+
"Topic :: Security",
|
|
20
|
+
"Framework :: Pytest",
|
|
21
|
+
]
|
|
22
|
+
|
|
23
|
+
dependencies = [
|
|
24
|
+
"PySocks==1.7.1",
|
|
25
|
+
"attrs==25.3.0",
|
|
26
|
+
"certifi==2025.6.15",
|
|
27
|
+
"charset-normalizer==3.4.2",
|
|
28
|
+
"h11==0.16.0",
|
|
29
|
+
"idna==3.10",
|
|
30
|
+
"outcome==1.3.0.post0",
|
|
31
|
+
"pydantic-core==2.18.2",
|
|
32
|
+
"pydantic==2.7.1",
|
|
33
|
+
"requests==2.32.4",
|
|
34
|
+
"selenium==4.34.0",
|
|
35
|
+
"setuptools==80.9.0",
|
|
36
|
+
"sniffio==1.3.1",
|
|
37
|
+
"sortedcontainers==2.4.0",
|
|
38
|
+
"trio-websocket==0.12.2",
|
|
39
|
+
"trio==0.30.0",
|
|
40
|
+
"typing_extensions==4.14.0",
|
|
41
|
+
"urllib3==2.4.0",
|
|
42
|
+
"websocket-client==1.8.0",
|
|
43
|
+
"wsproto==1.2.0",
|
|
44
|
+
"typer"
|
|
45
|
+
]
|
|
46
|
+
|
|
47
|
+
[project.scripts]
|
|
48
|
+
scythe = "scythe.cli.main:main"
|
|
49
|
+
|
|
50
|
+
[tool.setuptools]
|
|
51
|
+
# Use find_packages and exclude tests/examples from the distribution
|
|
52
|
+
packages = {find = {exclude = ["tests*", "examples*"]}}
|
|
53
|
+
|
|
54
|
+
[tool.setuptools.dynamic]
|
|
55
|
+
version = {file = "0.15.0"}
|
|
56
|
+
dependencies = {file = "requirements.txt"}
|
|
@@ -1,20 +1,22 @@
|
|
|
1
|
+
PySocks==1.7.1
|
|
1
2
|
attrs==25.3.0
|
|
2
3
|
certifi==2025.6.15
|
|
3
4
|
charset-normalizer==3.4.2
|
|
4
5
|
h11==0.16.0
|
|
5
6
|
idna==3.10
|
|
6
7
|
outcome==1.3.0.post0
|
|
7
|
-
PySocks==1.7.1
|
|
8
|
-
pydantic==2.7.1
|
|
9
8
|
pydantic-core==2.18.2
|
|
9
|
+
pydantic==2.7.1
|
|
10
10
|
requests==2.32.4
|
|
11
11
|
selenium==4.34.0
|
|
12
12
|
setuptools==80.9.0
|
|
13
13
|
sniffio==1.3.1
|
|
14
14
|
sortedcontainers==2.4.0
|
|
15
|
-
trio==0.30.0
|
|
16
15
|
trio-websocket==0.12.2
|
|
16
|
+
trio==0.30.0
|
|
17
17
|
typing_extensions==4.14.0
|
|
18
18
|
urllib3==2.4.0
|
|
19
19
|
websocket-client==1.8.0
|
|
20
20
|
wsproto==1.2.0
|
|
21
|
+
# CLI framework
|
|
22
|
+
typer==0.12.5
|