diff options
-rwxr-xr-x | tor-metrics/generate.py | 1 | ||||
-rw-r--r-- | tor-metrics/relays.py | 42 | ||||
-rw-r--r-- | tor-metrics/templates/contact.html | 11 | ||||
-rw-r--r-- | tor-metrics/templates/relay-info.html | 4 |
4 files changed, 56 insertions, 2 deletions
diff --git a/tor-metrics/generate.py b/tor-metrics/generate.py index e0cb0c6..ae4a748 100755 --- a/tor-metrics/generate.py +++ b/tor-metrics/generate.py @@ -33,6 +33,7 @@ if __name__ == '__main__': RELAY_SET.write_pages_by_key('as') RELAY_SET.write_pages_by_key('country') RELAY_SET.write_pages_by_key('platform') + RELAY_SET.write_pages_by_key('contact') RELAY_SET.write_pages_by_flag() RELAY_SET.write_relay_info() diff --git a/tor-metrics/relays.py b/tor-metrics/relays.py index a64f097..2b79af5 100644 --- a/tor-metrics/relays.py +++ b/tor-metrics/relays.py @@ -5,6 +5,7 @@ Relays class object consisting of relays (list of dict) and onionoo fetch timestamp ''' +import hashlib import json import os import time @@ -18,6 +19,27 @@ ABS_PATH = os.path.dirname(os.path.abspath(__file__)) ENV = Environment(loader=FileSystemLoader(os.path.join(ABS_PATH, 'templates')), trim_blocks=True, lstrip_blocks=True) +def hash_filter(value, hash_type='md5'): + ''' + Custom hash filter for jinja; defaults to "md5" if no type specified + + :param value: value to be hashed + :param hash_type: valid hash type + :return: computed hash as a hexadecimal string + ''' + hash_func = getattr(hashlib, hash_type, None) + + if hash_func: + computed_hash = hash_func(value.encode("utf-8")).hexdigest() + else: + raise AttributeError( + "No hashing function named {hname}".format(hname=hash_type) + ) + + return computed_hash + +ENV.filters['hash'] = hash_filter + class Relays: ''' Relay class consisting of relays (list of dict) and onionoo fetch timestamp @@ -174,6 +196,26 @@ class Relays: else: self.json['sorted']['family'][member]['middle_count'] += 1 + c_str = relay.get('contact', '').encode('utf-8') + c_hash = hashlib.md5(c_str).hexdigest() + if 'contact' not in self.json['sorted']: + self.json['sorted']['contact'] = dict() + if not c_hash in self.json['sorted']['contact']: + self.json['sorted']['contact'][c_hash] = { + 'relays': list(), + 'contact': c_str, + 'bw': 0, + 'exit_count': 0, + 'middle_count': 0 + } + bw = relay['observed_bandwidth'] + self.json['sorted']['contact'][c_hash]['relays'].append(idx) + self.json['sorted']['contact'][c_hash]['bw'] += bw + if 'Exit' in relay['flags']: + self.json['sorted']['contact'][c_hash]['exit_count'] += 1 + else: + self.json['sorted']['contact'][c_hash]['middle_count'] += 1 + def create_output_dir(self): ''' Ensure config:output_root exists (required for write functions) diff --git a/tor-metrics/templates/contact.html b/tor-metrics/templates/contact.html new file mode 100644 index 0000000..10bfd93 --- /dev/null +++ b/tor-metrics/templates/contact.html @@ -0,0 +1,11 @@ +{% extends "relay-list.html" %} +{% if relays.json['relay_subset'][0]['contact'] %} + {% set contact = relays.json['relay_subset'][0]['contact']|escape %} + {% set contact_hash = relays.json['relay_subset'][0]['contact']|hash %} +{% else %} + {% set contact = 'none' %} + {% set contact_hash = ''|hash %} +{% endif %} +{% block title %}Tor Relays :: Contact {{ contact_hash }}{% endblock %} +{% block header %}<a href="../../">Home</a> :: Contact {{ contact_hash }}{% endblock %} +{% block description %}Relays with contact info <code>{{ contact }}</code> are responsible for ~{{ bandwidth }} MB/s of traffic, with {% if middle_count > 0 %}{{ middle_count }} middle relay{% if middle_count > 1 %}s{% endif %}{% if exit_count > 0 %} and {% endif %}{% endif %}{% if exit_count > 0 %}{{ exit_count }} exit relay{% if exit_count > 1 %}s{% endif %}{% endif %}.{% endblock %} diff --git a/tor-metrics/templates/relay-info.html b/tor-metrics/templates/relay-info.html index 2ed50d3..9b8eed1 100644 --- a/tor-metrics/templates/relay-info.html +++ b/tor-metrics/templates/relay-info.html @@ -17,9 +17,9 @@ <dt>Contact</dt> {% if relay['contact'] %} - <dd>{{ relay['contact']|escape }}</dd> + <dd><a href="{{ path_prefix }}contact/{{ relay['contact']|hash }}">{{ relay['contact']|escape }}</a></dd> {% else %} - <dd>none</dd> + <dd><a href="{{ path_prefix }}contact/{{ ''|hash }}">none</a></dd> {% endif %} <dt>Dir Address</dt> |