|
|
@ -29,8 +29,6 @@ module_name = "Sherlock: Find Usernames Across Social Networks"
|
|
|
|
__version__ = "0.14.0"
|
|
|
|
__version__ = "0.14.0"
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
class SherlockFuturesSession(FuturesSession):
|
|
|
|
class SherlockFuturesSession(FuturesSession):
|
|
|
|
def request(self, method, url, hooks={}, *args, **kwargs):
|
|
|
|
def request(self, method, url, hooks={}, *args, **kwargs):
|
|
|
|
"""Request URL.
|
|
|
|
"""Request URL.
|
|
|
@ -191,15 +189,14 @@ def sherlock(username, site_data, query_notify,
|
|
|
|
# Limit number of workers to 20.
|
|
|
|
# Limit number of workers to 20.
|
|
|
|
# This is probably vastly overkill.
|
|
|
|
# This is probably vastly overkill.
|
|
|
|
if len(site_data) >= 20:
|
|
|
|
if len(site_data) >= 20:
|
|
|
|
max_workers=20
|
|
|
|
max_workers = 20
|
|
|
|
else:
|
|
|
|
else:
|
|
|
|
max_workers=len(site_data)
|
|
|
|
max_workers = len(site_data)
|
|
|
|
|
|
|
|
|
|
|
|
# Create multi-threaded session for all requests.
|
|
|
|
# Create multi-threaded session for all requests.
|
|
|
|
session = SherlockFuturesSession(max_workers=max_workers,
|
|
|
|
session = SherlockFuturesSession(max_workers=max_workers,
|
|
|
|
session=underlying_session)
|
|
|
|
session=underlying_session)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
# Results from analysis of all sites
|
|
|
|
# Results from analysis of all sites
|
|
|
|
results_total = {}
|
|
|
|
results_total = {}
|
|
|
|
|
|
|
|
|
|
|
@ -255,7 +252,7 @@ def sherlock(username, site_data, query_notify,
|
|
|
|
elif request_method == "PUT":
|
|
|
|
elif request_method == "PUT":
|
|
|
|
request = session.put
|
|
|
|
request = session.put
|
|
|
|
else:
|
|
|
|
else:
|
|
|
|
raise RuntimeError( f"Unsupported request_method for {url}")
|
|
|
|
raise RuntimeError(f"Unsupported request_method for {url}")
|
|
|
|
|
|
|
|
|
|
|
|
if request_payload is not None:
|
|
|
|
if request_payload is not None:
|
|
|
|
request_payload = interpolate_string(request_payload, username)
|
|
|
|
request_payload = interpolate_string(request_payload, username)
|
|
|
@ -367,13 +364,13 @@ def sherlock(username, site_data, query_notify,
|
|
|
|
# error_flag True denotes no error found in the HTML
|
|
|
|
# error_flag True denotes no error found in the HTML
|
|
|
|
# error_flag False denotes error found in the HTML
|
|
|
|
# error_flag False denotes error found in the HTML
|
|
|
|
error_flag = True
|
|
|
|
error_flag = True
|
|
|
|
errors=net_info.get("errorMsg")
|
|
|
|
errors = net_info.get("errorMsg")
|
|
|
|
# errors will hold the error message
|
|
|
|
# errors will hold the error message
|
|
|
|
# it can be string or list
|
|
|
|
# it can be string or list
|
|
|
|
# by insinstance method we can detect that
|
|
|
|
# by insinstance method we can detect that
|
|
|
|
# and handle the case for strings as normal procedure
|
|
|
|
# and handle the case for strings as normal procedure
|
|
|
|
# and if its list we can iterate the errors
|
|
|
|
# and if its list we can iterate the errors
|
|
|
|
if isinstance(errors,str):
|
|
|
|
if isinstance(errors, str):
|
|
|
|
# Checks if the error message is in the HTML
|
|
|
|
# Checks if the error message is in the HTML
|
|
|
|
# if error is present we will set flag to False
|
|
|
|
# if error is present we will set flag to False
|
|
|
|
if errors in r.text:
|
|
|
|
if errors in r.text:
|
|
|
@ -440,7 +437,6 @@ def sherlock(username, site_data, query_notify,
|
|
|
|
raise ValueError(f"Unknown Error Type '{error_type}' for "
|
|
|
|
raise ValueError(f"Unknown Error Type '{error_type}' for "
|
|
|
|
f"site '{social_network}'")
|
|
|
|
f"site '{social_network}'")
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
# Notify caller about results of query.
|
|
|
|
# Notify caller about results of query.
|
|
|
|
query_notify.update(result)
|
|
|
|
query_notify.update(result)
|
|
|
|
|
|
|
|
|
|
|
@ -481,7 +477,8 @@ def timeout_check(value):
|
|
|
|
except:
|
|
|
|
except:
|
|
|
|
raise ArgumentTypeError(f"Timeout '{value}' must be a number.")
|
|
|
|
raise ArgumentTypeError(f"Timeout '{value}' must be a number.")
|
|
|
|
if timeout <= 0:
|
|
|
|
if timeout <= 0:
|
|
|
|
raise ArgumentTypeError(f"Timeout '{value}' must be greater than 0.0s.")
|
|
|
|
raise ArgumentTypeError(
|
|
|
|
|
|
|
|
f"Timeout '{value}' must be greater than 0.0s.")
|
|
|
|
return timeout
|
|
|
|
return timeout
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
@ -567,7 +564,8 @@ def main():
|
|
|
|
|
|
|
|
|
|
|
|
# Check for newer version of Sherlock. If it exists, let the user know about it
|
|
|
|
# Check for newer version of Sherlock. If it exists, let the user know about it
|
|
|
|
try:
|
|
|
|
try:
|
|
|
|
r = requests.get("https://raw.githubusercontent.com/sherlock-project/sherlock/master/sherlock/sherlock.py")
|
|
|
|
r = requests.get(
|
|
|
|
|
|
|
|
"https://raw.githubusercontent.com/sherlock-project/sherlock/master/sherlock/sherlock.py")
|
|
|
|
|
|
|
|
|
|
|
|
remote_version = str(re.findall('__version__ = "(.*)"', r.text)[0])
|
|
|
|
remote_version = str(re.findall('__version__ = "(.*)"', r.text)[0])
|
|
|
|
local_version = __version__
|
|
|
|
local_version = __version__
|
|
|
@ -579,7 +577,6 @@ def main():
|
|
|
|
except Exception as error:
|
|
|
|
except Exception as error:
|
|
|
|
print(f"A problem occurred while checking for an update: {error}")
|
|
|
|
print(f"A problem occurred while checking for an update: {error}")
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
# Argument check
|
|
|
|
# Argument check
|
|
|
|
# TODO regex check on args.proxy
|
|
|
|
# TODO regex check on args.proxy
|
|
|
|
if args.tor and (args.proxy is not None):
|
|
|
|
if args.tor and (args.proxy is not None):
|
|
|
@ -610,11 +607,11 @@ def main():
|
|
|
|
print("You can only use --output with a single username")
|
|
|
|
print("You can only use --output with a single username")
|
|
|
|
sys.exit(1)
|
|
|
|
sys.exit(1)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
# Create object with all information about sites we are aware of.
|
|
|
|
# Create object with all information about sites we are aware of.
|
|
|
|
try:
|
|
|
|
try:
|
|
|
|
if args.local:
|
|
|
|
if args.local:
|
|
|
|
sites = SitesInformation(os.path.join(os.path.dirname(__file__), "resources/data.json"))
|
|
|
|
sites = SitesInformation(os.path.join(
|
|
|
|
|
|
|
|
os.path.dirname(__file__), "resources/data.json"))
|
|
|
|
else:
|
|
|
|
else:
|
|
|
|
sites = SitesInformation(args.json_file)
|
|
|
|
sites = SitesInformation(args.json_file)
|
|
|
|
except Exception as error:
|
|
|
|
except Exception as error:
|
|
|
@ -648,7 +645,8 @@ def main():
|
|
|
|
site_missing.append(f"'{site}'")
|
|
|
|
site_missing.append(f"'{site}'")
|
|
|
|
|
|
|
|
|
|
|
|
if site_missing:
|
|
|
|
if site_missing:
|
|
|
|
print(f"Error: Desired sites not found: {', '.join(site_missing)}.")
|
|
|
|
print(
|
|
|
|
|
|
|
|
f"Error: Desired sites not found: {', '.join(site_missing)}.")
|
|
|
|
|
|
|
|
|
|
|
|
if not site_data:
|
|
|
|
if not site_data:
|
|
|
|
sys.exit(1)
|
|
|
|
sys.exit(1)
|
|
|
@ -685,7 +683,8 @@ def main():
|
|
|
|
if dictionary.get("status").status == QueryStatus.CLAIMED:
|
|
|
|
if dictionary.get("status").status == QueryStatus.CLAIMED:
|
|
|
|
exists_counter += 1
|
|
|
|
exists_counter += 1
|
|
|
|
file.write(dictionary["url_user"] + "\n")
|
|
|
|
file.write(dictionary["url_user"] + "\n")
|
|
|
|
file.write(f"Total Websites Username Detected On : {exists_counter}\n")
|
|
|
|
file.write(
|
|
|
|
|
|
|
|
f"Total Websites Username Detected On : {exists_counter}\n")
|
|
|
|
|
|
|
|
|
|
|
|
if args.csv:
|
|
|
|
if args.csv:
|
|
|
|
result_file = f"{username}.csv"
|
|
|
|
result_file = f"{username}.csv"
|
|
|
|