Commit 2053b0af authored by Leigh B Stoller's avatar Leigh B Stoller

We love usage stats!

parent 04d2a732
......@@ -30,6 +30,14 @@ else {
$DEFAULT_AGGREGATE = "Utah APT";
}
$urn_mapping =
array("urn:publicid:IDN+utah.cloudlab.us+authority+cm" => "Utah",
"urn:publicid:IDN+wisc.cloudlab.us+authority+cm" => "Wisc",
"urn:publicid:IDN+clemson.cloudlab.us+authority+cm" => "Clem",
"urn:publicid:IDN+apt.emulab.net+authority+cm" => "APT",
"urn:publicid:IDN+emulab.net+authority+cm" => "MS",
"urn:publicid:IDN+utahddc.geniracks.net+authority+cm" => "DDC");
class Instance
{
var $instance;
......
......@@ -13,7 +13,7 @@ function (sup, moment)
var date = $.trim($(this).html());
if (date != "") {
$(this).html(moment($(this).html())
.format("MMM Do, h:mm a"));
.format("ll"));
}
});
InitTable("table1");
......
......@@ -1250,6 +1250,12 @@ function (_, sup, moment, marked, UriTemplate, ShowImagingModal,
//
function DoSnapshotNode(node_id)
{
// Do not allow snapshot if the experiment is not in the ready state.
if (lastStatus != "ready") {
alert("Experiment is not ready yet, snapshot not allowed");
return;
}
// Default to update unless checkbox says otherwise.
var update_profile = 1;
var update_prepare = 0;
......
require(window.APT_OPTIONS.configObject,
['js/quickvm_sup', 'moment'],
function (sup, moment)
{
'use strict';
function initialize()
{
window.APT_OPTIONS.initialize(sup);
// Format dates with moment before display.
$('.format-date').each(function() {
var date = $.trim($(this).html());
if (date != "") {
$(this).html(moment($(this).html())
.format("MMM Do, h:mm a"));
}
});
InitTable("uid");
InitTable("pid");
}
function InitTable(name)
{
var tablename = "#tablesorter_" + name;
var searchname = "#search_" + name;
var table = $(tablename)
.tablesorter({
theme : 'green',
//cssChildRow: "tablesorter-childRow",
// initialize zebra and filter widgets
widgets: ["zebra", "filter", "resizable", "math"],
widgetOptions: {
// include child row content while filtering, if true
filter_childRows : true,
// include all columns in the search.
filter_anyMatch : true,
// class name applied to filter row and each input
filter_cssFilter : 'form-control',
// search from beginning
filter_startsWith : false,
// Set this option to false for case sensitive search
filter_ignoreCase : true,
// Only one search box.
filter_columnFilters : false,
// data-math attribute
math_data : 'math',
// ignore first column
math_ignore : [0],
// integers
math_mask : '',
}
});
// Target the $('.search') input using built in functioning
// this binds to the search using "search" and "keyup"
// Allows using filter_liveSearch or delayed search &
// pressing escape to cancel the search
$.tablesorter.filter.bindSearch(table, $(searchname));
}
$(document).ready(initialize);
});
......@@ -106,6 +106,8 @@ else {
function SPITROWS($all, $name, $result)
{
global $TBBASE, $urn_mapping;
echo "<input class='form-control search' type='search' data-column='all'
id='experiment_search_${name}' placeholder='Search'>\n";
......@@ -122,7 +124,12 @@ function SPITROWS($all, $name, $result)
}
echo " <th>Project</th>
<th>Status</th>
<th>Created</th>
<th>Cluster</th>\n";
if (ISADMIN()) {
echo " <th>P</th>\n";
echo " <th>V</th>\n";
}
echo " <th>Created</th>
<th>Expires</th>
</tr>
</thead>
......@@ -139,16 +146,23 @@ function SPITROWS($all, $name, $result)
$profile_name = $profile_id;
$creator_uid = $row["creator"];
$pid = $row["pid"];
$urn = $row["aggregate_urn"];
$cluster = $urn_mapping[$urn];
$pcount = $row["physnode_count"];
$vcount = $row["virtnode_count"];
list($foo,$hrn) = preg_split("/\./", $row["hrn"]);
$email = $row["email"];
# If a guest user, use email instead.
if (isset($email)) {
$creator = $email;
}
else {
elseif (ISADMIN()) {
$creator = "<a href='$TBBASE/showuser.php3?user=$creator_idx'>".
"$creator_uid</a>";
}
else {
$creator = $creator_uid;
}
if ($row["expired"]) {
$status = "expired";
}
......@@ -168,9 +182,20 @@ function SPITROWS($all, $name, $result)
if ($all) {
echo "<td>$creator</td>";
}
echo " <td><a href='$TBBASE/showproject.php3?pid=$pid'>$pid</a></td>";
echo " <td>$status</td>
<td class='format-date'>$created</td>
if (ISADMIN()) {
echo " <td><a href='$TBBASE/showproject.php3?pid=$pid'>".
"$pid</a></td>";
}
else {
echo " <td>$pid</td>\n";
}
echo " <td>$status</td>\n";
echo " <td>$cluster</td>\n";
if (ISADMIN()) {
echo "<td>$pcount</td>";
echo "<td>$vcount</td>";
}
echo" <td class='format-date'>$created</td>
<td class='format-date'>$expires</td>
</tr>\n";
}
......@@ -190,7 +215,7 @@ if (mysql_num_rows($query_result1) == 0) {
if (ISADMIN()) {
$message .= "<img src='images/redball.gif'>".
"<a href='myexperiments.php?all=1'>";
$message .= "Show all user Experiments</a>";
$message .= "Show all user Experiments</a><br>";
}
echo $message;
}
......
......@@ -283,7 +283,8 @@ $PAGEHEADER_FUNCTION = function($thinheader = 0, $ignore1 = NULL,
<li><a href='create-dataset.php'>Create Dataset</a></li>";
if (ISADMIN()) {
echo " <li class='divider'></li>
<li><a href='activity.php'>Activity</a></li>";
<li><a href='activity.php'>Activity</a></li>
<li><a href='sumstats.php'>Summary Stats</a></li>";
}
echo " </ul>
</li>\n";
......
<?php
#
# Copyright (c) 2000-2015 University of Utah and the Flux Group.
#
# {{{EMULAB-LICENSE
#
# This file is part of the Emulab network testbed software.
#
# This file is free software: you can redistribute it and/or modify it
# under the terms of the GNU Affero General Public License as published by
# the Free Software Foundation, either version 3 of the License, or (at
# your option) any later version.
#
# This file is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public
# License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this file. If not, see <http://www.gnu.org/licenses/>.
#
# }}}
#
chdir("..");
include("defs.php3");
include_once("geni_defs.php");
chdir("apt");
include("quickvm_sup.php");
include("instance_defs.php");
$page_title = "Summary Stats";
#
# Verify page arguments.
#
$optargs = OptionalPageArguments("showby", PAGEARG_STRING);
if (!isset($showby)) {
$showby = "user";
}
#
# Get current user.
#
RedirectSecure();
$this_user = CheckLoginOrRedirect();
if (!ISADMIN()) {
SPITUSERERROR("You do not have permission to view summary stats");
}
SPITHEADER(1);
echo "<link rel='stylesheet'
href='css/tablesorter.css'>\n";
function ShowByCreator()
{
global $urn_mapping, $TBBASE;
$query_result =
DBQueryFatal("select creator,aggregate_urn,count(creator) as ecount, ".
" sum(physnode_count) as pcount, ".
" truncate(sum(physnode_count * ".
" ((UNIX_TIMESTAMP(destroyed) - ".
" UNIX_TIMESTAMP(created)) / 3600.0)),2) as phours ".
"from apt_instance_history ".
"group by creator,aggregate_urn");
#
# Aggregate the per aggregate rows into a single row per user.
#
$uid_array = array();
while ($row = mysql_fetch_array($query_result)) {
$uid = $row["creator"];
$ecount = $row["ecount"];
$urn = $row["aggregate_urn"];
$cluster= $urn_mapping[$urn];
$ecount = $row["ecount"];
$pcount = $row["pcount"];
$phours = $row["phours"];
if (!array_key_exists($uid, $uid_array)) {
$uid_array[$uid] = array("ecount" => 0,
"pnodes" => 0,
"phours" => 0,
"Utah" => array("ecount" => 0,
"pcount" => 0,
"phours" => 0),
"Wisc" => array("ecount" => 0,
"pcount" => 0,
"phours" => 0),
"Clem" => array("ecount" => 0,
"pcount" => 0,
"phours" => 0),
"APT" => array("ecount" => 0,
"pcount" => 0,
"phours" => 0));
}
if ($cluster == "MS" || $cluster == "DDC") {
next;
}
$uid_array[$uid]["ecount"] += $ecount;
$uid_array[$uid]["pcount"] += $pcount;
$uid_array[$uid]["phours"] += $phours;
$uid_array[$uid][$cluster]["ecount"] = $ecount;
$uid_array[$uid][$cluster]["pcount"] = $pcount;
$uid_array[$uid][$cluster]["phours"] = $phours;
}
echo "<input class='form-control search' type='search' data-column='0'
id='search_uid' placeholder='Search'>\n";
echo " <table class='tablesorter' id='tablesorter_uid'>
<thead>
<tr>
<th rowspan=2>UID</th>
<th colspan=3>Totals</th>
<th colspan=3>APT</th>
<th colspan=3>Utah</th>
<th colspan=3>Wisc</th>
<th colspan=3>Clem</th>
</tr>
<tr>
<th>Expt</th>
<th>Pnodes</th>
<th>PHours</th>
<th>Expt</th>
<th>Pnodes</th>
<th>PHours</th>
<th>Expt</th>
<th>Pnodes</th>
<th>PHours</th>
<th>Expt</th>
<th>Pnodes</th>
<th>PHours</th>
<th>Expt</th>
<th>Pnodes</th>
<th>PHours</th>
</tr>
<tr>
<th class='filter-false sorter-false'>Totals</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
</tr>
</thead>\n";
echo" <tfoot>
<tr>
<th class='filter-false sorter-false'>Totals</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
</tr>
</tfoot>\n";
foreach ($uid_array as $uid => $ref) {
$uid = "<a href='$TBBASE/showuser.php3?user=$uid'>$uid</a>";
echo
"<tr>".
"<td>$uid</td>".
"<td>" . $ref["ecount"] . "</td> ".
"<td>" . $ref["pcount"] . "</td> ".
"<td>" . $ref["phours"] . "</td> ".
"<td>" . $ref["APT"]["ecount"] . "</td> ".
"<td>" . $ref["APT"]["pcount"] . "</td> ".
"<td>" . $ref["APT"]["phours"] . "</td> ".
"<td>" . $ref["Utah"]["ecount"] . "</td> ".
"<td>" . $ref["Utah"]["pcount"] . "</td> ".
"<td>" . $ref["Utah"]["phours"] . "</td> ".
"<td>" . $ref["Wisc"]["ecount"] . "</td> ".
"<td>" . $ref["Wisc"]["pcount"] . "</td> ".
"<td>" . $ref["Wisc"]["phours"] . "</td> ".
"<td>" . $ref["Clem"]["ecount"] . "</td> ".
"<td>" . $ref["Clem"]["pcount"] . "</td> ".
"<td>" . $ref["Clem"]["phours"] . "</td> ".
"</tr>\n";
}
echo "</table>";
}
function ShowByProject()
{
global $urn_mapping, $TBBASE;
$query_result =
DBQueryFatal("select pid,aggregate_urn,count(pid) as ecount, ".
" sum(physnode_count) as pcount, ".
" truncate(sum(physnode_count * ".
" ((UNIX_TIMESTAMP(destroyed) - ".
" UNIX_TIMESTAMP(created)) / 3600.0)),2) as phours ".
"from apt_instance_history ".
"group by pid,aggregate_urn");
#
# Aggregate the per aggregate rows into a single row per user.
#
$pid_array = array();
while ($row = mysql_fetch_array($query_result)) {
$pid = $row["pid"];
$urn = $row["aggregate_urn"];
$cluster= $urn_mapping[$urn];
$ecount = $row["ecount"];
$pcount = $row["pcount"];
$phours = $row["phours"];
if (!$pid) {
$pid = "NONE";
}
if (!array_key_exists($pid, $pid_array)) {
$pid_array[$pid] = array("ecount" => 0,
"pnodes" => 0,
"phours" => 0,
"Utah" => array("ecount" => 0,
"pcount" => 0,
"phours" => 0),
"Wisc" => array("ecount" => 0,
"pcount" => 0,
"phours" => 0),
"Clem" => array("ecount" => 0,
"pcount" => 0,
"phours" => 0),
"APT" => array("ecount" => 0,
"pcount" => 0,
"phours" => 0));
}
if ($cluster == "MS" || $cluster == "DDC") {
next;
}
$pid_array[$pid]["ecount"] += $ecount;
$pid_array[$pid]["pcount"] += $pcount;
$pid_array[$pid]["phours"] += $phours;
$pid_array[$pid][$cluster]["ecount"] = $ecount;
$pid_array[$pid][$cluster]["pcount"] = $pcount;
$pid_array[$pid][$cluster]["phours"] = $phours;
}
echo "<input class='form-control search' type='search' data-column='0'
id='search_pid' placeholder='Search'>\n";
echo " <table class='tablesorter' id='tablesorter_pid'>
<thead>
<tr>
<th rowspan=2>PID</th>
<th colspan=3>Totals</th>
<th colspan=3>APT</th>
<th colspan=3>Utah</th>
<th colspan=3>Wisc</th>
<th colspan=3>Clem</th>
</tr>
<tr>
<th>Expt</th>
<th>Pnodes</th>
<th>Phours</th>
<th>Expt</th>
<th>Pnodes</th>
<th>Phours</th>
<th>Expt</th>
<th>Pnodes</th>
<th>Phours</th>
<th>Expt</th>
<th>Pnodes</th>
<th>Phours</th>
<th>Expt</th>
<th>Pnodes</th>
<th>Phours</th>
</tr>
<tr>
<th class='filter-false sorter-false'>Totals</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
</tr>
</thead>\n";
echo" <tfoot>
<tr>
<th class='filter-false sorter-false'>Totals</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false' data-math='col-sum'>0</th>
<th class='filter-false sorter-false'
data-math='col-sum' data-math-mask='##0.00'>0</th>
</tr>
</tfoot>\n";
foreach ($pid_array as $pid => $ref) {
if ($pid != "NONE") {
$pid = "<a href='$TBBASE/showproject.php3?pid=$pid'>$pid</a>";
}
echo
"<tr>".
"<td>$pid</td>".
"<td>" . $ref["ecount"] . "</td> ".
"<td>" . $ref["pcount"] . "</td> ".
"<td>" . $ref["phours"] . "</td> ".
"<td>" . $ref["APT"]["ecount"] . "</td> ".
"<td>" . $ref["APT"]["pcount"] . "</td> ".
"<td>" . $ref["APT"]["phours"] . "</td> ".
"<td>" . $ref["Utah"]["ecount"] . "</td> ".
"<td>" . $ref["Utah"]["pcount"] . "</td> ".
"<td>" . $ref["Utah"]["phours"] . "</td> ".
"<td>" . $ref["Wisc"]["ecount"] . "</td> ".
"<td>" . $ref["Wisc"]["pcount"] . "</td> ".
"<td>" . $ref["Wisc"]["phours"] . "</td> ".
"<td>" . $ref["Clem"]["ecount"] . "</td> ".
"<td>" . $ref["Clem"]["pcount"] . "</td> ".
"<td>" . $ref["Clem"]["phours"] . "</td> ".
"</tr>\n";
}
echo "</table>";
}
echo "<div class='row'>
<div class='col-lg-12 col-lg-offset-0
col-md-12 col-md-offset-0
col-sm-12 col-sm-offset-0
col-xs-12 col-xs-offset-0'>\n";
if ($showby == "user") {
echo "<a href='sumstats.php?showby=project'>Show project stats</a><br>\n";
ShowByCreator();
}
else {
echo "<a href='sumstats.php?showby=user'>Show user stats</a><br>\n";
ShowByProject();
}
echo " </div>
</div>\n";
echo "<script src='js/lib/jquery-2.0.3.min.js'></script>\n";
echo "<script src='js/lib/jquery.tablesorter.min.js'></script>\n";
echo "<script src='js/lib/jquery.tablesorter.widgets.min.js'></script>\n";
echo "<script src='js/lib/jquery.tablesorter.widget-math.js'></script>\n";
echo "<script src='js/lib/bootstrap.js'></script>\n";
echo "<script src='js/lib/require.js' data-main='js/sumstats'></script>\n";
SPITFOOTER();
?>
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment