[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]

[or-cvs] [ernie/master 2/8] Keep presented graphs up to date automatically.



Author: Kevin Berry <xckjb88@xxxxxxxxx>
Date: Thu, 1 Jul 2010 01:46:21 -0400
Subject: Keep presented graphs up to date automatically.
Commit: a87bb2b7b4860dff8a4014fc91c54351e51f245a

I implemented some of the servlet logic to keep the presented
graph menus up to date so they don't have to be changed
manually.
---
 .../WEB-INF/templates/graphs_bridge-users.tpl.jsp  |  192 ++++++--------------
 .../WEB-INF/templates/graphs_exit-relays.tpl.jsp   |  100 ++++++-----
 .../WEB-INF/templates/graphs_network-size.tpl.jsp  |  119 +++++++------
 3 files changed, 180 insertions(+), 231 deletions(-)

diff --git a/jsp/war/WEB-INF/templates/graphs_bridge-users.tpl.jsp b/jsp/war/WEB-INF/templates/graphs_bridge-users.tpl.jsp
index 9c3a565..724d3c8 100644
--- a/jsp/war/WEB-INF/templates/graphs_bridge-users.tpl.jsp
+++ b/jsp/war/WEB-INF/templates/graphs_bridge-users.tpl.jsp
@@ -1,135 +1,59 @@
+<%@page import="java.io.*" %>
+<%@page import="java.util.*" %>
 <div>
-  <h2>Tor Metrics Portal: Graphs</h2>
-  <br/>
-  <h3>Tor users via bridges</h3>
-  <br/>
-  <p>Users who cannot connect directly to the Tor network instead
-  connect via bridges, which are non-public relays. The following
-  graphs display an estimate of Tor users via bridges based on the
-  unique IP addresses as seen by a few hundred bridges.</p>
-  <ul>
-    <li><a href="#bahrain">Bahrain</a></li>
-    <li><a href="#china">China</a></li>
-    <li><a href="#cuba">Cuba</a></li>
-    <li><a href="#ethiopia">Ethiopia</a></li>
-    <li><a href="#iran">Iran</a></li>
-    <li><a href="#burma">Burma</a></li>
-    <li><a href="#saudi">Saudi</a></li>
-    <li><a href="#syria">Syria</a></li>
-    <li><a href="#tunisia">Tunisia</a></li>
-    <li><a href="#turkmenistan">Turkmenistan</a></li>
-    <li><a href="#uzbekistan">Uzbekistan</a></li>
-    <li><a href="#vietnam">Vietnam</a></li>
-    <li><a href="#yemen">Yemen</a></li>
-  </ul>
-  <ul>
-    <li><a href="csv/bridge-users.csv">CSV</a> file containing all
-    data.</li>
-    <li><a href="csv/monthly-users-peak.csv">CSV</a> file containing peak daily Tor users (recurring and bridge) per month by country.</li>
-    <li><a href="csv/monthly-users-average.csv">CSV</a> file containing average daily Tor users (recurring and bridge) per month by country.</li>
-    </ul>        <p><a id="bahrain"/>
-    <img src="graphs/bridge-users/bahrain-bridges-30d.png"/>
-    <img src="graphs/bridge-users/bahrain-bridges-90d.png"/>
-    <img src="graphs/bridge-users/bahrain-bridges-180d.png"/>
-    <img src="graphs/bridge-users/bahrain-bridges-all.png"/>
-    <img src="graphs/bridge-users/bahrain-bridges-2010.png"/>
-    <img src="graphs/bridge-users/bahrain-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/bahrain-bridges-2010-06.png"/>
-    </p><p><a id="china"/>
-    <img src="graphs/bridge-users/china-bridges-30d.png"/>
-    <img src="graphs/bridge-users/china-bridges-90d.png"/>
-    <img src="graphs/bridge-users/china-bridges-180d.png"/>
-    <img src="graphs/bridge-users/china-bridges-all.png"/>
-    <img src="graphs/bridge-users/china-bridges-2010.png"/>
-    <img src="graphs/bridge-users/china-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/china-bridges-2010-06.png"/>
-    </p><p><a id="cuba"/>
-    <img src="graphs/bridge-users/cuba-bridges-30d.png"/>
-    <img src="graphs/bridge-users/cuba-bridges-90d.png"/>
-    <img src="graphs/bridge-users/cuba-bridges-180d.png"/>
-    <img src="graphs/bridge-users/cuba-bridges-all.png"/>
-    <img src="graphs/bridge-users/cuba-bridges-2010.png"/>
-    <img src="graphs/bridge-users/cuba-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/cuba-bridges-2010-06.png"/>
-    </p><p><a id="ethiopia"/>
-    <img src="graphs/bridge-users/ethiopia-bridges-30d.png"/>
-    <img src="graphs/bridge-users/ethiopia-bridges-90d.png"/>
-    <img src="graphs/bridge-users/ethiopia-bridges-180d.png"/>
-    <img src="graphs/bridge-users/ethiopia-bridges-all.png"/>
-    <img src="graphs/bridge-users/ethiopia-bridges-2010.png"/>
-    <img src="graphs/bridge-users/ethiopia-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/ethiopia-bridges-2010-06.png"/>
-    </p><p><a id="iran"/>
-    <img src="graphs/bridge-users/iran-bridges-30d.png"/>
-    <img src="graphs/bridge-users/iran-bridges-90d.png"/>
-    <img src="graphs/bridge-users/iran-bridges-180d.png"/>
-    <img src="graphs/bridge-users/iran-bridges-all.png"/>
-    <img src="graphs/bridge-users/iran-bridges-2010.png"/>
-    <img src="graphs/bridge-users/iran-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/iran-bridges-2010-06.png"/>
-    </p><p><a id="burma"/>
-    <img src="graphs/bridge-users/burma-bridges-30d.png"/>
-    <img src="graphs/bridge-users/burma-bridges-90d.png"/>
-    <img src="graphs/bridge-users/burma-bridges-180d.png"/>
-    <img src="graphs/bridge-users/burma-bridges-all.png"/>
-    <img src="graphs/bridge-users/burma-bridges-2010.png"/>
-    <img src="graphs/bridge-users/burma-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/burma-bridges-2010-06.png"/>
-    </p><p><a id="saudi"/>
-    <img src="graphs/bridge-users/saudi-bridges-30d.png"/>
-    <img src="graphs/bridge-users/saudi-bridges-90d.png"/>
-    <img src="graphs/bridge-users/saudi-bridges-180d.png"/>
-    <img src="graphs/bridge-users/saudi-bridges-all.png"/>
-    <img src="graphs/bridge-users/saudi-bridges-2010.png"/>
-    <img src="graphs/bridge-users/saudi-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/saudi-bridges-2010-06.png"/>
-    </p><p><a id="syria"/>
-    <img src="graphs/bridge-users/syria-bridges-30d.png"/>
-    <img src="graphs/bridge-users/syria-bridges-90d.png"/>
-    <img src="graphs/bridge-users/syria-bridges-180d.png"/>
-    <img src="graphs/bridge-users/syria-bridges-all.png"/>
-    <img src="graphs/bridge-users/syria-bridges-2010.png"/>
-    <img src="graphs/bridge-users/syria-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/syria-bridges-2010-06.png"/>
-    </p><p><a id="tunisia"/>
-    <img src="graphs/bridge-users/tunisia-bridges-30d.png"/>
-    <img src="graphs/bridge-users/tunisia-bridges-90d.png"/>
-    <img src="graphs/bridge-users/tunisia-bridges-180d.png"/>
-    <img src="graphs/bridge-users/tunisia-bridges-all.png"/>
-    <img src="graphs/bridge-users/tunisia-bridges-2010.png"/>
-    <img src="graphs/bridge-users/tunisia-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/tunisia-bridges-2010-06.png"/>
-    </p><p><a id="turkmenistan"/>
-    <img src="graphs/bridge-users/turkmenistan-bridges-30d.png"/>
-    <img src="graphs/bridge-users/turkmenistan-bridges-90d.png"/>
-    <img src="graphs/bridge-users/turkmenistan-bridges-180d.png"/>
-    <img src="graphs/bridge-users/turkmenistan-bridges-all.png"/>
-    <img src="graphs/bridge-users/turkmenistan-bridges-2010.png"/>
-    <img src="graphs/bridge-users/turkmenistan-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/turkmenistan-bridges-2010-06.png"/>
-    </p><p><a id="uzbekistan"/>
-    <img src="graphs/bridge-users/uzbekistan-bridges-30d.png"/>
-    <img src="graphs/bridge-users/uzbekistan-bridges-90d.png"/>
-    <img src="graphs/bridge-users/uzbekistan-bridges-180d.png"/>
-    <img src="graphs/bridge-users/uzbekistan-bridges-all.png"/>
-    <img src="graphs/bridge-users/uzbekistan-bridges-2010.png"/>
-    <img src="graphs/bridge-users/uzbekistan-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/uzbekistan-bridges-2010-06.png"/>
-    </p><p><a id="vietnam"/>
-    <img src="graphs/bridge-users/vietnam-bridges-30d.png"/>
-    <img src="graphs/bridge-users/vietnam-bridges-90d.png"/>
-    <img src="graphs/bridge-users/vietnam-bridges-180d.png"/>
-    <img src="graphs/bridge-users/vietnam-bridges-all.png"/>
-    <img src="graphs/bridge-users/vietnam-bridges-2010.png"/>
-    <img src="graphs/bridge-users/vietnam-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/vietnam-bridges-2010-06.png"/>
-    </p><p><a id="yemen"/>
-    <img src="graphs/bridge-users/yemen-bridges-30d.png"/>
-    <img src="graphs/bridge-users/yemen-bridges-90d.png"/>
-    <img src="graphs/bridge-users/yemen-bridges-180d.png"/>
-    <img src="graphs/bridge-users/yemen-bridges-all.png"/>
-    <img src="graphs/bridge-users/yemen-bridges-2010.png"/>
-    <img src="graphs/bridge-users/yemen-bridges-2010-q2.png"/>
-    <img src="graphs/bridge-users/yemen-bridges-2010-06.png"/>
-    </p><br/>
-  </div>
+<%
+        out.print( "        <h2>Tor Metrics Portal: Graphs</h2>\n"
+        + "        <br/>\n"
+        + "        <h3>Tor users via bridges</h3>\n"
+        + "        <br/>\n"
+        + "        <p>Users who cannot connect directly to the Tor network instead\n"
+        + "        connect via bridges, which are non-public relays. The following\n"
+        + "        graphs display an estimate of Tor users via bridges based on the\n"
+        + "        unique IP addresses as seen by a few hundred bridges.</p>\n"
+        + "        <ul>\n"
+        + "          <li><a href=\"#bahrain\">Bahrain</a></li>\n"
+        + "          <li><a href=\"#china\">China</a></li>\n"
+        + "          <li><a href=\"#cuba\">Cuba</a></li>\n"
+        + "          <li><a href=\"#ethiopia\">Ethiopia</a></li>\n"
+        + "          <li><a href=\"#iran\">Iran</a></li>\n"
+        + "          <li><a href=\"#burma\">Burma</a></li>\n"
+        + "          <li><a href=\"#saudi\">Saudi</a></li>\n"
+        + "          <li><a href=\"#syria\">Syria</a></li>\n"
+        + "          <li><a href=\"#tunisia\">Tunisia</a></li>\n"
+        + "          <li><a href=\"#turkmenistan\">Turkmenistan</a></li>\n"
+        + "          <li><a href=\"#uzbekistan\">Uzbekistan</a></li>\n"
+        + "          <li><a href=\"#vietnam\">Vietnam</a></li>\n"
+        + "          <li><a href=\"#yemen\">Yemen</a></li>\n"
+        + "        </ul>\n"
+        + "        <ul>\n"
+        + "          <li><a href=\"csv/bridge-users.csv\">CSV</a> file containing all\n"
+        + "             data.</li>\n"
+        + "          <li><a href=\"csv/monthly-users-peak.csv\">CSV</a> "
+          + "file containing peak daily Tor users (recurring and bridge) "
+          + "per month by country.</li>\n"
+        + "          <li><a href=\"csv/monthly-users-average.csv\">"
+          + "CSV</a> file containing average daily Tor users (recurring "
+          + "and bridge) per month by country.</li>\n"
+        + "        </ul>"
+        + "        ");
+    List<String> countries = Arrays.asList((
+        "bahrain,china,cuba,ethiopia,iran,burma,saudi,syria,tunisia,"
+        + "turkmenistan,uzbekistan,vietnam,yemen").split(","));
+    List<String> suffixes = new ArrayList<String>(Arrays.asList(
+        "30d,90d,180d,all".split(",")));
+    Calendar now = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
+    suffixes.add(String.format("%tY", now));
+    suffixes.add(String.format("%1$tY-q%2$d", now,
+        1 + now.get(Calendar.MONTH) / 3));
+    suffixes.add(String.format("%1$tY-%1$tm", now));
+    for (String country : countries) {
+      out.print("<p><a id=\"" + country + "\"/>\n");
+      for (String suffix : suffixes) {
+        out.print("        <img src=\"graphs/bridge-users/" + country
+            + "-bridges-" + suffix + ".png\"/>\n");
+      }
+      out.print("        </p>");
+    }
+    out.print("<br/>\n");
+%>
+</div>
diff --git a/jsp/war/WEB-INF/templates/graphs_exit-relays.tpl.jsp b/jsp/war/WEB-INF/templates/graphs_exit-relays.tpl.jsp
index 407af83..98474b0 100644
--- a/jsp/war/WEB-INF/templates/graphs_exit-relays.tpl.jsp
+++ b/jsp/war/WEB-INF/templates/graphs_exit-relays.tpl.jsp
@@ -1,45 +1,59 @@
+<%@page import="java.io.*" %>
+<%@page import="java.util.*" %>
 <div>
-  <h2>Tor Metrics Portal: Graphs</h2>
-  <br/>
-  <h3>Exit relays in the Tor network</h3>
-  <br/>
-  <p>The number of exit relays in the Tor network can be extracted from
-  the hourly published network status consensuses.</p>
-  <ul>
-    <li>Past <a href="#exit-72h">72 hours</a> up to
-    now</li>
-    <li>Past <a href="#exit-30d">30</a>,
-    <a href="#exit-90d">90</a>,
-    <a href="#exit-180d">180</a> days</li>
-    <li><a href="#exit-all">All data</a> up to today</li>
-    <li>Annual graphs of
-    <a href="#exit-2010">2010</a>,
-    <a href="#exit-2009">2009</a>,
-    <a href="#exit-2008">2008</a>,
-    <a href="#exit-2007">2007</a>,
-    <a href="#exit-2006">2006</a></li>
-    <li>Quarterly graphs of
-    <a href="#exit-2010-q2">Q2 2010</a>,
-    <a href="#exit-2010-q1">Q1 2010</a></li>
-    <li>Monthly graphs of
-    <a href="#exit-2010-06">Jun 2010</a>,
-    <a href="#exit-2010-05">May 2010</a></li>
-    <li><a href="csv/exit.csv">CSV</a> file
-    containing raw data</li>
-  </ul>
-  </p><p><a id="exit-72h"/><img src="graphs/exit/exit-72h.png"/>
-  </p><p><a id="exit-30d"/><img src="graphs/exit/exit-30d.png"/>
-  </p><p><a id="exit-90d"/><img src="graphs/exit/exit-90d.png"/>
-  </p><p><a id="exit-180d"/><img src="graphs/exit/exit-180d.png"/>
-  </p><p><a id="exit-all"/><img src="graphs/exit/exit-all.png"/>
-  </p><p><a id="exit-2010"/><img src="graphs/exit/exit-2010.png"/>
-  </p><p><a id="exit-2009"/><img src="graphs/exit/exit-2009.png"/>
-  </p><p><a id="exit-2008"/><img src="graphs/exit/exit-2008.png"/>
-  </p><p><a id="exit-2007"/><img src="graphs/exit/exit-2007.png"/>
-  </p><p><a id="exit-2006"/><img src="graphs/exit/exit-2006.png"/>
-  </p><p><a id="exit-2010-q2"/><img src="graphs/exit/exit-2010-q2.png"/>
-  </p><p><a id="exit-2010-q1"/><img src="graphs/exit/exit-2010-q1.png"/>
-  </p><p><a id="exit-2010-06"/><img src="graphs/exit/exit-2010-06.png"/>
-  </p><p><a id="exit-2010-05"/><img src="graphs/exit/exit-2010-05.png"/>
-  </p><br/>
+<%
+        out.print( "        <h2>Tor Metrics Portal: Graphs</h2>\n"
+        + "        <br/>\n"
+        + "        <h3>Exit relays in the Tor network</h3>\n"
+        + "        <br/>\n"
+        + "        <p>The number of exit relays in the Tor network can be extracted from\n"
+        + "        the hourly published network status consensuses.</p>\n"
+        + "        <ul>\n"
+        + "          <li>Past <a href=\"#exit-72h\">72 hours</a> up to\n"
+        + "              now</li>\n"
+        + "          <li>Past <a href=\"#exit-30d\">30</a>,\n"
+        + "              <a href=\"#exit-90d\">90</a>,\n"
+        + "              <a href=\"#exit-180d\">180</a> days</li>\n"
+        + "          <li><a href=\"#exit-all\">All data</a> up to today</li>\n"
+        + "          <li>Annual graphs of\n");
+    Calendar now = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
+    Calendar lastQuarter = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
+    lastQuarter.add(Calendar.MONTH, -3);
+    Calendar lastMonth = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
+    lastMonth.add(Calendar.MONTH, -1);
+    for (int i = now.get(Calendar.YEAR); i > 2006; i--) {
+      out.print("              <a href=\"#exit-" + i + "\">"
+          + i + "</a>,\n");
+    }
+    out.print("              <a href=\"#exit-2006\">2006</a></li>\n");
+    out.print("          <li>Quarterly graphs of\n");
+    out.print(String.format("              <a href=\"#exit-%1$tY-q%2$d\">"
+        + "Q%2$d %1$tY</a>,%n", now, 1 + now.get(Calendar.MONTH) / 3));
+    out.print(String.format("              <a href=\"#exit-%1$tY-q%2$d\">"
+        + "Q%2$d %1$tY</a></li>%n", lastQuarter, 1 + lastQuarter.get(Calendar.MONTH) / 3));
+    out.print("          <li>Monthly graphs of\n");
+    out.print(String.format("              <a href=\"#exit-%1$tY-%1$tm\">"
+        + "%1$tb %1$tY</a>,%n", now));
+    out.print(String.format("              <a href=\"#exit-%1$tY-%1$tm\">"
+        + "%1$tb %1$tY</a></li>%n", lastMonth));
+    out.print("          <li><a href=\"csv/exit.csv\">CSV</a> file\n"
+        + "              containing raw data</li>\n"
+        + "        </ul>\n");
+    out.print("        </p><p><a id=\"exit-72h\"/><img src=\"graphs/exit/exit-72h.png\"/>\n"
+        + "        </p><p><a id=\"exit-30d\"/><img src=\"graphs/exit/exit-30d.png\"/>\n"
+        + "        </p><p><a id=\"exit-90d\"/><img src=\"graphs/exit/exit-90d.png\"/>\n"
+        + "        </p><p><a id=\"exit-180d\"/><img src=\"graphs/exit/exit-180d.png\"/>\n"
+        + "        </p><p><a id=\"exit-all\"/><img src=\"graphs/exit/exit-all.png\"/>\n");
+    for (int i = now.get(Calendar.YEAR); i > 2006; i--) {
+      out.print("        </p><p><a id=\"exit-" + i + "\"/><img src=\"graphs/exit/exit-" + i + ".png\"/>\n");
+    }
+    out.print("        </p><p><a id=\"exit-2006\"/><img src=\"graphs/exit/exit-2006.png\"/>\n");
+    out.print(String.format("        </p><p><a id=\"exit-%1$tY-q%2$d\"/><img src=\"graphs/exit/exit-%1$tY-q%2$d.png\"/>\n",
+        now, 1 + now.get(Calendar.MONTH) / 3));
+    out.print(String.format("        </p><p><a id=\"exit-%1$tY-q%2$d\"/><img src=\"graphs/exit/exit-%1$tY-q%2$d.png\"/>\n",
+        lastQuarter, 1 + lastQuarter.get(Calendar.MONTH) / 3));
+    out.print(String.format("        </p><p><a id=\"exit-%1$tY-%1$tm\"/><img src=\"graphs/exit/exit-%1$tY-%1$tm.png\"/>\n", now));
+    out.print(String.format("        </p><p><a id=\"exit-%1$tY-%1$tm\"/><img src=\"graphs/exit/exit-%1$tY-%1$tm.png\"/>\n", lastMonth));
+    out.print("        </p><br/>\n");
+%>
 </div>
diff --git a/jsp/war/WEB-INF/templates/graphs_network-size.tpl.jsp b/jsp/war/WEB-INF/templates/graphs_network-size.tpl.jsp
index 441e01d..9c88a2b 100644
--- a/jsp/war/WEB-INF/templates/graphs_network-size.tpl.jsp
+++ b/jsp/war/WEB-INF/templates/graphs_network-size.tpl.jsp
@@ -1,55 +1,66 @@
+<%@page import="java.util.*" %>
+<%@page import="java.io.*" %>
 <div>
-  <h2>Tor Metrics Portal: Graphs</h2>
-  <br/>
-  <h3>Relays and bridges in the Tor network</h3>
-  <br/>
-  <p>The number of relays and bridges in the Tor network can be extracted from
-  the hourly published network status consensuses and sanitized bridge statuses.</p>
-  <ul>
-    <li>Past <a href="#networksize-30d">30</a>,
-    <a href="#networksize-90d">90</a>,
-    <a href="#networksize-180d">180</a> days</li>
-    <li><a href="#networksize-all">All data</a> up to today</li>
-    <li>Annual graphs of
-    <a href="#networksize-2010">2010</a>,
-    <a href="#networksize-2009">2009</a>,
-    <a href="#networksize-2008">2008</a>,
-    <a href="#networksize-2007">2007</a>,
-    <a href="#networksize-2006">2006</a></li>
-    <li>Quarterly graphs of
-    <a href="#networksize-2010-q2">Q2 2010</a>,
-    <a href="#networksize-2010-q1">Q1 2010</a></li>
-    <li>Monthly graphs of
-    <a href="#networksize-2010-06">Jun 2010</a>,
-    <a href="#networksize-2010-05">May 2010</a></li>
-    <li><a href="csv/networksize.csv">CSV</a> file
-    containing raw data</li>
-  </ul>
-  <p><a id="networksize-30d"/>
-    <img src="graphs/networksize/networksize-30d.png"/>
-    </p><p><a id="networksize-90d"/>
-    <img src="graphs/networksize/networksize-90d.png"/>
-    </p><p><a id="networksize-180d"/>
-    <img src="graphs/networksize/networksize-180d.png"/>
-    </p><p><a id="networksize-all"/>
-    <img src="graphs/networksize/networksize-all.png"/>
-    </p><p><a id="networksize-2010"/>
-    <img src="graphs/networksize/networksize-2010.png"/>
-    </p><p><a id="networksize-2009"/>
-    <img src="graphs/networksize/networksize-2009.png"/>
-    </p><p><a id="networksize-2008"/>
-    <img src="graphs/networksize/networksize-2008.png"/>
-    </p><p><a id="networksize-2007"/>
-    <img src="graphs/networksize/networksize-2007.png"/>
-    </p><p><a id="networksize-2006"/>
-    <img src="graphs/networksize/networksize-2006.png"/>
-    </p><p><a id="networksize-2010-q2"/>
-    <img src="graphs/networksize/networksize-2010-q2.png"/>
-    </p><p><a id="networksize-2010-q1"/>
-    <img src="graphs/networksize/networksize-2010-q1.png"/>
-    </p><p><a id="networksize-2010-06"/>
-    <img src="graphs/networksize/networksize-2010-06.png"/>
-    </p><p><a id="networksize-2010-05"/>
-    <img src="graphs/networksize/networksize-2010-05.png"/>
-    </p><br/>
-  </div>
+<%
+        out.print("        <h2>Tor Metrics Portal: Graphs</h2>\n"
+        + "        <br/>\n"
+        + "        <h3>Relays and bridges in the Tor network</h3>\n"
+        + "        <br/>\n"
+        + "        <p>The number of relays and bridges in the Tor network can be extracted from\n"
+        + "        the hourly published network status consensuses and sanitized bridge statuses.</p>\n"
+        + "        <ul>\n"
+        + "          <li>Past <a href=\"#networksize-30d\">30</a>,\n"
+        + "              <a href=\"#networksize-90d\">90</a>,\n"
+        + "              <a href=\"#networksize-180d\">180</a> days</li>\n"
+        + "          <li><a href=\"#networksize-all\">All data</a> up to today</li>\n"
+        + "          <li>Annual graphs of\n");
+    Calendar now = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
+    Calendar lastQuarter = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
+    lastQuarter.add(Calendar.MONTH, -3);
+    Calendar lastMonth = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
+    lastMonth.add(Calendar.MONTH, -1);
+    for (int i = now.get(Calendar.YEAR); i > 2006; i--) {
+      out.print("              <a href=\"#networksize-" + i + "\">"
+          + i + "</a>,\n");
+    }
+    out.print("              <a href=\"#networksize-2006\">2006</a></li>\n");
+    out.print("          <li>Quarterly graphs of\n");
+    out.print(String.format("              <a href=\"#networksize-%1$tY-q%2$d\">"
+        + "Q%2$d %1$tY</a>,%n", now, 1 + now.get(Calendar.MONTH) / 3));
+    out.print(String.format("              <a href=\"#networksize-%1$tY-q%2$d\">"
+        + "Q%2$d %1$tY</a></li>%n", lastQuarter, 1 + lastQuarter.get(Calendar.MONTH) / 3));
+    out.print("          <li>Monthly graphs of\n");
+    out.print(String.format("              <a href=\"#networksize-%1$tY-%1$tm\">"
+        + "%1$tb %1$tY</a>,%n", now));
+    out.print(String.format("              <a href=\"#networksize-%1$tY-%1$tm\">"
+        + "%1$tb %1$tY</a></li>%n", lastMonth));
+    out.print("          <li><a href=\"csv/networksize.csv\">CSV</a> file\n"
+        + "              containing raw data</li>\n"
+        + "        </ul>\n"
+        + "        <p><a id=\"networksize-30d\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-30d.png\"/>\n"
+        + "        </p><p><a id=\"networksize-90d\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-90d.png\"/>\n"
+        + "        </p><p><a id=\"networksize-180d\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-180d.png\"/>\n"
+        + "        </p><p><a id=\"networksize-all\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-all.png\"/>\n");
+    for (int i = now.get(Calendar.YEAR); i > 2006; i--) {
+      out.print("        </p><p><a id=\"networksize-" + i + "\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-" + i + ".png\"/>\n");
+    }
+    out.print("        </p><p><a id=\"networksize-2006\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-2006.png\"/>\n");
+    out.print(String.format("        </p><p><a id=\"networksize-%1$tY-q%2$d\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-%1$tY-q%2$d.png\"/>\n",
+        now, 1 + now.get(Calendar.MONTH) / 3));
+    out.print(String.format("        </p><p><a id=\"networksize-%1$tY-q%2$d\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-%1$tY-q%2$d.png\"/>\n",
+        lastQuarter, 1 + lastQuarter.get(Calendar.MONTH) / 3));
+    out.print(String.format("        </p><p><a id=\"networksize-%1$tY-%1$tm\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-%1$tY-%1$tm.png\"/>\n", now));
+    out.print(String.format("        </p><p><a id=\"networksize-%1$tY-%1$tm\"/>\n"
+        + "          <img src=\"graphs/networksize/networksize-%1$tY-%1$tm.png\"/>\n", lastMonth));
+    out.print("        </p><br/>\n");
+%>
+</div>
-- 
1.7.1