From db6caed7df2e6c5620b34808e2aa9fbfb9dc4c1e Mon Sep 17 00:00:00 2001 From: Romain Richard Date: Tue, 27 Jul 2021 23:30:35 +0200 Subject: [PATCH 1/2] Replace --ipaddress and --domain with --target This simplifies the interface, no need for the user to switch arguments, the script will figure it out itself just like it does with the values in the file passed with the --file argument. Factorize the code a bit more: * Added get_args() to handle argument parsing * Added check_targets() to handle checking targets This helps keep the main() function short and clean. It also now allows users to easily call this script without using the CLI, by writing a new python script: ``` from investigate import SHODAN, WHOIS, check_targets check_targets(["abc.com", "1.2.3.4"], [SHODAN, WHOIS]) ``` Move the ip_check() and domain_check() functions to be next to check_targets(), I think it makes more sense than having those all the way at the bottom while the other functions related to those are at the top. --- investigate.py | 134 +++++++++++++++++++++++++++---------------------- 1 file changed, 73 insertions(+), 61 deletions(-) diff --git a/investigate.py b/investigate.py index 11e17e4..f0637b2 100755 --- a/investigate.py +++ b/investigate.py @@ -51,15 +51,26 @@ def main(): """ - Defining main parser for arguments passed to the script. + Parse arguments and run the checks. """ + args = get_args() + if args.target: + targets = [args.target] + else: + with open(args.file) as f: + targets = f.readlines() + check_targets(targets, args.platforms) + +def get_args(): + """ + Defining main parser for arguments passed to the script. + """ parser = argparse.ArgumentParser( description="Investigate an IP address or Domain for available OSINT." ) group = parser.add_mutually_exclusive_group(required=True) - group.add_argument("-i", "--ipaddress", help="IP to investigate.") - group.add_argument("-d", "--domain", help="Domain to investigate.") + group.add_argument("-t", "--target", help="Target (IP or domain) to investigate.") group.add_argument( "-f", "--file", @@ -73,32 +84,65 @@ def main(): default=PLATFORMS, choices=PLATFORMS, ) - args = parser.parse_args() - - if args.ipaddress: - ip_check(args.ipaddress, args.platforms) - elif args.domain: - domain_check(args.domain, args.platforms) - elif args.file: - targets_processed_count = 0 - is_ratelimited = bool(set(args.platforms).intersection(RATELIMITED_PLATFORMS)) - with open(args.file) as file: - for target in file: - if targets_processed_count > 5: - print("Stopping due to API ratelimits.") - break - clean = target.strip() - kind = clean.replace(".", "").replace(":", "").replace("/", "") - if kind.isdigit(): - if is_ratelimited: - targets_processed_count += 1 - ip_check(clean, args.platforms) - elif kind.isalnum(): - if is_ratelimited: - targets_processed_count += 1 - domain_check(clean, args.platforms) - else: - print(f"Skipping {clean}, can't determine the type.") + return parser.parse_args() + + +def check_targets(targets, platforms): + """ + Check the list of targets (IP or domain). + """ + targets_processed_count = 0 + is_ratelimited = bool(set(platforms).intersection(RATELIMITED_PLATFORMS)) + for target in targets: + if targets_processed_count > 5: + print("Stopping due to API ratelimits.") + break + target = target.strip() + kind = target.replace(".", "").replace(":", "").replace("/", "") + if kind.isdigit(): + # Target only contains digits, must be an IP address + if is_ratelimited: + targets_processed_count += 1 + ip_check(target, platforms) + elif kind.isalnum(): + # Target must be a domain + if is_ratelimited: + targets_processed_count += 1 + domain_check(target, platforms) + else: + print(f"Skipping {target}, can't determine the type.") + + +def ip_check(target, platforms): + """ + Collection of all IP check functions to run. + """ + if IPINFO_IO in platforms: + geo_info(target) + if SHODAN in platforms: + shodan_check(target) + if VIRUSTOTAL in platforms: + vt_ip_check(target) + if ALIENVAULT_OTX in platforms: + av_otx(target) + if IBM_X_FORCE in platforms: + xforce_ip(target) + if ROBTEX in platforms: + robtex(target) + + +def domain_check(target, platforms): + """ + Collection of all Domain check functions to run. + """ + if WHOIS in platforms: + whois_lookup(target) + if VIRUSTOTAL in platforms: + vt_domain_check(target) + if ALIENVAULT_OTX in platforms: + av_otx_domain(target) + if IBM_X_FORCE in platforms: + xforce_domain(target) # Start of IP Check functions @@ -568,37 +612,5 @@ def xforce_domain(target): ) -def ip_check(target, platforms): - """ - Collection of all IP check functions to run. - """ - if IPINFO_IO in platforms: - geo_info(target) - if SHODAN in platforms: - shodan_check(target) - if VIRUSTOTAL in platforms: - vt_ip_check(target) - if ALIENVAULT_OTX in platforms: - av_otx(target) - if IBM_X_FORCE in platforms: - xforce_ip(target) - if ROBTEX in platforms: - robtex(target) - - -def domain_check(target, platforms): - """ - Collection of all Domain check functions to run. - """ - if WHOIS in platforms: - whois_lookup(target) - if VIRUSTOTAL in platforms: - vt_domain_check(target) - if ALIENVAULT_OTX in platforms: - av_otx_domain(target) - if IBM_X_FORCE in platforms: - xforce_domain(target) - - if __name__ == "__main__": main() From 693dec0bf26a72bec4f04a969857fae72fdad5f2 Mon Sep 17 00:00:00 2001 From: Romain Richard Date: Tue, 27 Jul 2021 23:43:27 +0200 Subject: [PATCH 2/2] Replace --ipaddress and --domain with --target in README too --- README.md | 18 +++++++----------- 1 file changed, 7 insertions(+), 11 deletions(-) diff --git a/README.md b/README.md index 4850964..917d445 100644 --- a/README.md +++ b/README.md @@ -53,14 +53,10 @@ $ investigate #### Example Usage -Python Hunt can take single IPs as command line argument with `-i` or `--ipaddress`. +Python Hunt can perform a lookup for an IP addresse and domain: ```bash -$ investigate -i 95.217.163.246 -``` - -It can also perform a lookup for domains with `-d` or `--domain` flags. -```bash -$ investigate -d apple.com +$ investigate -t 95.217.163.246 +$ investigate -t apple.com ``` Finally, it can check a file for a list of IPs or Domains. You may mix types in the file, but they must be 1 per line. @@ -79,7 +75,7 @@ By default, if no platform is specified, the script will run through all of them. ```bash -$ investigate -i 165.254.239.130 -p ipinfo +$ investigate -t 165.254.239.130 -p ipinfo ``` Or ```bash @@ -89,7 +85,7 @@ $ investigate -f IoC_file.txt -p otx shodan #### Example Output ```bash -$ investigate -i 193.34.167.111 +$ investigate -t 193.34.167.111 _________________________________________ Investigating 193.34.167.111: @@ -159,7 +155,7 @@ _________________________________________ --- ```bash -$ investigate -d creditkarma.com +$ investigate -t creditkarma.com __________________________________________________ Investigating Domain "creditkarma.com" @@ -210,7 +206,7 @@ __________________________________________________ --- ```bash -$ investigate -i 165.254.239.130 -p ipinfo robtex +$ investigate -t 165.254.239.130 -p ipinfo robtex _________________________________________ Investigating 165.254.239.130: