[tor-commits] [atlas/master] Add five graphs per relay showing path-selection weights.

art at torproject.org art at torproject.org
Thu Aug 23 10:08:58 UTC 2012


commit 0829e9fc7258f0380359c15e7801a8861670ca37
Author: Karsten Loesing <karsten.loesing at gmx.net>
Date:   Thu Aug 23 09:14:54 2012 +0200

    Add five graphs per relay showing path-selection weights.
    
    Implements #5755.
---
 js/models/graph.js          |  156 ++++++++++++++++++++++++++++++++++++++-----
 js/views/details/main.js    |   91 +++++++++++++++++++++++--
 run.py                      |    2 +-
 templates/details/main.html |  109 +++++++++++++++++++++++++++---
 4 files changed, 320 insertions(+), 38 deletions(-)

diff --git a/js/models/graph.js b/js/models/graph.js
index a121722..a3c5d37 100644
--- a/js/models/graph.js
+++ b/js/models/graph.js
@@ -9,25 +9,30 @@ define([
         baseurl: 'https://onionoo.torproject.org',
         initialize: function() {
         this.set({
-            days: {write: [], read: []},
-            week: {write: [], read: []},
-            month: {write: [], read: []},
-            months: {write: [], read: []},
-            year: {write: [], read: []},
-            years: {write: [], read: []}
+            bw_days: {write: [], read: []},
+            bw_week: {write: [], read: []},
+            bw_month: {write: [], read: []},
+            bw_months: {write: [], read: []},
+            bw_year: {write: [], read: []},
+            bw_years: {write: [], read: []},
+            weights_week: {advbw: [], cw: [], guard: [], exit: []},
+            weights_month: {advbw: [], cw: [], guard: [], exit: []},
+            weights_months: {advbw: [], cw: [], guard: [], exit: []},
+            weights_year: {advbw: [], cw: [], guard: [], exit: []},
+            weights_years: {advbw: [], cw: [], guard: [], exit: []}
             });
         },
-        lookup: function(fingerprint, options) {
+        lookup_bw: function(fingerprint, options) {
             var model = this;
             var success = options.success;
             // Clear the model
             this.set({
-                days: {write: [], read: []},
-                week: {write: [], read: []},
-                month: {write: [], read: []},
-                months: {write: [], read: []},
-                year: {write: [], read: []},
-                years: {write: [], read: []}
+                bw_days: {write: [], read: []},
+                bw_week: {write: [], read: []},
+                bw_month: {write: [], read: []},
+                bw_months: {write: [], read: []},
+                bw_year: {write: [], read: []},
+                bw_years: {write: [], read: []}
             });
 
             $.getJSON(this.baseurl+'/bandwidth?lookup='+fingerprint, function(data) {
@@ -35,8 +40,7 @@ define([
                 success(model, data);
             });
         },
-
-        parsebwdata: function(data) {
+        parse_bw_data: function(data) {
             var model = this;
             var relay = data.relays[0];
             this.fingerprint = relay.fingerprint;
@@ -63,7 +67,7 @@ define([
                     // funky way of setting and getting attributes in
                     // models.
                     // XXX probably want to refactor.
-                    var mperiod = period.split("_")[1]
+                    var mperiod = "bw_" + period.split("_")[1]
                     var newar = model.get(mperiod).write;
                     newar.push([y,x]);
                     var toset = {mperiod: {write: newar}};
@@ -85,13 +89,131 @@ define([
                     if (value != null) {
                         x = value*history[period].factor;
                     }
-                    var mperiod = period.split("_")[1]
+                    var mperiod = "bw_" + period.split("_")[1]
                     var newar = model.get(mperiod).read;
                     newar.push([y,x]);
                     var toset = {mperiod: {read: newar}};
                     model.set(toset);
                 });
             });
+        },
+        lookup_weights: function(fingerprint, options) {
+            var model = this;
+            var success = options.success;
+            // Clear the model
+            this.set({
+                weights_week: {advbw: [], cw: [], guard: [], exit: []},
+                weights_month: {advbw: [], cw: [], guard: [], exit: []},
+                weights_months: {advbw: [], cw: [], guard: [], exit: []},
+                weights_year: {advbw: [], cw: [], guard: [], exit: []},
+                weights_years: {advbw: [], cw: [], guard: [], exit: []}
+            });
+
+            $.getJSON(this.baseurl+'/weights?lookup='+fingerprint, function(data) {
+                model.data = data;
+                success(model, data);
+            });
+        },
+        parse_weights_data: function(data) {
+            var model = this;
+            var relay = data.relays[0];
+            this.fingerprint = relay.fingerprint;
+
+            if ("advertised_bandwidth_fraction" in relay) {
+                var history = relay.advertised_bandwidth_fraction;
+                _.each(_.keys(relay.advertised_bandwidth_fraction), function(period, i) {
+                    var first = history[period].first.split(' ');
+                    var date = first[0].split('-');
+                    var time = first[1].split(':');
+                    first = new Date(date[0], date[1]-1, date[2],
+                                    time[0], time[1], time[2]);
+                    var y = first.getTime();
+                    _.each(history[period].values, function(value, i) {
+                        y += history[period].interval*1000;
+                        var x = null
+                        if (value != null) {
+                            x = value*history[period].factor;
+                        }
+                        var mperiod = "weights_" + period.split("_")[1]
+                        var newar = model.get(mperiod).advbw;
+                        newar.push([y,x]);
+                        var toset = {mperiod: {advbw: newar}};
+                        model.set(toset);
+                    });
+                });
+            }
+
+            if ("consensus_weight_fraction" in relay) {
+                var history = relay.consensus_weight_fraction;
+                _.each(_.keys(relay.consensus_weight_fraction), function(period, i) {
+                    var first = history[period].first.split(' ');
+                    var date = first[0].split('-');
+                    var time = first[1].split(':');
+                    first = new Date(date[0], date[1]-1, date[2],
+                                    time[0], time[1], time[2]);
+                    var y = first.getTime();
+                    _.each(history[period].values, function(value, i) {
+                        y += history[period].interval*1000;
+                        var x = null
+                        if (value != null) {
+                            x = value*history[period].factor;
+                        }
+                        var mperiod = "weights_" + period.split("_")[1]
+                        var newar = model.get(mperiod).cw;
+                        newar.push([y,x]);
+                        var toset = {mperiod: {cw: newar}};
+                        model.set(toset);
+                    });
+                });
+            }
+
+            if ("guard_probability" in relay) {
+                var history = relay.guard_probability;
+                _.each(_.keys(relay.guard_probability), function(period, i) {
+                    var first = history[period].first.split(' ');
+                    var date = first[0].split('-');
+                    var time = first[1].split(':');
+                    first = new Date(date[0], date[1]-1, date[2],
+                                    time[0], time[1], time[2]);
+                    var y = first.getTime();
+                    _.each(history[period].values, function(value, i) {
+                        y += history[period].interval*1000;
+                        var x = null
+                        if (value != null) {
+                            x = value*history[period].factor;
+                        }
+                        var mperiod = "weights_" + period.split("_")[1]
+                        var newar = model.get(mperiod).guard;
+                        newar.push([y,x]);
+                        var toset = {mperiod: {guard: newar}};
+                        model.set(toset);
+                    });
+                });
+            }
+
+            if ("exit_probability" in relay) {
+                var history = relay.exit_probability;
+                _.each(_.keys(relay.exit_probability), function(period, i) {
+                    var first = history[period].first.split(' ');
+                    var date = first[0].split('-');
+                    var time = first[1].split(':');
+                    first = new Date(date[0], date[1]-1, date[2],
+                                    time[0], time[1], time[2]);
+                    var y = first.getTime();
+                    _.each(history[period].values, function(value, i) {
+                        y += history[period].interval*1000;
+                        var x = null
+                        if (value != null) {
+                            x = value*history[period].factor;
+                        }
+                        var mperiod = "weights_" + period.split("_")[1]
+                        var newar = model.get(mperiod).exit;
+                        newar.push([y,x]);
+                        var toset = {mperiod: {exit: newar}};
+                        model.set(toset);
+                    });
+                });
+            }
         }
     })
     return graphModel;
diff --git a/js/views/details/main.js b/js/views/details/main.js
index 64698c7..e09da3e 100644
--- a/js/views/details/main.js
+++ b/js/views/details/main.js
@@ -28,10 +28,10 @@ define([
             var compiledTemplate = _.template(mainDetailsTemplate, data);
             this.el.html(compiledTemplate);
             var graph = this.graph;
-            this.graph.lookup(this.model.fingerprint, {
+            this.graph.lookup_bw(this.model.fingerprint, {
                 success: function() {
-                    graph.parsebwdata(graph.data);
-                    //console.log(graph.get('days').write);
+                    graph.parse_bw_data(graph.data);
+                    //console.log(graph.get('bw_days').write);
                     function showTooltip(x, y, contents) {
                         $('<div id="graphtooltip">' + contents + '</div>').css( {
                             position: 'absolute',
@@ -44,8 +44,8 @@ define([
                             opacity: 0.80
                         }).appendTo("body").fadeIn(200);
                     }
-                    graphs = ['days', 'week', 'month',
-                            'months', 'year', 'years'];
+                    graphs = ['bw_days', 'bw_week', 'bw_month',
+                            'bw_months', 'bw_year', 'bw_years'];
                     _.each(graphs, function(g) {
                         var plot_data = [{data: graph.get(g).write, label: 'write'},
                                          {data: graph.get(g).read, label: 'read'}];
@@ -59,11 +59,11 @@ define([
                                 xaxis: {mode: 'time', tickLength: 5},
                                 yaxis: {tickFormatter : function suffixFormatter(val, axis) {
                                 if (val > 1000000)
-                                   return (val / 1000000).toFixed(axis.tickDecimals) + " MB/s";
+                                   return (val / 1000000).toFixed(2) + " MB/s";
                                 else if (val > 1000)
-                                   return (val / 1000).toFixed(axis.tickDecimals) + " KB/s";
+                                   return (val / 1000).toFixed(2) + " KB/s";
                                 else
-                                   return val.toFixed(axis.tickDecimals) + " B/s";
+                                   return val.toFixed(2) + " B/s";
                                 }},
                         });
                         $("#"+g).resize();
@@ -105,6 +105,81 @@ define([
                 $(this).children(".tooltip").hide();
 
             });
+
+            this.graph.lookup_weights(this.model.fingerprint, {
+                success: function() {
+                    graph.parse_weights_data(graph.data);
+                    //console.log(graph.get('weights_week').write);
+                    function showTooltip(x, y, contents) {
+                        $('<div id="graphtooltip">' + contents + '</div>').css( {
+                            position: 'absolute',
+                            display: 'none',
+                            top: y - 25,
+                            left: x + 5,
+                            border: '1px solid #fdd',
+                            padding: '2px',
+                            'background-color': '#fee',
+                            opacity: 0.80
+                        }).appendTo("body").fadeIn(200);
+                    }
+                    graphs = ['weights_week', 'weights_month',
+                            'weights_months', 'weights_year', 'weights_years'];
+                    _.each(graphs, function(g) {
+                        var plot_data = [{data: graph.get(g).advbw, label: 'advertised bandwidth fraction'},
+                                         {data: graph.get(g).cw, label: 'consensus weight fraction'},
+                                         {data: graph.get(g).guard, label: 'guard probability'},
+                                         {data: graph.get(g).exit, label: 'exit probability'}];
+                        $.plot($("#"+g),
+                            plot_data, {
+                                series: {
+                                    lines: {show: true},
+                                    points: {show: true},
+                                    },
+                                grid: { hoverable: true, clickable: true },
+                                xaxis: {mode: 'time', tickLength: 5},
+                                yaxis: {tickFormatter : function suffixFormatter(val, axis) {
+                                   return (val * 100).toFixed(axis.tickDecimals) + " %";
+                                }},
+                        });
+                        $("#"+g).resize();
+
+
+                        $("#save_"+g).attr('href', Canvas2Image.saveAsPNG($("#"+g+" > canvas.base")[0], false));
+
+                        var previousItem = null;
+                        $("#"+g).bind("plothover", function (event, pos, item){
+                            if (item) {
+                                if (previousItem != item.dataIndex) {
+                                    previousItem = item.dataIndex;
+
+                                    $("#graphtooltip").remove();
+                                    var x = item.datapoint[0].toFixed(2),
+                                        y = item.datapoint[1].toFixed(2);
+                                    var weight = (100 * item.datapoint[1]).toFixed(3) + " %";
+                                    showTooltip(item.pageX, item.pageY,
+                                                weight);
+
+                                }
+                            } else {
+                                $("#graphtooltip").remove();
+                                previousItem = null;
+                            }
+                        });
+                    });
+                }
+            });
+
+            $("#loading").hide();
+            $(".flag .tooltip").hide();
+            $(".tip").popover();
+            $(".flag").hover(function(){
+                $(this).children(".tooltip").show();
+
+            }, function(e){
+
+                $(this).children(".tooltip").hide();
+
+            });
         }
     });
     return new mainDetailsView;
diff --git a/run.py b/run.py
index 4292c66..2ab45f1 100644
--- a/run.py
+++ b/run.py
@@ -101,5 +101,5 @@ rest_api = [(r"/(.*)", LongStatic, {"path": "./"})]
 if __name__ == "__main__":
     application = web.Application(rest_api)
     application.listen(8888)
-    print "Running on http://127.0.0.1:8888/index.html"
+    print "Running on http://192.168.178.31:8888/index.html"
     ioloop.IOLoop.instance().start()
diff --git a/templates/details/main.html b/templates/details/main.html
index 7a16f59..4a82e30 100644
--- a/templates/details/main.html
+++ b/templates/details/main.html
@@ -89,12 +89,12 @@
     <ul class="thumbnails">
         <li class="span8">
           <div class="thumbnail">
-            <div id="days" class="graph">
+            <div id="bw_days" class="graph">
             <img src="img/no-data-available.png" alt="">
             </div>
             <div class="caption">
               <h5>3 Days graph</h5>
-              <a id="save_days" href="">Save Graph</a>
+              <a id="save_bw_days" href="">Save Graph</a>
             </div>
           </div>
           </li>
@@ -104,12 +104,12 @@
         <li class="span8">
           <div class="thumbnail">
 
-            <div id="week" class="graph">
+            <div id="bw_week" class="graph">
             <img src="img/no-data-available.png" alt="">
             </div>
             <div class="caption">
               <h5>1 Week graph</h5>
-              <a id="save_week" href="">Save Graph</a>
+              <a id="save_bw_week" href="">Save Graph</a>
             </div>
           </div>
         </li>
@@ -120,12 +120,12 @@
     <ul class="thumbnails">
         <li class="span8">
           <div class="thumbnail">
-            <div id="month" class="graph">
+            <div id="bw_month" class="graph">
             <img src="img/no-data-available.png" alt="">
             </div>
             <div class="caption">
               <h5>1 Month graph</h5>
-              <a id="save_month" href="">Save Graph</a>
+              <a id="save_bw_month" href="">Save Graph</a>
             </div>
           </div>
           </li>
@@ -136,12 +136,12 @@
         <li class="span8">
           <div class="thumbnail">
 
-            <div id="months" class="graph">
+            <div id="bw_months" class="graph">
             <img src="img/no-data-available.png" alt="">
             </div>
             <div class="caption">
               <h5>3 Months graph</h5>
-              <a id="save_months" href="">Save Graph</a>
+              <a id="save_bw_months" href="">Save Graph</a>
             </div>
           </div>
         </li>
@@ -152,12 +152,12 @@
     <ul class="thumbnails">
         <li class="span8">
           <div class="thumbnail">
-            <div id="year" class="graph">
+            <div id="bw_year" class="graph">
             <img src="img/no-data-available.png" alt="">
             </div>
             <div class="caption">
               <h5>1 Year graph</h5>
-              <a id="save_year" href="">Save Graph</a>
+              <a id="save_bw_year" href="">Save Graph</a>
             </div>
           </div>
           </li>
@@ -167,13 +167,98 @@
         <ul class="thumbnails">
         <li class="span8">
           <div class="thumbnail">
-            <div id="years" class="graph">
+            <div id="bw_years" class="graph">
             <img src="img/no-data-available.png" alt="">
             </div>
 
            <div class="caption">
               <h5>5 Years graph</h5>
-              <a id="save_years" href="">Save Graph</a>
+              <a id="save_bw_years" href="">Save Graph</a>
+            </div>
+          </div>
+        </li>
+      </ul>
+</div>
+
+<div class="row">
+        <ul class="thumbnails">
+        <li class="span8">
+          <div class="thumbnail">
+            <div id="weights_week" class="graph">
+            <img src="img/no-data-available.png" alt="">
+            </div>
+
+           <div class="caption">
+              <h5>1 Week graph</h5>
+              <a id="save_weights_week" href="">Save Graph</a>
+            </div>
+          </div>
+        </li>
+      </ul>
+</div>
+
+<div class="row">
+        <ul class="thumbnails">
+        <li class="span8">
+          <div class="thumbnail">
+            <div id="weights_month" class="graph">
+            <img src="img/no-data-available.png" alt="">
+            </div>
+
+           <div class="caption">
+              <h5>1 Month graph</h5>
+              <a id="save_weights_month" href="">Save Graph</a>
+            </div>
+          </div>
+        </li>
+      </ul>
+</div>
+
+<div class="row">
+        <ul class="thumbnails">
+        <li class="span8">
+          <div class="thumbnail">
+            <div id="weights_months" class="graph">
+            <img src="img/no-data-available.png" alt="">
+            </div>
+
+           <div class="caption">
+              <h5>3 Months graph</h5>
+              <a id="save_weights_months" href="">Save Graph</a>
+            </div>
+          </div>
+        </li>
+      </ul>
+</div>
+
+<div class="row">
+        <ul class="thumbnails">
+        <li class="span8">
+          <div class="thumbnail">
+            <div id="weights_year" class="graph">
+            <img src="img/no-data-available.png" alt="">
+            </div>
+
+           <div class="caption">
+              <h5>1 Year graph</h5>
+              <a id="save_weights_year" href="">Save Graph</a>
+            </div>
+          </div>
+        </li>
+      </ul>
+</div>
+
+<div class="row">
+        <ul class="thumbnails">
+        <li class="span8">
+          <div class="thumbnail">
+            <div id="weights_years" class="graph">
+            <img src="img/no-data-available.png" alt="">
+            </div>
+
+           <div class="caption">
+              <h5>5 Years graph</h5>
+              <a id="save_weights_years" href="">Save Graph</a>
             </div>
           </div>
         </li>





More information about the tor-commits mailing list