feat: support scanning IP addresses
This commit is contained in:
@@ -18,13 +18,14 @@ class StrixAgent(BaseAgent):
|
|||||||
|
|
||||||
super().__init__(config)
|
super().__init__(config)
|
||||||
|
|
||||||
async def execute_scan(self, scan_config: dict[str, Any]) -> dict[str, Any]:
|
async def execute_scan(self, scan_config: dict[str, Any]) -> dict[str, Any]: # noqa: PLR0912
|
||||||
user_instructions = scan_config.get("user_instructions", "")
|
user_instructions = scan_config.get("user_instructions", "")
|
||||||
targets = scan_config.get("targets", [])
|
targets = scan_config.get("targets", [])
|
||||||
|
|
||||||
repositories = []
|
repositories = []
|
||||||
local_code = []
|
local_code = []
|
||||||
urls = []
|
urls = []
|
||||||
|
ip_addresses = []
|
||||||
|
|
||||||
for target in targets:
|
for target in targets:
|
||||||
target_type = target["type"]
|
target_type = target["type"]
|
||||||
@@ -53,6 +54,8 @@ class StrixAgent(BaseAgent):
|
|||||||
|
|
||||||
elif target_type == "web_application":
|
elif target_type == "web_application":
|
||||||
urls.append(details["target_url"])
|
urls.append(details["target_url"])
|
||||||
|
elif target_type == "ip_address":
|
||||||
|
ip_addresses.append(details["target_ip"])
|
||||||
|
|
||||||
task_parts = []
|
task_parts = []
|
||||||
|
|
||||||
@@ -74,6 +77,10 @@ class StrixAgent(BaseAgent):
|
|||||||
task_parts.append("\n\nURLs:")
|
task_parts.append("\n\nURLs:")
|
||||||
task_parts.extend(f"- {url}" for url in urls)
|
task_parts.extend(f"- {url}" for url in urls)
|
||||||
|
|
||||||
|
if ip_addresses:
|
||||||
|
task_parts.append("\n\nIP Addresses:")
|
||||||
|
task_parts.extend(f"- {ip}" for ip in ip_addresses)
|
||||||
|
|
||||||
task_description = " ".join(task_parts)
|
task_description = " ".join(task_parts)
|
||||||
|
|
||||||
if user_instructions:
|
if user_instructions:
|
||||||
|
|||||||
@@ -260,6 +260,9 @@ Examples:
|
|||||||
# Domain penetration test
|
# Domain penetration test
|
||||||
strix --target example.com
|
strix --target example.com
|
||||||
|
|
||||||
|
# IP address penetration test
|
||||||
|
strix --target 192.168.1.42
|
||||||
|
|
||||||
# Multiple targets (e.g., white-box testing with source and deployed app)
|
# Multiple targets (e.g., white-box testing with source and deployed app)
|
||||||
strix --target https://github.com/user/repo --target https://example.com
|
strix --target https://github.com/user/repo --target https://example.com
|
||||||
strix --target ./my-project --target https://staging.example.com --target https://prod.example.com
|
strix --target ./my-project --target https://staging.example.com --target https://prod.example.com
|
||||||
@@ -275,7 +278,7 @@ Examples:
|
|||||||
type=str,
|
type=str,
|
||||||
required=True,
|
required=True,
|
||||||
action="append",
|
action="append",
|
||||||
help="Target to test (URL, repository, local directory path, or domain name). "
|
help="Target to test (URL, repository, local directory path, domain name, or IP address). "
|
||||||
"Can be specified multiple times for multi-target scans.",
|
"Can be specified multiple times for multi-target scans.",
|
||||||
)
|
)
|
||||||
parser.add_argument(
|
parser.add_argument(
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
|
import ipaddress
|
||||||
import re
|
import re
|
||||||
import secrets
|
import secrets
|
||||||
import shutil
|
import shutil
|
||||||
@@ -141,7 +142,7 @@ def generate_run_name() -> str:
|
|||||||
|
|
||||||
|
|
||||||
# Target processing utilities
|
# Target processing utilities
|
||||||
def infer_target_type(target: str) -> tuple[str, dict[str, str]]:
|
def infer_target_type(target: str) -> tuple[str, dict[str, str]]: # noqa: PLR0911
|
||||||
if not target or not isinstance(target, str):
|
if not target or not isinstance(target, str):
|
||||||
raise ValueError("Target must be a non-empty string")
|
raise ValueError("Target must be a non-empty string")
|
||||||
|
|
||||||
@@ -167,6 +168,13 @@ def infer_target_type(target: str) -> tuple[str, dict[str, str]]:
|
|||||||
return "repository", {"target_repo": target}
|
return "repository", {"target_repo": target}
|
||||||
return "web_application", {"target_url": target}
|
return "web_application", {"target_url": target}
|
||||||
|
|
||||||
|
try:
|
||||||
|
ip_obj = ipaddress.ip_address(target)
|
||||||
|
except ValueError:
|
||||||
|
pass
|
||||||
|
else:
|
||||||
|
return "ip_address", {"target_ip": str(ip_obj)}
|
||||||
|
|
||||||
path = Path(target).expanduser()
|
path = Path(target).expanduser()
|
||||||
try:
|
try:
|
||||||
if path.exists():
|
if path.exists():
|
||||||
@@ -191,7 +199,8 @@ def infer_target_type(target: str) -> tuple[str, dict[str, str]]:
|
|||||||
"- A valid URL (http:// or https://)\n"
|
"- A valid URL (http:// or https://)\n"
|
||||||
"- A Git repository URL (https://github.com/... or git@github.com:...)\n"
|
"- A Git repository URL (https://github.com/... or git@github.com:...)\n"
|
||||||
"- A local directory path\n"
|
"- A local directory path\n"
|
||||||
"- A domain name (e.g., example.com)"
|
"- A domain name (e.g., example.com)\n"
|
||||||
|
"- An IP address (e.g., 192.168.1.10)"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user