import requests import json import time import uuid import re from pathlib import Path # open clusters/ransomware ransompath = Path(__file__).parent.parent.parent / 'clusters' / 'ransomware.json' ransomware_galaxy = ransompath.open("r") ransom_galaxy = json.load(ransomware_galaxy) ransomware_galaxy.close() # get groups names from ransomlook ransomlook_groups = requests.get("https://www.ransomlook.io/api/groups") ransomlook_groups = ransomlook_groups.json() # tracking updated and created clusters updated = [] created = [] # preparing name groups exception management # For now, only seen exceptions are groups with a known synonym in parentheses # ex: "Eraleign (Apt73)" exceptions = [] pattern = re.compile(r'^(.*)\((.*)\)$') for rlookgroup in ransomlook_groups: match = pattern.match(rlookgroup) if match: # Name as registred in ransomlook, first known name, synonym exceptions.append((rlookgroup, match.group(1).strip(), match.group(2).strip())) for rlookgroup in ransomlook_groups: # check if it is an exception true_rlookgroup = rlookgroup synonym = "" if exceptions: for exception in exceptions: if rlookgroup.lower() == exception[0].lower(): rlookgroup = exception[1] synonym = exception[2] break # get data from ransomlook ransom_data = requests.get( "https://www.ransomlook.io/api/group/" + str(true_rlookgroup) ).json() # checking if the cluster exists cluster_exist = False for cluster in ransom_galaxy['values']: if cluster['value'].lower() == rlookgroup.lower(): cluster_exist = True elif 'meta' in cluster: if 'synonyms' in cluster['meta']: for syn in cluster['meta']['synonyms']: if syn.lower() == rlookgroup.lower(): cluster_exist = True # Updating the cluster if existing if cluster_exist == True: if 'description' not in cluster: if ransom_data[0]['meta'] is not None: cluster['description'] = ransom_data[0]['meta'] if 'meta' not in cluster: cluster['meta'] = {} if 'links' not in cluster['meta']: cluster['meta']['links'] = [] if 'locations' in ransom_data[0]: for location in ransom_data[0]['locations']: if location['slug'] not in cluster['meta']['links']: cluster['meta']['links'].append(location['slug']) if synonym: if 'synonyms' not in cluster['meta']: cluster['meta']['synonyms'] = [] cluster['meta']['synonyms'].append(synonym) if 'refs' not in cluster['meta']: cluster['meta']['refs'] = [] if 'profile' in ransom_data[0]: for url in ransom_data[0]['profile']: if url not in cluster['meta']['refs']: cluster['meta']['refs'].append(url) url = "https://www.ransomlook.io/group/" + true_rlookgroup if url not in cluster['meta']['refs']: cluster['meta']['refs'].append(url) if 'uuid' not in cluster: cluster['uuid'] = str( uuid.uuid5( uuid.UUID('10cf658b-5d32-4c4b-bb32-61760a640372'), rlookgroup ) ) break if cluster_exist == True: updated.append(str(rlookgroup)) else: # creating a new cluster created.append(str(rlookgroup)) new_cluster = {} new_cluster['value'] = rlookgroup if ransom_data[0]['meta'] is not None: new_cluster['description'] = ransom_data[0]['meta'] new_cluster['meta'] = {} new_cluster['meta']["links"] = [] if 'locations' in ransom_data[0]: for location in ransom_data[0]['locations']: if location['slug'] not in new_cluster['meta']['links']: new_cluster['meta']["links"].append(location['slug']) if synonym: new_cluster['meta']['synonyms'] = [] new_cluster['meta']['synonyms'].append(synonym) new_cluster['meta']["refs"] = [] url = "https://www.ransomlook.io/group/" + true_rlookgroup if url not in new_cluster['meta']['refs']: new_cluster['meta']['refs'].append(url) if 'profile' in ransom_data[0]: for url in ransom_data[0]['profile']: if url not in new_cluster['meta']['refs']: new_cluster['meta']["refs"].append(url) new_cluster['uuid'] = str( uuid.uuid5(uuid.UUID('10cf658b-5d32-4c4b-bb32-61760a640372'), rlookgroup) ) ransom_galaxy['values'].append(new_cluster) print("\n" + str(len(updated)) + " clusters updated:") print(updated) print("\n" + str(len(created)) + " clusters created:") print(created) print("\nTotal modified :" + str(len(updated) + len(created))) ransom_galaxy['version'] = ransom_galaxy['version'] + 1 tojson = json.dumps(ransom_galaxy, indent=2, ensure_ascii=False) ransomware_galaxy = ransompath.open("w+") ransomware_galaxy.write(tojson) ransomware_galaxy.close()