diff --git a/frontend/client/src/autotest/public/EmbeddedTkoClientTest.html b/frontend/client/src/autotest/public/EmbeddedTkoClientTest.html
index 0acea9b..1b880c1 100644
--- a/frontend/client/src/autotest/public/EmbeddedTkoClientTest.html
+++ b/frontend/client/src/autotest/public/EmbeddedTkoClientTest.html
@@ -9,35 +9,12 @@
   <script type="text/javascript">
     function initialize() {
       Autotest.initialize("http://autotest");
-
-      var plot1 = Autotest.createMetricsPlot(document.getElementById("plot1_canvas"));
-      queries = {}
-      queries["__main__"] = "SELECT test_name, AVG(IF(kernel LIKE '2.6.11%', iteration_value, NULL)) '2.6.11', STDDEV(IF(kernel LIKE '2.6.11%', iteration_value, NULL)) 'errors-2.6.11', AVG(IF(kernel LIKE '2.6.18%', iteration_value, NULL)) '2.6.18', STDDEV(IF(kernel LIKE '2.6.18%', iteration_value, NULL)) 'errors-2.6.18' FROM tko_perf_view_2 WHERE test_idx < 1000 AND test_name IN ('dbench', 'tbench') AND iteration_key = 'throughput' AND (kernel LIKE '2.6.11%' OR kernel LIKE '2.6.18%') GROUP BY test_name";
-      queries["__2.6.11__"] = "SELECT test_idx, iteration_value FROM tko_perf_view_2 WHERE test_idx < 1000 AND test_name IN ('dbench', 'tbench') AND iteration_key = 'throughput' AND kernel LIKE '2.6.11%%' AND test_name = %s ORDER BY iteration_value";
-      queries["__2.6.18__"] = "SELECT test_idx, iteration_value FROM tko_perf_view_2 WHERE test_idx < 1000 AND test_name IN ('dbench', 'tbench') AND iteration_key = 'throughput' AND kernel LIKE '2.6.18%%' AND test_name = %s ORDER BY iteration_value";
-      plot1.refresh({
-          plot : "Bar",
-          invert : [],
-          queries : queries
-      });
-
-      var plot2 = Autotest.createMetricsPlot(document.getElementById("plot2_canvas"));
-      queries = {}
-      queries["__main__"] = "SELECT kernel, AVG(iteration_value) 'throughput', STDDEV(iteration_value) 'errors-throughput' FROM tko_perf_view_2 WHERE test_idx < 1000 AND test_name = 'dbench' AND iteration_key ='throughput' GROUP BY kernel";
-      queries["__throughput__"] = "SELECT test_idx, iteration_value FROM tko_perf_view_2 WHERE test_idx < 1000 AND test_name = 'dbench' AND iteration_key ='throughput' AND kernel = %s ORDER BY iteration_value";
-      plot2.refresh({
-          plot : "Line",
-          invert : [],
-          queries : queries
-      });
     }
   </script>
 </head>
 
 <body onload="initialize()">
   Top text
-  <div id="plot1_canvas"></div>
   Middle text
-  <div id="plot2_canvas"></div>
   Bottom text
 </body>
diff --git a/frontend/client/src/autotest/tko/DynamicGraphingFrontend.java b/frontend/client/src/autotest/tko/DynamicGraphingFrontend.java
deleted file mode 100644
index 64536ba..0000000
--- a/frontend/client/src/autotest/tko/DynamicGraphingFrontend.java
+++ /dev/null
@@ -1,97 +0,0 @@
-package autotest.tko;
-
-import autotest.common.JsonRpcCallback;
-import autotest.common.ui.TabView;
-import autotest.tko.PreconfigSelector.PreconfigHandler;
-import autotest.tko.TableView.TableSwitchListener;
-
-import com.google.gwt.event.dom.client.ClickEvent;
-import com.google.gwt.event.dom.client.ClickHandler;
-import com.google.gwt.json.client.JSONObject;
-import com.google.gwt.json.client.JSONValue;
-import com.google.gwt.user.client.ui.Button;
-import com.google.gwt.user.client.ui.HasHorizontalAlignment;
-
-import java.util.Map;
-
-public abstract class DynamicGraphingFrontend extends GraphingFrontend
-                                              implements ClickHandler, PreconfigHandler {
-    protected PreconfigSelector preconfig;
-    protected Button graphButton = new Button("Graph");
-    protected Plot plot;
-    private TabView parent;
-
-    public DynamicGraphingFrontend(final TabView parent, Plot plot, String preconfigType) {
-        this.parent = parent;
-        this.plot = plot;
-        plot.setDrilldownTrigger();
-        preconfig = new PreconfigSelector(preconfigType, this);
-        graphButton.addClickHandler(this);
-    }
-
-    @Override
-    public void onClick(ClickEvent event) {
-        if (event.getSource() != graphButton) {
-            super.onClick(event);
-            return;
-        }
-
-        parent.updateHistory();
-        plot.setVisible(false);
-        embeddingLink.setVisible(false);
-        graphButton.setEnabled(false);
-
-        JSONObject params = buildParams();
-        if (params == null) {
-            graphButton.setEnabled(true);
-            return;
-        }
-
-        plot.refresh(params, new JsonRpcCallback() {
-            @Override
-            public void onSuccess(JSONValue result) {
-                plot.setVisible(true);
-                embeddingLink.setVisible(true);
-                graphButton.setEnabled(true);
-            }
-
-            @Override
-            public void onError(JSONObject errorObject) {
-                super.onError(errorObject);
-                graphButton.setEnabled(true);
-            }
-        });
-    }
-
-    protected abstract JSONObject buildParams();
-
-    @Override
-    public void refresh() {
-        // Nothing to refresh
-    }
-
-    protected void commonInitialization() {
-        table.setWidget(table.getRowCount(), 1, graphButton);
-        table.setWidget(table.getRowCount(), 0, plot);
-        table.getFlexCellFormatter().setColSpan(table.getRowCount() - 1, 0, 3);
-
-        table.setWidget(table.getRowCount(), 2, embeddingLink);
-        table.getFlexCellFormatter().setHorizontalAlignment(
-                table.getRowCount() - 1, 2, HasHorizontalAlignment.ALIGN_RIGHT);
-
-        plot.setVisible(false);
-        embeddingLink.setVisible(false);
-
-        initWidget(table);
-    }
-
-    public void handlePreconfig(Map<String, String> preconfigParameters) {
-        handleHistoryArguments(preconfigParameters);
-    }
-
-    @Override
-    protected void setListener(TableSwitchListener listener) {
-        super.setListener(listener);
-        plot.setListener(listener);
-    }
-}
diff --git a/frontend/client/src/autotest/tko/EmbeddedTkoClient.java b/frontend/client/src/autotest/tko/EmbeddedTkoClient.java
index 0ed0a0b..08ba372 100644
--- a/frontend/client/src/autotest/tko/EmbeddedTkoClient.java
+++ b/frontend/client/src/autotest/tko/EmbeddedTkoClient.java
@@ -19,30 +19,8 @@
     public void onModuleLoad() {
         JsonRpcProxy.setDefaultBaseUrl(JsonRpcProxy.TKO_BASE_URL);
         testDetailView = new TestDetailView();
-        injectNativeMethods();
     }
 
-    /**
-     * Creates a global object named Autotest with the following methods.  This objects acts as the
-     * entry point for externally-written native code to create embeddable widgets.
-     * * initialize(autoservServerUrl) -- must call this before anything else, passing in the URL
-     *   to the Autotest server (i.e. "http://myhost").
-     * * createMetricsPlot(parent) -- returns a metrics plot object attached to the given parent 
-     *   element.
-     */
-    private native void injectNativeMethods() /*-{
-        var instance = this;
-        $wnd.Autotest = {
-            initialize: function(autotestServerUrl) {
-                instance.@autotest.tko.EmbeddedTkoClient::initialize(Ljava/lang/String;)(autotestServerUrl);
-            },
-
-            createMetricsPlot: function(parent) {
-                return instance.@autotest.tko.EmbeddedTkoClient::createMetricsPlot(Lcom/google/gwt/dom/client/Element;)(parent);
-            }
-        }
-    }-*/;
-
     @SuppressWarnings("unused") // called from native
     private void initialize(String autotestServerUrl) {
         this.autotestServerUrl = autotestServerUrl;
@@ -51,32 +29,6 @@
         JsonRpcProxy.setProxy(JsonRpcProxy.TKO_BASE_URL, proxy);
     }
 
-    @SuppressWarnings("unused") // called from native
-    private JavaScriptObject createMetricsPlot(Element parent) {
-        UncaughtExceptionHandler handler = GWT.getUncaughtExceptionHandler();
-        if (handler == null) {
-            return doCreateMetricsPlot(parent);
-        }
-
-        try {
-            return doCreateMetricsPlot(parent);
-        } catch (Throwable throwable) {
-            handler.onUncaughtException(throwable);
-            return null;
-        }
-    }
-
-    private JavaScriptObject doCreateMetricsPlot(Element parent) {
-        if (parent == null) {
-            throw new IllegalArgumentException("parent element cannot be null");
-        }
-        Plot plot = new MetricsPlot();
-        plot.setDrilldownTrigger();
-        plot.setListener(this);
-        parent.appendChild(plot.getElement());
-        return plot.getNativeProxy();
-    }
-
     public HistoryToken getSelectTestHistoryToken(int testId) {
         testDetailView.updateObjectId(Integer.toString(testId));
         return testDetailView.getHistoryArguments();
diff --git a/frontend/client/src/autotest/tko/ExistingGraphsFrontend.java b/frontend/client/src/autotest/tko/ExistingGraphsFrontend.java
deleted file mode 100644
index 57faee6..0000000
--- a/frontend/client/src/autotest/tko/ExistingGraphsFrontend.java
+++ /dev/null
@@ -1,300 +0,0 @@
-package autotest.tko;
-
-import autotest.common.JsonRpcCallback;
-import autotest.common.SimpleCallback;
-import autotest.common.StaticDataRepository;
-import autotest.common.Utils;
-import autotest.common.ui.TabView;
-
-import com.google.gwt.event.dom.client.BlurEvent;
-import com.google.gwt.event.dom.client.BlurHandler;
-import com.google.gwt.event.dom.client.ClickEvent;
-import com.google.gwt.event.dom.client.ClickHandler;
-import com.google.gwt.event.logical.shared.SelectionEvent;
-import com.google.gwt.event.logical.shared.SelectionHandler;
-import com.google.gwt.json.client.JSONArray;
-import com.google.gwt.json.client.JSONObject;
-import com.google.gwt.json.client.JSONString;
-import com.google.gwt.json.client.JSONValue;
-import com.google.gwt.user.client.ui.Button;
-import com.google.gwt.user.client.ui.CheckBox;
-import com.google.gwt.user.client.ui.HorizontalPanel;
-import com.google.gwt.user.client.ui.ListBox;
-import com.google.gwt.user.client.ui.MultiWordSuggestOracle;
-import com.google.gwt.user.client.ui.Panel;
-import com.google.gwt.user.client.ui.SuggestBox;
-import com.google.gwt.user.client.ui.SuggestOracle;
-import com.google.gwt.user.client.ui.TextBox;
-
-import java.util.Arrays;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Map;
-import java.util.Set;
-
-public class ExistingGraphsFrontend extends GraphingFrontend {
-
-    private CheckBox normalize = new CheckBox("Normalize Performance (allows multiple benchmarks" +
-                                              " on one graph)");
-    private MultiWordSuggestOracle oracle = new MultiWordSuggestOracle();
-    private TextBox hostname = new TextBox();
-    private SuggestBox hostnameSuggest = new SuggestBox(oracle, hostname);
-    private Panel benchmarkWrapper = new HorizontalPanel();
-    private TextBox kernel = new TextBox();
-    private JSONObject hostsAndTests = null;
-    private Button graphButton = new Button("Graph");
-    
-    private ListBox singleBenchmark = new ListBox(false);
-    private ListBox multiBenchmark = new ListBox(true);
-
-    public ExistingGraphsFrontend(final TabView parent) {
-        normalize.addClickHandler(new ClickHandler() {
-            public void onClick(ClickEvent event) {
-                normalizeClicked();
-            }
-        });
-        
-        hostnameSuggest.getTextBox().addBlurHandler(new BlurHandler() {
-            public void onBlur(BlurEvent event) {
-                refreshTests();
-            }
-        });
-        hostnameSuggest.addSelectionHandler(new SelectionHandler<SuggestOracle.Suggestion>() {
-            public void onSelection(SelectionEvent<SuggestOracle.Suggestion> event) {
-                refreshTests();
-            }
-        });
-
-        addBenchmarkItem("(Please select a hostname first)");
-        
-        graphButton.addClickHandler(new ClickHandler() {
-            public void onClick(ClickEvent event) {
-                parent.updateHistory();
-                showGraph();
-            }
-        });
-
-        kernel.setText("all");
-        
-        table.setWidget(0, 0, normalize);
-        table.getFlexCellFormatter().setColSpan(0, 0, 2);
-        benchmarkWrapper.add(singleBenchmark);
-        benchmarkWrapper.add(multiBenchmark);
-        multiBenchmark.setVisible(false);
-        
-        addControl("Hostname:", hostnameSuggest);
-        addControl("Benchmark:", benchmarkWrapper);
-        addControl("Kernel:", kernel);
-        table.setWidget(table.getRowCount(), 1, graphButton);
-
-        table.getColumnFormatter().setWidth(0, "1px");
-        
-        initWidget(table);
-    }
-    
-    private void addBenchmarkItem(String item) {
-        singleBenchmark.addItem(item);
-        multiBenchmark.addItem(item);
-    }
-
-    private void getHostsAndTests(final SimpleCallback onFinished) {
-        setEnabled(false);
-        rpcProxy.rpcCall("get_hosts_and_tests", new JSONObject(), new JsonRpcCallback() {
-            @Override
-            public void onSuccess(JSONValue result) {
-                hostsAndTests = result.isObject();
-                onFinished.doCallback(null);
-                setEnabled(true);
-            }
-        });
-    }
-
-    @Override
-    public void refresh() {
-        getHostsAndTests(new SimpleCallback() {
-            public void doCallback(Object source) {
-                oracle.clear();
-                for (String host : hostsAndTests.keySet()) {
-                    oracle.add(host);
-                }
-            } 
-        });
-    }
-
-    @Override
-    public void addToHistory(Map<String, String> args) {
-        args.put("normalize", String.valueOf(normalize.getValue()));
-        args.put("hostname", hostname.getText());
-
-        // Add the selected benchmarks
-        StringBuilder benchmarks = new StringBuilder();
-        ListBox benchmark = getVisibleBenchmark();
-        for (int i = 0; i < benchmark.getItemCount(); i++) {
-            if (benchmark.isItemSelected(i)) {
-                benchmarks.append(benchmark.getValue(i));
-                benchmarks.append(",");
-            }
-        }
-
-        args.put("benchmark", benchmarks.toString());
-        args.put("kernel", kernel.getText());
-    }
-
-    @Override
-    public void handleHistoryArguments(final Map<String, String> args) {
-        hostname.setText(args.get("hostname"));
-        normalize.setValue(Boolean.parseBoolean(args.get("normalize")));
-        normalizeClicked();
-        kernel.setText(args.get("kernel"));
-
-        getHostsAndTests(new SimpleCallback() {
-            public void doCallback(Object source) {
-                refreshTests();
-                
-                ListBox benchmark = getVisibleBenchmark();
-                Set<String> benchmarks =
-                    new HashSet<String>(Arrays.asList(args.get("benchmark").split(",")));
-                for (int i = 0; i < benchmark.getItemCount(); i++) {
-                    benchmark.setItemSelected(i, benchmarks.contains(benchmark.getValue(i)));
-                }
-            } 
-        });
-    }
-    
-    private ListBox getVisibleBenchmark() {
-        boolean multiVisible = normalize.getValue();
-        if (multiVisible) {
-            assert multiBenchmark.isVisible();
-            return multiBenchmark;
-        } else {
-            assert singleBenchmark.isVisible();
-            return singleBenchmark;
-        }
-    }
-
-    @Override
-    protected void addAdditionalEmbeddingParams(JSONObject params) {
-        // No embedding
-    }
-
-    // Change the state of the page based on the status of the "normalize" checkbox
-    private void normalizeClicked() {
-        boolean multiVisible = normalize.getValue();
-        ListBox dest;
-        ListBox src;
-        
-        if (multiVisible) {
-            dest = multiBenchmark;
-            src = singleBenchmark;
-        } else {
-            dest = singleBenchmark;
-            src = multiBenchmark;
-        }
-        
-        dest.setVisible(true);
-        src.setVisible(false);
-        
-        dest.setSelectedIndex(src.getSelectedIndex());
-        src.setSelectedIndex(-1);
-    }
-
-    private void setEnabled(boolean enabled) {
-        normalize.setEnabled(enabled);
-        hostname.setEnabled(enabled);
-        singleBenchmark.setEnabled(enabled);
-        multiBenchmark.setEnabled(enabled);
-        kernel.setEnabled(enabled);
-        graphButton.setEnabled(enabled);
-    }
-    
-    private void refreshTests() {
-        JSONValue value = hostsAndTests.get(hostnameSuggest.getText());
-        if (value == null) {
-            return;
-        }
-
-        HashSet<String> selectedTests = new HashSet<String>();
-        ListBox benchmark = getVisibleBenchmark();
-        for (int i = 0; i < benchmark.getItemCount(); i++) {
-            if (benchmark.isItemSelected(i)) {
-                selectedTests.add(benchmark.getValue(i));
-            }
-        }
-        
-        JSONArray tests = value.isObject().get("tests").isArray();
-        singleBenchmark.clear();
-        multiBenchmark.clear();
-        for (int i = 0; i < tests.size(); i++) {
-            String test = Utils.jsonToString(tests.get(i));
-            addBenchmarkItem(test);
-            if (selectedTests.contains(test)) {
-                benchmark.setItemSelected(i, true);
-            }
-        }
-    }
-    
-    private void showGraph() {
-        String hostnameStr = hostnameSuggest.getText();
-        
-        JSONValue value = hostsAndTests.get(hostnameStr);
-        if (value == null) {
-            return;
-        }
-        
-        String url;
-        HashMap<String, String> args = new HashMap<String, String>();
-        args.put("kernel", kernel.getText());
-        
-        if (normalize.getValue()) {
-            url = "/tko/machine_aggr.cgi?";
-            final JSONArray tests = new JSONArray();
-            for (int i = 0; i < multiBenchmark.getItemCount(); i++) {
-                if (multiBenchmark.isItemSelected(i)) {
-                    tests.set(tests.size(), new JSONString(multiBenchmark.getValue(i)));
-                }
-            }
-            
-            args.put("machine", hostnameStr);
-
-            StringBuilder arg = new StringBuilder();
-            for (int i = 0; i < tests.size(); i++) {
-                String test = Utils.jsonToString(tests.get(i));
-                String key = getKey(test);
-                if (i != 0) {
-                    arg.append(",");
-                }
-                arg.append(test);
-                arg.append(":");
-                arg.append(key);
-            }
-            args.put("benchmark_key", arg.toString());
-        } else {
-            int benchmarkIndex = singleBenchmark.getSelectedIndex();
-            if (benchmarkIndex == -1) {
-                return;
-            }
-            
-            url = "/tko/machine_test_attribute_graph.cgi?";
-            
-            JSONObject hostObject = value.isObject();
-            String machine = Utils.jsonToString(hostObject.get("id"));
-            String benchmarkStr = singleBenchmark.getValue(benchmarkIndex);
-            
-            args.put("machine", machine);
-            args.put("benchmark", benchmarkStr);
-            args.put("key", getKey(benchmarkStr));
-        }
-        Utils.openUrlInNewWindow(url + Utils.encodeUrlArguments(args));
-    }
-    
-    private String getKey(String benchmark) {
-        JSONObject benchmarkKey =
-            StaticDataRepository.getRepository().getData("benchmark_key").isObject();
-        return Utils.jsonToString(benchmarkKey.get(benchmark.replaceAll("\\..*", "")));
-    }
-
-    @Override
-    public String getFrontendId() {
-        return "existing_graphs";
-    }
-}
diff --git a/frontend/client/src/autotest/tko/GraphingFrontend.java b/frontend/client/src/autotest/tko/GraphingFrontend.java
deleted file mode 100644
index 7b4dcad..0000000
--- a/frontend/client/src/autotest/tko/GraphingFrontend.java
+++ /dev/null
@@ -1,145 +0,0 @@
-package autotest.tko;
-
-import autotest.common.CustomHistory;
-import autotest.common.JsonRpcCallback;
-import autotest.common.JsonRpcProxy;
-import autotest.common.Utils;
-import autotest.common.CustomHistory.CustomHistoryListener;
-import autotest.common.CustomHistory.HistoryToken;
-import autotest.common.ui.NotifyManager;
-import autotest.common.ui.SimpleDialog;
-import autotest.tko.TableView.TableSwitchListener;
-
-import com.google.gwt.event.dom.client.ClickEvent;
-import com.google.gwt.event.dom.client.ClickHandler;
-import com.google.gwt.json.client.JSONNumber;
-import com.google.gwt.json.client.JSONObject;
-import com.google.gwt.json.client.JSONString;
-import com.google.gwt.json.client.JSONValue;
-import com.google.gwt.user.client.Window;
-import com.google.gwt.user.client.ui.Anchor;
-import com.google.gwt.user.client.ui.Composite;
-import com.google.gwt.user.client.ui.FlexTable;
-import com.google.gwt.user.client.ui.HasVerticalAlignment;
-import com.google.gwt.user.client.ui.TextBox;
-import com.google.gwt.user.client.ui.Widget;
-
-import java.util.Map;
-
-public abstract class GraphingFrontend extends Composite
-                                       implements CustomHistoryListener, ClickHandler {
-    public static final String HISTORY_TOKEN = "embedded_query";
-
-    protected FlexTable table = new FlexTable();
-    protected JsonRpcProxy rpcProxy = JsonRpcProxy.getProxy();
-    protected Anchor embeddingLink = new Anchor("[Link to this graph]");
-    protected TableSwitchListener listener;
-
-    public abstract void refresh();
-    public abstract void addToHistory(Map<String, String> args);
-    public abstract void handleHistoryArguments(Map<String, String> args);
-
-    /**
-     * This function allows subclasses to add parameters to the call to get_embedding_id() RPC,
-     * called when a user requests an embeddable link to a graph.
-     */
-    protected abstract void addAdditionalEmbeddingParams(JSONObject params);
-
-    /**
-     * @return a short text ID for the frontend
-     */
-    public abstract String getFrontendId();
-
-    protected GraphingFrontend() {
-        CustomHistory.addHistoryListener(this);
-        embeddingLink.addClickHandler(this);
-    }
-
-    public void onClick(ClickEvent event) {
-        assert event.getSource() == embeddingLink;
-        JSONObject params = new JSONObject();
-        params.put("url_token", new JSONString(CustomHistory.getLastHistoryToken().toString()));
-        addAdditionalEmbeddingParams(params);
-
-        rpcProxy.rpcCall("get_embedding_id", params, new JsonRpcCallback() {
-            @Override
-            public void onSuccess(JSONValue result) {
-                String id = Utils.jsonToString(result);
-                showEmbeddedGraphHtml(id);
-            }
-        });
-    }
-
-    private void showEmbeddedGraphHtml(String embeddedGraphId) {
-        StringBuilder link = new StringBuilder();
-        link.append("<a href=\"http://");
-        link.append(Window.Location.getHost());
-        link.append(Window.Location.getPath());
-        link.append("#");
-        link.append(HISTORY_TOKEN);
-        link.append("=");
-        link.append(embeddedGraphId);
-
-        link.append("\"><img border=\"0\" src=\"http://");
-        link.append(Window.Location.getHost());
-
-        link.append(JsonRpcProxy.TKO_BASE_URL);
-        link.append("plot/?id=");
-        link.append(embeddedGraphId);
-
-        link.append("&max_age=10");
-
-        link.append("\"></a>");
-
-        TextBox linkBox = new TextBox();
-        linkBox.setText(link.toString());
-        linkBox.setWidth("100%");
-        linkBox.setSelectionRange(0, link.length());
-
-        new SimpleDialog("Paste HTML to embed in website:", linkBox).center();
-    }
-
-    protected void setListener(TableSwitchListener listener) {
-        this.listener = listener;
-    }
-
-    protected void addControl(String text, Widget control) {
-        int row = TkoUtils.addControlRow(table, text, control);
-        table.getFlexCellFormatter().setColSpan(row, 1, 2);
-        table.getFlexCellFormatter().setWidth(row, 1, "100%");
-        table.getFlexCellFormatter().setVerticalAlignment(row, 0, HasVerticalAlignment.ALIGN_TOP);
-    }
-
-    // TODO(showard): merge this with the code from SavedQueriesControl
-    public void onHistoryChanged(Map<String, String> arguments) {
-        final String idString = arguments.get(HISTORY_TOKEN);
-        if (idString == null) {
-            return;
-        }
-
-        JSONObject args = new JSONObject();
-        args.put("id", new JSONNumber(Integer.parseInt(idString)));
-        rpcProxy.rpcCall("get_embedded_query_url_token", args, new JsonRpcCallback() {
-            @Override
-            public void onSuccess(JSONValue result) {
-                String tokenString = Utils.jsonToString(result);
-                HistoryToken token;
-                try {
-                    token = HistoryToken.fromString(tokenString);
-                } catch (IllegalArgumentException exc) {
-                    NotifyManager.getInstance().showError("Invalid embedded query token " +
-                                                          tokenString);
-                    return;
-                }
-
-                // since this is happening asynchronously, the history may have changed, so ensure
-                // it's set back to what it should be.
-                HistoryToken shortToken = new HistoryToken();
-                shortToken.put(HISTORY_TOKEN, idString);
-                CustomHistory.newItem(shortToken);
-
-                CustomHistory.simulateHistoryToken(token);
-            }
-        });
-    }
-}
diff --git a/frontend/client/src/autotest/tko/GraphingView.java b/frontend/client/src/autotest/tko/GraphingView.java
deleted file mode 100644
index 3b0dade..0000000
--- a/frontend/client/src/autotest/tko/GraphingView.java
+++ /dev/null
@@ -1,105 +0,0 @@
-package autotest.tko;
-
-import autotest.common.CustomHistory.HistoryToken;
-import autotest.common.ui.ExtendedListBox;
-import autotest.common.ui.TabView;
-import autotest.tko.TableView.TableSwitchListener;
-
-import com.google.gwt.event.dom.client.ChangeEvent;
-import com.google.gwt.event.dom.client.ChangeHandler;
-import com.google.gwt.user.client.ui.DeckPanel;
-
-import java.util.Map;
-
-public class GraphingView extends TabView {
-
-    private ExtendedListBox frontendSelection = new ExtendedListBox();
-    private MetricsPlotFrontend metricsPlotFrontend = new MetricsPlotFrontend(this);
-    private MachineQualHistogramFrontend machineQualHistogramFrontend =
-        new MachineQualHistogramFrontend(this);
-    private ExistingGraphsFrontend existingGraphsFrontend = new ExistingGraphsFrontend(this);
-    private DeckPanel controlPanel = new DeckPanel();
-    private GraphingFrontend frontends[] = {
-            metricsPlotFrontend,
-            machineQualHistogramFrontend,
-            existingGraphsFrontend,
-    };
-
-    public GraphingView(TableSwitchListener listener) {
-        metricsPlotFrontend.setListener(listener);
-        machineQualHistogramFrontend.setListener(listener);
-    }
-    
-    @Override
-    public void initialize() {
-        super.initialize();
-        frontendSelection.addItem("Metrics Plot", metricsPlotFrontend.getFrontendId());
-        frontendSelection.addItem("Machine Qualification Histogram", 
-                                  machineQualHistogramFrontend.getFrontendId());
-        frontendSelection.addItem("Existing Graphs", existingGraphsFrontend.getFrontendId());
-
-        frontendSelection.addChangeHandler(new ChangeHandler() {
-            public void onChange(ChangeEvent event) {
-                showSelectedView();
-                updateHistory();
-            }
-        });
-
-        controlPanel.add(metricsPlotFrontend);
-        controlPanel.add(machineQualHistogramFrontend);
-        controlPanel.add(existingGraphsFrontend);
-        controlPanel.showWidget(0);
-
-        addWidget(frontendSelection, "graphing_type");
-        addWidget(controlPanel, "graphing_frontend");
-    }
-
-    @Override
-    public String getElementId() {
-        return "graphing_view";
-    }
-    
-    private GraphingFrontend getSelectedFrontend() {
-        return frontends[frontendSelection.getSelectedIndex()];
-    }
-
-    @Override
-    public void refresh() {
-        super.refresh();
-        getSelectedFrontend().refresh();
-    }
-
-    @Override
-    public void display() {
-        super.display();
-        CommonPanel.getPanel().setConditionVisible(false);
-    }
-    
-    @Override
-    public HistoryToken getHistoryArguments() {
-        HistoryToken args = super.getHistoryArguments();
-        args.put("view", getSelectedFrontend().getFrontendId());
-        getSelectedFrontend().addToHistory(args);
-        return args;
-    }
-
-    @Override
-    public void handleHistoryArguments(Map<String, String> arguments) {
-        super.handleHistoryArguments(arguments);
-        String frontendId = arguments.get("view");
-        frontendSelection.selectByValue(frontendId);
-        for (GraphingFrontend frontend : frontends) {
-            if (frontend.getFrontendId().equals(frontendId)) {
-                frontend.handleHistoryArguments(arguments);
-                break;
-            }
-        }
-        showSelectedView();
-    }
-    
-    private void showSelectedView() {
-        int index = frontendSelection.getSelectedIndex();
-        controlPanel.showWidget(index);
-        frontends[index].refresh();
-    }
-}
diff --git a/frontend/client/src/autotest/tko/MachineQualHistogram.java b/frontend/client/src/autotest/tko/MachineQualHistogram.java
deleted file mode 100644
index 757553e..0000000
--- a/frontend/client/src/autotest/tko/MachineQualHistogram.java
+++ /dev/null
@@ -1,49 +0,0 @@
-package autotest.tko;
-
-import autotest.common.Utils;
-import autotest.common.ui.SimpleDialog;
-import autotest.tko.TableView.TableViewConfig;
-
-import com.google.gwt.json.client.JSONObject;
-import com.google.gwt.user.client.ui.HTML;
-
-class MachineQualHistogram extends Plot {
-    public MachineQualHistogram() {
-        super("create_qual_histogram");
-    }
-
-    /**
-     * drilldownParams contains:
-     * * type: "normal", "not_applicable", or "empty"
-     * for type "normal":
-     *   * filterString: SQL filter for selected bucket
-     * for type "not_applicable":
-     *   * hosts: HTML list of hosts in this bucket
-     */
-    @Override
-    protected void showDrilldownImpl(JSONObject drilldownParams) {
-        String type = Utils.jsonToString(drilldownParams.get("type"));
-        if (type.equals("normal")) {
-            String filterString = Utils.jsonToString(drilldownParams.get("filterString"));
-            showNormalDrilldown(filterString);
-        } else if (type.equals("not_applicable")) {
-            String hosts = Utils.jsonToString(drilldownParams.get("hosts"));
-            showNADialog(hosts);
-        } else if (type.equals("empty")) {
-            showEmptyDialog();
-        }
-    }
-
-    private void showNormalDrilldown(final String filterString) {
-        CommonPanel.getPanel().setSqlCondition(filterString);
-        listener.onSwitchToTable(TableViewConfig.PASS_RATE);
-    }
-
-    private void showNADialog(String hosts) {
-        new SimpleDialog("Did not run any of the selected tests:", new HTML(hosts)).center();
-    }
-
-    private void showEmptyDialog() {
-        new SimpleDialog("No hosts in this pass rate range", new HTML()).center();
-    }
-}
diff --git a/frontend/client/src/autotest/tko/MachineQualHistogramFrontend.java b/frontend/client/src/autotest/tko/MachineQualHistogramFrontend.java
deleted file mode 100644
index 5d226cd..0000000
--- a/frontend/client/src/autotest/tko/MachineQualHistogramFrontend.java
+++ /dev/null
@@ -1,135 +0,0 @@
-package autotest.tko;
-
-import autotest.common.ui.NotifyManager;
-import autotest.common.ui.TabView;
-
-import com.google.gwt.json.client.JSONNumber;
-import com.google.gwt.json.client.JSONObject;
-import com.google.gwt.json.client.JSONString;
-import com.google.gwt.user.client.ui.TextBox;
-
-import java.util.Map;
-
-public class MachineQualHistogramFrontend extends DynamicGraphingFrontend {
-    private static final String DEFAULT_INTERVAL = "10";
-
-    private FilterSelector globalFilters =
-        new FilterSelector(DBColumnSelector.TEST_VIEW);
-    private FilterSelector testFilters =
-        new FilterSelector(DBColumnSelector.TEST_VIEW);
-    private TextBox interval = new TextBox();
-
-    public MachineQualHistogramFrontend(final TabView parent) {
-        super(parent, new MachineQualHistogram(), "qual");
-
-        interval.setText(DEFAULT_INTERVAL);
-
-        addControl("Preconfigured:", preconfig);
-        addControl("Global filters:", globalFilters);
-        addControl("Test set filters:", testFilters);
-        addControl("Interval:", interval);
-        
-        commonInitialization();
-    }
-    
-    @Override
-    protected void addAdditionalEmbeddingParams(JSONObject params) {
-        params.put("graph_type", new JSONString("qual"));
-        params.put("params", buildParams());
-    }
-    
-    private JSONString buildQuery() {
-        String gFilterString = globalFilters.getFilterString();
-        String tFilterString = testFilters.getFilterString();
-        boolean hasGFilter = !gFilterString.equals("");
-        boolean hasTFilter = !tFilterString.equals("");
-        
-        StringBuilder sql = new StringBuilder();
-        
-        sql.append("SELECT hostname, COUNT(DISTINCT ");
-        if (hasTFilter) {
-            sql.append("IF(");
-            sql.append(tFilterString);
-            sql.append(", test_idx, NULL)");
-        } else {
-            sql.append("test_idx");
-        }
-        sql.append(") 'total', COUNT(DISTINCT IF(");
-        if (hasTFilter) {
-            sql.append(TkoUtils.wrapWithParens(tFilterString));
-            sql.append(" AND ");
-        }
-        
-        sql.append("status = 'GOOD', test_idx, NULL)) 'good' FROM tko_test_view_outer_joins");
-        if (hasGFilter) {
-            sql.append(" WHERE ");
-            sql.append(gFilterString);
-        }
-        sql.append(" GROUP BY hostname");
-        return new JSONString(sql.toString());
-    }
-    
-    private JSONString buildFilterString() {
-        StringBuilder filterString = new StringBuilder();
-        String gFilterString = globalFilters.getFilterString();
-        String tFilterString = testFilters.getFilterString();
-        boolean hasGFilter = !gFilterString.equals("");
-        boolean hasTFilter = !tFilterString.equals("");
-        if (hasGFilter) {
-            filterString.append(TkoUtils.wrapWithParens(gFilterString));
-            if (hasTFilter) {
-                filterString.append(" AND ");
-            }
-        }
-        if (hasTFilter) {
-            filterString.append(TkoUtils.wrapWithParens(tFilterString));
-        }
-        return new JSONString(filterString.toString());
-    }
-    
-    @Override
-    protected JSONObject buildParams() {
-        if (interval.getText().equals("")) {
-            NotifyManager.getInstance().showError("You must enter an interval");
-            return null;
-        }
-        
-        int intervalValue;
-        try {
-            intervalValue = Integer.parseInt(interval.getText());
-        } catch (NumberFormatException e) {
-            NotifyManager.getInstance().showError("Interval must be an integer");
-            return null;
-        }
-        
-        JSONObject params = new JSONObject();
-        params.put("query", buildQuery());
-        params.put("filter_string", buildFilterString());
-        params.put("interval", new JSONNumber(intervalValue));
-
-        return params;
-    }
-
-    @Override
-    public String getFrontendId() {
-        return "machine_qual_histogram";
-    }
-    
-    @Override
-    public void addToHistory(Map<String, String> args) {
-        globalFilters.addToHistory(args, "globalFilter");
-        testFilters.addToHistory(args, "testFilter");
-        args.put("interval", interval.getText());
-    }
-    
-    @Override
-    public void handleHistoryArguments(Map<String, String> args) {
-        setVisible(false);
-        globalFilters.reset();
-        testFilters.reset();
-        globalFilters.handleHistoryArguments(args, "globalFilter");
-        testFilters.handleHistoryArguments(args, "testFilter");
-        interval.setText(args.get("interval"));
-        setVisible(true);
-    }
-}
diff --git a/frontend/client/src/autotest/tko/MetricsPlot.java b/frontend/client/src/autotest/tko/MetricsPlot.java
deleted file mode 100644
index 567dc68..0000000
--- a/frontend/client/src/autotest/tko/MetricsPlot.java
+++ /dev/null
@@ -1,64 +0,0 @@
-package autotest.tko;
-
-import autotest.common.JsonRpcCallback;
-import autotest.common.Utils;
-import autotest.common.ui.SimpleDialog;
-
-import com.google.gwt.event.dom.client.ClickEvent;
-import com.google.gwt.event.dom.client.ClickHandler;
-import com.google.gwt.json.client.JSONArray;
-import com.google.gwt.json.client.JSONObject;
-import com.google.gwt.json.client.JSONString;
-import com.google.gwt.json.client.JSONValue;
-import com.google.gwt.user.client.ui.Anchor;
-import com.google.gwt.user.client.ui.FlexTable;
-
-class MetricsPlot extends Plot {
-    public MetricsPlot() {
-        super("create_metrics_plot");
-    }
-
-    /**
-     * drilldownParams contains:
-     * * query - SQL query for the selected series
-     * * series - name of the selected series
-     * * param - parameter to fill in query for the selected data point
-     */
-    @Override
-    protected void showDrilldownImpl(JSONObject drilldownParams) {
-        String query = Utils.jsonToString(drilldownParams.get("query"));
-        final String series = Utils.jsonToString(drilldownParams.get("series"));
-        final String param = Utils.jsonToString(drilldownParams.get("param"));
-
-        JSONObject params = new JSONObject();
-        params.put("query", new JSONString(query));
-        params.put("param", new JSONString(param));
-        rpcProxy.rpcCall("execute_query_with_param", params, new JsonRpcCallback() {
-            @Override
-            public void onSuccess(JSONValue result) {
-                JSONArray data = result.isArray();
-
-                String title = series + " for " + param;
-                FlexTable contents = new FlexTable();
-                final SimpleDialog drill = new SimpleDialog(title, contents);
-
-                for (int i = 0; i < data.size(); i++) {
-                    final JSONArray row = data.get(i).isArray();
-                    final int testId = (int) row.get(0).isNumber().doubleValue();
-                    String yValue = Utils.jsonToString(row.get(1));
-
-                    Anchor link = new Anchor(yValue);
-                    link.addClickHandler(new ClickHandler() {
-                        public void onClick(ClickEvent event) {
-                            drill.hide();
-                            listener.onSelectTest(testId);
-                        }
-                    });
-                    contents.setWidget(i, 0, link);
-                }
-
-                drill.center();
-            }
-        });
-    }
-}
diff --git a/frontend/client/src/autotest/tko/MetricsPlotFrontend.java b/frontend/client/src/autotest/tko/MetricsPlotFrontend.java
deleted file mode 100644
index cd4cd51..0000000
--- a/frontend/client/src/autotest/tko/MetricsPlotFrontend.java
+++ /dev/null
@@ -1,341 +0,0 @@
-package autotest.tko;
-
-import autotest.common.Utils;
-import autotest.common.ui.ExtendedListBox;
-import autotest.common.ui.NotifyManager;
-import autotest.common.ui.TabView;
-import autotest.tko.SeriesSelector.Series;
-
-import com.google.gwt.event.dom.client.ChangeEvent;
-import com.google.gwt.event.dom.client.ChangeHandler;
-import com.google.gwt.event.dom.client.ClickEvent;
-import com.google.gwt.event.dom.client.ClickHandler;
-import com.google.gwt.json.client.JSONObject;
-import com.google.gwt.json.client.JSONString;
-import com.google.gwt.user.client.ui.HorizontalPanel;
-import com.google.gwt.user.client.ui.Panel;
-import com.google.gwt.user.client.ui.RadioButton;
-import com.google.gwt.user.client.ui.TextBox;
-import com.google.gwt.user.client.ui.VerticalPanel;
-
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-public class MetricsPlotFrontend extends DynamicGraphingFrontend implements ClickHandler {
-    
-    public static final String NORMALIZE_SINGLE = "single";
-    public static final String NORMALIZE_FIRST = "first";
-    public static final String NORMALIZE_SERIES_PREFIX = "series__";
-    public static final String NORMALIZE_X_PREFIX = "x__";
-    
-    protected FilterSelector globalFilter = new FilterSelector(DBColumnSelector.PERF_VIEW);
-    private ExtendedListBox plotSelector = new ExtendedListBox();
-    private ExtendedListBox xAxis = new DBColumnSelector(DBColumnSelector.PERF_VIEW, true);
-    private RadioButton noNormalizeMultiple =
-        new RadioButton("normalize", "No normalization (multiple subplots)");
-    private RadioButton noNormalizeSingle =
-        new RadioButton("normalize", "No normalization (single plot)");
-    private RadioButton normalizeFirst = new RadioButton("normalize", "First data point");
-    private RadioButton normalizeSeries = new RadioButton("normalize", "Specified series:");
-    private ExtendedListBox normalizeSeriesSelect = new ExtendedListBox();
-    private RadioButton normalizeX = new RadioButton("normalize", "Specified X-axis value:");
-    private TextBox normalizeXSelect = new TextBox();
-    private SeriesSelector seriesSelector = new SeriesSelector(new ChangeHandler() {
-        public void onChange(ChangeEvent event) {
-            refreshSeries();
-        }
-    });
-    
-    public MetricsPlotFrontend(final TabView parent) {
-        super(parent, new MetricsPlot(), "metrics");
-
-        noNormalizeSingle.setValue(true);
-
-        noNormalizeMultiple.addClickHandler(this);
-        noNormalizeSingle.addClickHandler(this);
-        normalizeFirst.addClickHandler(this);
-        normalizeSeries.addClickHandler(this);
-        normalizeX.addClickHandler(this);
-
-        normalizeSeriesSelect.setEnabled(false);
-        normalizeXSelect.setEnabled(false);
-
-        plotSelector.addItem("Line");
-        plotSelector.addItem("Bar");
-        plotSelector.addChangeHandler(new ChangeHandler() {
-            public void onChange(ChangeEvent event) {
-                checkNormalizeInput();
-            }
-        });
-
-        Panel normalizePanel = new VerticalPanel();
-        normalizePanel.add(noNormalizeMultiple);
-        normalizePanel.add(noNormalizeSingle);
-        Panel seriesPanel = new HorizontalPanel();
-        seriesPanel.add(normalizeSeries);
-        seriesPanel.add(normalizeSeriesSelect);
-        normalizePanel.add(seriesPanel);
-        normalizePanel.add(normalizeFirst);
-        Panel baselinePanel = new HorizontalPanel();
-        baselinePanel.add(normalizeX);
-        baselinePanel.add(normalizeXSelect);
-        normalizePanel.add(baselinePanel);
-        
-        addControl("Preconfigured:", preconfig);
-        addControl("Plot:", plotSelector);
-        addControl("X-axis values:", xAxis);
-        addControl("Global filters:", globalFilter);
-        addControl("Series:", seriesSelector);
-        addControl("Normalize to:", normalizePanel);
-        
-        commonInitialization();
-    }
-
-    @Override
-    public void onClick(ClickEvent event) {
-        if (event.getSource() != noNormalizeSingle && event.getSource() != noNormalizeMultiple 
-                && event.getSource() != normalizeSeries && event.getSource() != normalizeX) {
-            super.onClick(event);
-            return;
-        }
-
-        normalizeSeriesSelect.setEnabled(false);
-        normalizeXSelect.setEnabled(false);
-        if (event.getSource() == normalizeSeries) {
-            normalizeSeriesSelect.setEnabled(true);
-            refreshSeries();
-        } else if (event.getSource() == normalizeX) {
-            normalizeXSelect.setEnabled(true);
-        }
-
-        checkInvertible();
-    }
-    
-    private void addNormalizeParameter(String plotType, Map<String, String> parameters) {
-        String normalizationType = null;
-        if (plotType.equals("Line") && noNormalizeSingle.getValue()) {
-            normalizationType = NORMALIZE_SINGLE;
-        } else if (normalizeFirst.getValue()) {
-            normalizationType = NORMALIZE_FIRST;
-        } else if (normalizeSeries.getValue()) {
-            String series = normalizeSeriesSelect.getSelectedValue();
-            normalizationType = NORMALIZE_SERIES_PREFIX + series;
-        } else if (normalizeX.getValue()) {
-            String baseline = normalizeXSelect.getText();
-            normalizationType = NORMALIZE_X_PREFIX + baseline;
-        }
-        
-        if (normalizationType != null) {
-            parameters.put("normalize", normalizationType);
-        }
-    }
-
-    @Override
-    public void addToHistory(Map<String, String> args) {
-        String plot = plotSelector.getValue(plotSelector.getSelectedIndex());
-        args.put("plot", plot);
-        args.put("xAxis", xAxis.getSelectedValue());
-        globalFilter.addToHistory(args, "globalFilter");
-        seriesSelector.addToHistory(args);
-        addNormalizeParameter(plot, args);
-    }
-    
-    @Override
-    public void handleHistoryArguments(Map<String, String> args) {
-        setVisible(false);
-        plot.setVisible(false);
-        embeddingLink.setVisible(false);
-        globalFilter.reset();
-        seriesSelector.reset();
-        for (int i = 0; i < plotSelector.getItemCount(); i++) {
-            if (plotSelector.getValue(i).equals(args.get("plot"))) {
-                plotSelector.setSelectedIndex(i);
-                break;
-            }
-        }
-        
-        xAxis.selectByValue(args.get("xAxis"));
-        globalFilter.handleHistoryArguments(args, "globalFilter");
-        seriesSelector.handleHistoryArguments(args);
-        
-        refreshSeries();
-        noNormalizeMultiple.setValue(true);
-        normalizeSeriesSelect.setEnabled(false);
-        normalizeXSelect.setEnabled(false);
-        String normalizeString = args.get("normalize");
-        if (normalizeString != null) {
-            if (normalizeString.equals(NORMALIZE_SINGLE)) {
-                noNormalizeSingle.setValue(true);
-            } else if (normalizeString.equals(NORMALIZE_FIRST)) {
-                normalizeFirst.setValue(true);
-            } else if (normalizeString.startsWith(NORMALIZE_SERIES_PREFIX)) {
-                normalizeSeries.setValue(true);
-                String series = normalizeString.substring(NORMALIZE_SERIES_PREFIX.length());
-                for (int i = 0; i < normalizeSeriesSelect.getItemCount(); i++) {
-                    if (normalizeSeriesSelect.getValue(i).equals(series)) {
-                        normalizeSeriesSelect.setSelectedIndex(i);
-                        break;
-                    }
-                }
-                normalizeSeriesSelect.setEnabled(true);
-            } else if (normalizeString.startsWith(NORMALIZE_X_PREFIX)) {
-                normalizeX.setValue(true);
-                normalizeXSelect.setText(normalizeString.substring(NORMALIZE_X_PREFIX.length()));
-                normalizeXSelect.setEnabled(true);
-            }
-        }
-        checkNormalizeInput();
-        checkInvertible();
-
-        setVisible(true);
-    }
-    
-    @Override
-    protected void addAdditionalEmbeddingParams(JSONObject params) {
-        params.put("graph_type", new JSONString("metrics"));
-        params.put("params", buildParams());
-    }
-    
-    private void refreshSeries() {
-        String selectedValue = normalizeSeriesSelect.getSelectedValue();
-        normalizeSeriesSelect.clear();
-        for (Series selector : seriesSelector.getAllSeries()) {
-            normalizeSeriesSelect.addItem(selector.getName());
-            if (selector.getName().equals(selectedValue)) {
-                normalizeSeriesSelect.setSelectedIndex(normalizeSeriesSelect.getItemCount() - 1);
-            }
-        }
-    }
-
-    // Disable "No Normalization (multiple)" for bar charts
-    private void checkNormalizeInput() {
-        if (plotSelector.getValue(plotSelector.getSelectedIndex()).equals("Line")) {
-            noNormalizeMultiple.setEnabled(true);
-        } else {
-            noNormalizeMultiple.setEnabled(false);
-            if (noNormalizeMultiple.getValue()) {
-                noNormalizeSingle.setValue(true);
-            }
-        }
-    }
-    
-    private JSONObject buildQueries() {
-        List<Series> seriesList = seriesSelector.getAllSeries();
-        JSONObject queries = new JSONObject();
-        StringBuilder sql = new StringBuilder();
-        
-        sql.append("SELECT ");
-        sql.append(xAxis.getSelectedValue());
-        for (Series series : seriesList) {
-            addSeriesSelects(series, sql);
-        }
-        
-        sql.append(" FROM tko_perf_view_2");
-            
-        String xFilterString = globalFilter.getFilterString();
-        if (xFilterString.equals("")) {
-            NotifyManager.getInstance().showError("You must enter a global filter");
-            return null;
-        }
-        
-        sql.append(" WHERE ");
-        sql.append(xFilterString);
-
-        sql.append(" GROUP BY ");
-        sql.append(xAxis.getSelectedValue());
-        queries.put("__main__", new JSONString(sql.toString()));
-        
-        for (Series series : seriesList) {
-            String drilldownQuery = getSeriesDrilldownQuery(series, xFilterString);
-            queries.put("__" + series.getName() + "__", new JSONString(drilldownQuery));
-        }
-        
-        return queries;
-    }
-
-    private String getSeriesDrilldownQuery(Series series, String xFilterString) {
-        StringBuilder sql;
-        sql = new StringBuilder();
-        ExtendedListBox valueSelector = series.getDBColumnSelector();
-        
-        sql.append("SELECT test_idx, ");
-        sql.append(valueSelector.getSelectedValue());
-        sql.append(" FROM tko_perf_view_2 WHERE ");
-        
-        String seriesFilter = series.getFilterString();
-        if (!xFilterString.equals("") || !seriesFilter.equals("")) {
-            sql.append(xFilterString.replace("%", "%%"));
-            if (!xFilterString.equals("") && !seriesFilter.equals("")) {
-                sql.append(" AND ");
-            }
-            sql.append(seriesFilter.replace("%", "%%"));
-            sql.append(" AND ");
-        }
-        
-        sql.append(xAxis.getSelectedValue());
-        sql.append(" = %s ORDER BY ");
-        sql.append(valueSelector.getSelectedValue());
-        return sql.toString();
-    }
-
-    private void addSeriesSelects(Series series, StringBuilder sql) {
-        ExtendedListBox valueSelector = series.getDBColumnSelector();
-        
-        StringBuilder ifClause = new StringBuilder();
-        String seriesFilter = series.getFilterString();
-        if (!seriesFilter.equals("")) {
-            ifClause.append("IF(");
-            ifClause.append(seriesFilter);
-            ifClause.append(", ");
-        }
-        ifClause.append(valueSelector.getSelectedValue());
-        if (!seriesFilter.equals("")) {
-            ifClause.append(", NULL)");   
-        }
-        
-        sql.append(", ");
-        sql.append(series.getAggregation());
-        sql.append(ifClause.toString());
-        sql.append(") '");
-        sql.append(series.getName());
-        sql.append("'");
-        if (series.wantErrorBars()) {
-            sql.append(", STDDEV(");
-            sql.append(ifClause.toString());
-            sql.append(") 'errors-");
-            sql.append(series.getName());
-            sql.append("'");
-        }
-    }
-    
-    // Disable the "Invert y-axis" checkboxes if inversion doesn't make sense
-    private void checkInvertible() {
-        boolean invertible = noNormalizeMultiple.getValue() || normalizeFirst.getValue()
-                             || normalizeX.getValue();
-        seriesSelector.setInvertible(invertible);
-    }
-    
-    @Override
-    protected JSONObject buildParams() {
-        JSONObject queries = buildQueries();
-        if (queries == null) {
-            return null;
-        }
-        
-        Map<String, String> params = new HashMap<String, String>();
-        String plot = plotSelector.getSelectedValue();
-        params.put("plot", plot);
-        addNormalizeParameter(plot, params);
-
-        JSONObject jsonParams = Utils.mapToJsonObject(params);
-        jsonParams.put("invert", Utils.stringsToJSON(seriesSelector.getInverted()));
-        jsonParams.put("queries", queries);
-        return jsonParams;
-    }
-
-    @Override
-    public String getFrontendId() {
-        return "metrics_plot";
-    }
-}
diff --git a/frontend/client/src/autotest/tko/Plot.java b/frontend/client/src/autotest/tko/Plot.java
deleted file mode 100644
index bacf01c..0000000
--- a/frontend/client/src/autotest/tko/Plot.java
+++ /dev/null
@@ -1,113 +0,0 @@
-package autotest.tko;
-
-import autotest.common.JsonRpcCallback;
-import autotest.common.JsonRpcProxy;
-import autotest.common.Utils;
-import autotest.tko.TableView.TableSwitchListener;
-
-import com.google.gwt.core.client.GWT;
-import com.google.gwt.core.client.JavaScriptObject;
-import com.google.gwt.core.client.GWT.UncaughtExceptionHandler;
-import com.google.gwt.json.client.JSONObject;
-import com.google.gwt.json.client.JSONString;
-import com.google.gwt.json.client.JSONValue;
-import com.google.gwt.user.client.ui.Composite;
-import com.google.gwt.user.client.ui.HTML;
-
-abstract class Plot extends Composite {
-    private static final String CALLBACK_PREFIX = "__plot_drilldown";
-
-    private static int callbackNameCounter = 0;
-    protected final static JsonRpcProxy rpcProxy = JsonRpcProxy.getProxy();
-
-    private String rpcName;
-    private HTML plotElement = new HTML();
-    protected TableSwitchListener listener;
-
-    private String callbackName;
-
-    private static class DummyRpcCallback extends JsonRpcCallback {
-        @Override
-        public void onSuccess(JSONValue result) {}
-    }
-
-    public Plot(String rpcName) {
-        this.rpcName = rpcName;
-        this.callbackName = getFreshCallbackName();
-        initWidget(plotElement);
-    }
-    
-    private static String getFreshCallbackName() {
-        callbackNameCounter++;
-        return CALLBACK_PREFIX + callbackNameCounter;
-    }
-
-    /**
-     * This function is called at initialization time and allows the plot to put native 
-     * callbacks in place for drilldown functionality from graphs.
-     */
-    public native void setDrilldownTrigger() /*-{
-        var instance = this;
-        var name = this.@autotest.tko.Plot::callbackName;
-        $wnd[name] = function(drilldownParams) {
-            instance.@autotest.tko.Plot::showDrilldown(Lcom/google/gwt/core/client/JavaScriptObject;)(drilldownParams);
-        }
-    }-*/;
-
-    /**
-     * Get a native JS object that acts as a proxy to this object.  Currently the only exposed
-     * method is refresh(params), where params is a JS object.  This is only necessary for allowing
-     * externally-written native code to use this object without having to write out the full JSNI
-     * method call syntax.
-     */
-    public native JavaScriptObject getNativeProxy() /*-{
-        var instance = this;
-        return {
-            refresh: function(params) {
-                jsonObjectParams = @com.google.gwt.json.client.JSONObject::new(Lcom/google/gwt/core/client/JavaScriptObject;)(params);
-                instance.@autotest.tko.Plot::refresh(Lcom/google/gwt/json/client/JSONObject;)(jsonObjectParams);
-            }
-        };
-    }-*/;
-
-    @SuppressWarnings("unused") // called from native code (see setDrilldownTrigger)
-    private void showDrilldown(JavaScriptObject drilldownParamsJso) {
-        UncaughtExceptionHandler handler = GWT.getUncaughtExceptionHandler();
-        if (handler == null) {
-            showDrilldownImpl(new JSONObject(drilldownParamsJso));
-            return;
-        }
-
-        try {
-            showDrilldownImpl(new JSONObject(drilldownParamsJso));
-        } catch (Throwable throwable) {
-            handler.onUncaughtException(throwable);
-        }
-    }
-
-    protected abstract void showDrilldownImpl(JSONObject drilldownParams);
-
-    public void refresh(JSONObject params, final JsonRpcCallback callback) {
-        params.put("drilldown_callback", new JSONString(callbackName));
-        rpcProxy.rpcCall(rpcName, params, new JsonRpcCallback() {
-            @Override
-            public void onSuccess(JSONValue result) {
-                plotElement.setHTML(Utils.jsonToString(result));
-                callback.onSuccess(result);
-            }
-
-            @Override
-            public void onError(JSONObject errorObject) {
-                callback.onError(errorObject);
-            }
-        });
-    }
-
-    public void refresh(JSONObject params) {
-        refresh(params, new DummyRpcCallback());
-    }
-
-    public void setListener(TableSwitchListener listener) {
-        this.listener = listener;
-    }
-}
diff --git a/frontend/client/src/autotest/tko/TkoClient.java b/frontend/client/src/autotest/tko/TkoClient.java
index f9fb41c..c738bb6 100644
--- a/frontend/client/src/autotest/tko/TkoClient.java
+++ b/frontend/client/src/autotest/tko/TkoClient.java
@@ -19,7 +19,6 @@
     private CommonPanel commonPanel;
     private TabView spreadsheetView;
     private TableView tableView;
-    private GraphingView graphingView;
     private TestDetailView detailView;
     
     private CustomTabPanel mainTabPanel = new CustomTabPanel();
@@ -44,13 +43,11 @@
         commonPanel = CommonPanel.getPanel();
         spreadsheetView = new SpreadsheetView(this);
         tableView = new TableView(this);
-        graphingView = new GraphingView(this);
         detailView = TkoUtils.factory.getTestDetailView();
         
         mainTabPanel.getCommonAreaPanel().add(commonPanel);
         mainTabPanel.addTabView(spreadsheetView);
         mainTabPanel.addTabView(tableView);
-        mainTabPanel.addTabView(graphingView);
         mainTabPanel.addTabView(detailView);
         
         savedQueriesControl = new SavedQueriesControl();
diff --git a/frontend/tko/graphing_utils.py b/frontend/tko/graphing_utils.py
deleted file mode 100644
index 9d1a9fb..0000000
--- a/frontend/tko/graphing_utils.py
+++ /dev/null
@@ -1,861 +0,0 @@
-# pylint: disable-msg=C0111
-
-import base64, os, tempfile, pickle, datetime, django.db
-import os.path, getpass
-from math import sqrt
-
-# When you import matplotlib, it tries to write some temp files for better
-# performance, and it does that to the directory in MPLCONFIGDIR, or, if that
-# doesn't exist, the home directory. Problem is, the home directory is not
-# writable when running under Apache, and matplotlib's not smart enough to
-# handle that. It does appear smart enough to handle the files going
-# away after they are written, though.
-
-temp_dir = os.path.join(tempfile.gettempdir(),
-                        '.matplotlib-%s' % getpass.getuser())
-if not os.path.exists(temp_dir):
-    os.mkdir(temp_dir)
-os.environ['MPLCONFIGDIR'] = temp_dir
-
-try:
-    import matplotlib
-    matplotlib.use('Agg')
-    import matplotlib.figure, matplotlib.backends.backend_agg
-    import StringIO, colorsys, PIL.Image, PIL.ImageChops
-except ImportError:
-    # Do nothing, in case this is part of a unit test, so the unit test
-    # can proceed.
-    pass
-
-from autotest_lib.frontend.afe import readonly_connection
-from autotest_lib.frontend.afe.model_logic import ValidationError
-from json import encoder
-from autotest_lib.client.common_lib import global_config
-from autotest_lib.frontend.tko import models, tko_rpc_utils
-
-_FIGURE_DPI = 100
-_FIGURE_WIDTH_IN = 10
-_FIGURE_BOTTOM_PADDING_IN = 2 # for x-axis labels
-
-_SINGLE_PLOT_HEIGHT = 6
-_MULTIPLE_PLOT_HEIGHT_PER_PLOT = 4
-
-_MULTIPLE_PLOT_MARKER_TYPE = 'o'
-_MULTIPLE_PLOT_MARKER_SIZE = 4
-_SINGLE_PLOT_STYLE = 'bs-' # blue squares with lines connecting
-_SINGLE_PLOT_ERROR_BAR_COLOR = 'r'
-
-_LEGEND_FONT_SIZE = 'xx-small'
-_LEGEND_HANDLE_LENGTH = 0.03
-_LEGEND_NUM_POINTS = 3
-_LEGEND_MARKER_TYPE = 'o'
-
-_LINE_XTICK_LABELS_SIZE = 'x-small'
-_BAR_XTICK_LABELS_SIZE = 8
-
-_json_encoder = encoder.JSONEncoder()
-
-class NoDataError(Exception):
-    """\
-    Exception to raise if the graphing query returned an empty resultset.
-    """
-
-
-def _colors(n):
-    """\
-    Generator function for creating n colors. The return value is a tuple
-    representing the RGB of the color.
-    """
-    for i in xrange(n):
-        yield colorsys.hsv_to_rgb(float(i) / n, 1.0, 1.0)
-
-
-def _resort(kernel_labels, list_to_sort):
-    """\
-    Resorts a list, using a list of kernel strings as the keys. Returns the
-    resorted list.
-    """
-
-    labels = [tko_rpc_utils.KernelString(label) for label in kernel_labels]
-    resorted_pairs = sorted(zip(labels, list_to_sort))
-
-    # We only want the resorted list; we are not interested in the kernel
-    # strings.
-    return [pair[1] for pair in resorted_pairs]
-
-
-def _quote(string):
-    return "%s%s%s" % ("'", string.replace("'", r"\'"), "'")
-
-
-_HTML_TEMPLATE = """\
-<html><head></head><body>
-<img src="data:image/png;base64,%s" usemap="#%s"
-  border="0" alt="graph">
-<map name="%s">%s</map>
-</body></html>"""
-
-_AREA_TEMPLATE = """\
-<area shape="rect" coords="%i,%i,%i,%i" title="%s"
-href="#"
-onclick="%s(%s); return false;">"""
-
-
-class MetricsPlot(object):
-    def __init__(self, query_dict, plot_type, inverted_series, normalize_to,
-                 drilldown_callback):
-        """
-        query_dict: dictionary containing the main query and the drilldown
-            queries.  The main query returns a row for each x value.  The first
-            column contains the x-axis label.  Subsequent columns contain data
-            for each series, named by the column names.  A column named
-            'errors-<x>' will be interpreted as errors for the series named <x>.
-
-        plot_type: 'Line' or 'Bar', depending on the plot type the user wants
-
-        inverted_series: list of series that should be plotted on an inverted
-            y-axis
-
-        normalize_to:
-            None - do not normalize
-            'first' - normalize against the first data point
-            'x__%s' - normalize against the x-axis value %s
-            'series__%s' - normalize against the series %s
-
-        drilldown_callback: name of drilldown callback method.
-        """
-        self.query_dict = query_dict
-        if plot_type == 'Line':
-            self.is_line = True
-        elif plot_type == 'Bar':
-            self.is_line = False
-        else:
-            raise ValidationError({'plot' : 'Plot must be either Line or Bar'})
-        self.plot_type = plot_type
-        self.inverted_series = inverted_series
-        self.normalize_to = normalize_to
-        if self.normalize_to is None:
-            self.normalize_to = ''
-        self.drilldown_callback = drilldown_callback
-
-
-class QualificationHistogram(object):
-    def __init__(self, query, filter_string, interval, drilldown_callback):
-        """
-        query: the main query to retrieve the pass rate information.  The first
-            column contains the hostnames of all the machines that satisfied the
-            global filter. The second column (titled 'total') contains the total
-            number of tests that ran on that machine and satisfied the global
-            filter. The third column (titled 'good') contains the number of
-            those tests that passed on that machine.
-
-        filter_string: filter to apply to the common global filter to show the
-                       Table View drilldown of a histogram bucket
-
-        interval: interval for each bucket. E.g., 10 means that buckets should
-                  be 0-10%, 10%-20%, ...
-
-        """
-        self.query = query
-        self.filter_string = filter_string
-        self.interval = interval
-        self.drilldown_callback = drilldown_callback
-
-
-def _create_figure(height_inches):
-    """\
-    Creates an instance of matplotlib.figure.Figure, given the height in inches.
-    Returns the figure and the height in pixels.
-    """
-
-    fig = matplotlib.figure.Figure(
-        figsize=(_FIGURE_WIDTH_IN, height_inches + _FIGURE_BOTTOM_PADDING_IN),
-        dpi=_FIGURE_DPI, facecolor='white')
-    fig.subplots_adjust(bottom=float(_FIGURE_BOTTOM_PADDING_IN) / height_inches)
-    return (fig, fig.get_figheight() * _FIGURE_DPI)
-
-
-def _create_line(plots, labels, plot_info):
-    """\
-    Given all the data for the metrics, create a line plot.
-
-    plots: list of dicts containing the plot data. Each dict contains:
-            x: list of x-values for the plot
-            y: list of corresponding y-values
-            errors: errors for each data point, or None if no error information
-                    available
-            label: plot title
-    labels: list of x-tick labels
-    plot_info: a MetricsPlot
-    """
-    # when we're doing any kind of normalization, all series get put into a
-    # single plot
-    single = bool(plot_info.normalize_to)
-
-    area_data = []
-    lines = []
-    if single:
-        plot_height = _SINGLE_PLOT_HEIGHT
-    else:
-        plot_height = _MULTIPLE_PLOT_HEIGHT_PER_PLOT * len(plots)
-    figure, height = _create_figure(plot_height)
-
-    if single:
-        subplot = figure.add_subplot(1, 1, 1)
-
-    # Plot all the data
-    for plot_index, (plot, color) in enumerate(zip(plots, _colors(len(plots)))):
-        needs_invert = (plot['label'] in plot_info.inverted_series)
-
-        # Add a new subplot, if user wants multiple subplots
-        # Also handle axis inversion for subplots here
-        if not single:
-            subplot = figure.add_subplot(len(plots), 1, plot_index + 1)
-            subplot.set_title(plot['label'])
-            if needs_invert:
-                # for separate plots, just invert the y-axis
-                subplot.set_ylim(1, 0)
-        elif needs_invert:
-            # for a shared plot (normalized data), need to invert the y values
-            # manually, since all plots share a y-axis
-            plot['y'] = [-y for y in plot['y']]
-
-        # Plot the series
-        subplot.set_xticks(range(0, len(labels)))
-        subplot.set_xlim(-1, len(labels))
-        if single:
-            lines += subplot.plot(plot['x'], plot['y'], label=plot['label'],
-                                  marker=_MULTIPLE_PLOT_MARKER_TYPE,
-                                  markersize=_MULTIPLE_PLOT_MARKER_SIZE)
-            error_bar_color = lines[-1].get_color()
-        else:
-            lines += subplot.plot(plot['x'], plot['y'], _SINGLE_PLOT_STYLE,
-                                  label=plot['label'])
-            error_bar_color = _SINGLE_PLOT_ERROR_BAR_COLOR
-        if plot['errors']:
-            subplot.errorbar(plot['x'], plot['y'], linestyle='None',
-                             yerr=plot['errors'], color=error_bar_color)
-        subplot.set_xticklabels([])
-
-    # Construct the information for the drilldowns.
-    # We need to do this in a separate loop so that all the data is in
-    # matplotlib before we start calling transform(); otherwise, it will return
-    # incorrect data because it hasn't finished adjusting axis limits.
-    for line in lines:
-
-        # Get the pixel coordinates of each point on the figure
-        x = line.get_xdata()
-        y = line.get_ydata()
-        label = line.get_label()
-        icoords = line.get_transform().transform(zip(x,y))
-
-        # Get the appropriate drilldown query
-        drill = plot_info.query_dict['__' + label + '__']
-
-        # Set the title attributes (hover-over tool-tips)
-        x_labels = [labels[x_val] for x_val in x]
-        titles = ['%s - %s: %f' % (label, x_label, y_val)
-                  for x_label, y_val in zip(x_labels, y)]
-
-        # Get the appropriate parameters for the drilldown query
-        params = [dict(query=drill, series=line.get_label(), param=x_label)
-                  for x_label in x_labels]
-
-        area_data += [dict(left=ix - 5, top=height - iy - 5,
-                           right=ix + 5, bottom=height - iy + 5,
-                           title= title,
-                           callback=plot_info.drilldown_callback,
-                           callback_arguments=param_dict)
-                      for (ix, iy), title, param_dict
-                      in zip(icoords, titles, params)]
-
-    subplot.set_xticklabels(labels, rotation=90, size=_LINE_XTICK_LABELS_SIZE)
-
-    # Show the legend if there are not multiple subplots
-    if single:
-        font_properties = matplotlib.font_manager.FontProperties(
-            size=_LEGEND_FONT_SIZE)
-        legend = figure.legend(lines, [plot['label'] for plot in plots],
-                               prop=font_properties,
-                               handlelen=_LEGEND_HANDLE_LENGTH,
-                               numpoints=_LEGEND_NUM_POINTS)
-        # Workaround for matplotlib not keeping all line markers in the legend -
-        # it seems if we don't do this, matplotlib won't keep all the line
-        # markers in the legend.
-        for line in legend.get_lines():
-            line.set_marker(_LEGEND_MARKER_TYPE)
-
-    return (figure, area_data)
-
-
-def _get_adjusted_bar(x, bar_width, series_index, num_plots):
-    """\
-    Adjust the list 'x' to take the multiple series into account. Each series
-    should be shifted such that the middle series lies at the appropriate x-axis
-    tick with the other bars around it.  For example, if we had four series
-    (i.e. four bars per x value), we want to shift the left edges of the bars as
-    such:
-    Bar 1: -2 * width
-    Bar 2: -width
-    Bar 3: none
-    Bar 4: width
-    """
-    adjust = (-0.5 * num_plots - 1 + series_index) * bar_width
-    return [x_val + adjust for x_val in x]
-
-
-# TODO(showard): merge much of this function with _create_line by extracting and
-# parameterizing methods
-def _create_bar(plots, labels, plot_info):
-    """\
-    Given all the data for the metrics, create a line plot.
-
-    plots: list of dicts containing the plot data.
-            x: list of x-values for the plot
-            y: list of corresponding y-values
-            errors: errors for each data point, or None if no error information
-                    available
-            label: plot title
-    labels: list of x-tick labels
-    plot_info: a MetricsPlot
-    """
-
-    area_data = []
-    bars = []
-    figure, height = _create_figure(_SINGLE_PLOT_HEIGHT)
-
-    # Set up the plot
-    subplot = figure.add_subplot(1, 1, 1)
-    subplot.set_xticks(range(0, len(labels)))
-    subplot.set_xlim(-1, len(labels))
-    subplot.set_xticklabels(labels, rotation=90, size=_BAR_XTICK_LABELS_SIZE)
-    # draw a bold line at y=0, making it easier to tell if bars are dipping
-    # below the axis or not.
-    subplot.axhline(linewidth=2, color='black')
-
-    # width here is the width for each bar in the plot. Matplotlib default is
-    # 0.8.
-    width = 0.8 / len(plots)
-
-    # Plot the data
-    for plot_index, (plot, color) in enumerate(zip(plots, _colors(len(plots)))):
-        # Invert the y-axis if needed
-        if plot['label'] in plot_info.inverted_series:
-            plot['y'] = [-y for y in plot['y']]
-
-        adjusted_x = _get_adjusted_bar(plot['x'], width, plot_index + 1,
-                                       len(plots))
-        bar_data = subplot.bar(adjusted_x, plot['y'],
-                               width=width, yerr=plot['errors'],
-                               facecolor=color,
-                               label=plot['label'])
-        bars.append(bar_data[0])
-
-    # Construct the information for the drilldowns.
-    # See comment in _create_line for why we need a separate loop to do this.
-    for plot_index, plot in enumerate(plots):
-        adjusted_x = _get_adjusted_bar(plot['x'], width, plot_index + 1,
-                                       len(plots))
-
-        # Let matplotlib plot the data, so that we can get the data-to-image
-        # coordinate transforms
-        line = subplot.plot(adjusted_x, plot['y'], linestyle='None')[0]
-        label = plot['label']
-        upper_left_coords = line.get_transform().transform(zip(adjusted_x,
-                                                               plot['y']))
-        bottom_right_coords = line.get_transform().transform(
-            [(x + width, 0) for x in adjusted_x])
-
-        # Get the drilldown query
-        drill = plot_info.query_dict['__' + label + '__']
-
-        # Set the title attributes
-        x_labels = [labels[x] for x in plot['x']]
-        titles = ['%s - %s: %f' % (plot['label'], label, y)
-                  for label, y in zip(x_labels, plot['y'])]
-        params = [dict(query=drill, series=plot['label'], param=x_label)
-                  for x_label in x_labels]
-        area_data += [dict(left=ulx, top=height - uly,
-                           right=brx, bottom=height - bry,
-                           title=title,
-                           callback=plot_info.drilldown_callback,
-                           callback_arguments=param_dict)
-                      for (ulx, uly), (brx, bry), title, param_dict
-                      in zip(upper_left_coords, bottom_right_coords, titles,
-                             params)]
-
-    figure.legend(bars, [plot['label'] for plot in plots])
-    return (figure, area_data)
-
-
-def _normalize(data_values, data_errors, base_values, base_errors):
-    """\
-    Normalize the data against a baseline.
-
-    data_values: y-values for the to-be-normalized data
-    data_errors: standard deviations for the to-be-normalized data
-    base_values: list of values normalize against
-    base_errors: list of standard deviations for those base values
-    """
-    values = []
-    for value, base in zip(data_values, base_values):
-        try:
-            values.append(100 * (value - base) / base)
-        except ZeroDivisionError:
-            # Base is 0.0 so just simplify:
-            #   If value < base: append -100.0;
-            #   If value == base: append 0.0 (obvious); and
-            #   If value > base: append 100.0.
-            values.append(100 * float(cmp(value, base)))
-
-    # Based on error for f(x,y) = 100 * (x - y) / y
-    if data_errors:
-        if not base_errors:
-            base_errors = [0] * len(data_errors)
-        errors = []
-        for data, error, base_value, base_error in zip(
-                data_values, data_errors, base_values, base_errors):
-            try:
-                errors.append(sqrt(error**2 * (100 / base_value)**2
-                        + base_error**2 * (100 * data / base_value**2)**2
-                        + error * base_error * (100 / base_value**2)**2))
-            except ZeroDivisionError:
-                # Again, base is 0.0 so do the simple thing.
-                errors.append(100 * abs(error))
-    else:
-        errors = None
-
-    return (values, errors)
-
-
-def _create_png(figure):
-    """\
-    Given the matplotlib figure, generate the PNG data for it.
-    """
-
-    # Draw the image
-    canvas = matplotlib.backends.backend_agg.FigureCanvasAgg(figure)
-    canvas.draw()
-    size = canvas.get_renderer().get_canvas_width_height()
-    image_as_string = canvas.tostring_rgb()
-    image = PIL.Image.fromstring('RGB', size, image_as_string, 'raw', 'RGB', 0,
-                                 1)
-    image_background = PIL.Image.new(image.mode, image.size,
-                                     figure.get_facecolor())
-
-    # Crop the image to remove surrounding whitespace
-    non_whitespace = PIL.ImageChops.difference(image, image_background)
-    bounding_box = non_whitespace.getbbox()
-    image = image.crop(bounding_box)
-
-    image_data = StringIO.StringIO()
-    image.save(image_data, format='PNG')
-
-    return image_data.getvalue(), bounding_box
-
-
-def _create_image_html(figure, area_data, plot_info):
-    """\
-    Given the figure and drilldown data, construct the HTML that will render the
-    graph as a PNG image, and attach the image map to that image.
-
-    figure: figure containing the drawn plot(s)
-    area_data: list of parameters for each area of the image map. See the
-               definition of the template string '_AREA_TEMPLATE'
-    plot_info: a MetricsPlot or QualHistogram
-    """
-
-    png, bbox = _create_png(figure)
-
-    # Construct the list of image map areas
-    areas = [_AREA_TEMPLATE %
-             (data['left'] - bbox[0], data['top'] - bbox[1],
-              data['right'] - bbox[0], data['bottom'] - bbox[1],
-              data['title'], data['callback'],
-              _json_encoder.encode(data['callback_arguments'])
-                  .replace('"', '&quot;'))
-             for data in area_data]
-
-    map_name = plot_info.drilldown_callback + '_map'
-    return _HTML_TEMPLATE % (base64.b64encode(png), map_name, map_name,
-                             '\n'.join(areas))
-
-
-def _find_plot_by_label(plots, label):
-    for index, plot in enumerate(plots):
-        if plot['label'] == label:
-            return index
-    raise ValueError('no plot labeled "%s" found' % label)
-
-
-def _normalize_to_series(plots, base_series):
-    base_series_index = _find_plot_by_label(plots, base_series)
-    base_plot = plots[base_series_index]
-    base_xs = base_plot['x']
-    base_values = base_plot['y']
-    base_errors = base_plot['errors']
-    del plots[base_series_index]
-
-    for plot in plots:
-        old_xs, old_values, old_errors = plot['x'], plot['y'], plot['errors']
-        new_xs, new_values, new_errors = [], [], []
-        new_base_values, new_base_errors = [], []
-        # Select only points in the to-be-normalized data that have a
-        # corresponding baseline value
-        for index, x_value in enumerate(old_xs):
-            try:
-                base_index = base_xs.index(x_value)
-            except ValueError:
-                continue
-
-            new_xs.append(x_value)
-            new_values.append(old_values[index])
-            new_base_values.append(base_values[base_index])
-            if old_errors:
-                new_errors.append(old_errors[index])
-                new_base_errors.append(base_errors[base_index])
-
-        if not new_xs:
-            raise NoDataError('No normalizable data for series ' +
-                              plot['label'])
-        plot['x'] = new_xs
-        plot['y'] = new_values
-        if old_errors:
-            plot['errors'] = new_errors
-
-        plot['y'], plot['errors'] = _normalize(plot['y'], plot['errors'],
-                                               new_base_values,
-                                               new_base_errors)
-
-
-def _create_metrics_plot_helper(plot_info, extra_text=None):
-    """
-    Create a metrics plot of the given plot data.
-    plot_info: a MetricsPlot object.
-    extra_text: text to show at the uppper-left of the graph
-
-    TODO(showard): move some/all of this logic into methods on MetricsPlot
-    """
-    query = plot_info.query_dict['__main__']
-    cursor = readonly_connection.cursor()
-    cursor.execute(query)
-
-    if not cursor.rowcount:
-        raise NoDataError('query did not return any data')
-    rows = cursor.fetchall()
-    # "transpose" rows, so columns[0] is all the values from the first column,
-    # etc.
-    columns = zip(*rows)
-
-    plots = []
-    labels = [str(label) for label in columns[0]]
-    needs_resort = (cursor.description[0][0] == 'kernel')
-
-    # Collect all the data for the plot
-    col = 1
-    while col < len(cursor.description):
-        y = columns[col]
-        label = cursor.description[col][0]
-        col += 1
-        if (col < len(cursor.description) and
-            'errors-' + label == cursor.description[col][0]):
-            errors = columns[col]
-            col += 1
-        else:
-            errors = None
-        if needs_resort:
-            y = _resort(labels, y)
-            if errors:
-                errors = _resort(labels, errors)
-
-        x = [index for index, value in enumerate(y) if value is not None]
-        if not x:
-            raise NoDataError('No data for series ' + label)
-        y = [y[i] for i in x]
-        if errors:
-            errors = [errors[i] for i in x]
-        plots.append({
-            'label': label,
-            'x': x,
-            'y': y,
-            'errors': errors
-        })
-
-    if needs_resort:
-        labels = _resort(labels, labels)
-
-    # Normalize the data if necessary
-    normalize_to = plot_info.normalize_to
-    if normalize_to == 'first' or normalize_to.startswith('x__'):
-        if normalize_to != 'first':
-            baseline = normalize_to[3:]
-            try:
-                baseline_index = labels.index(baseline)
-            except ValueError:
-                raise ValidationError({
-                    'Normalize' : 'Invalid baseline %s' % baseline
-                    })
-        for plot in plots:
-            if normalize_to == 'first':
-                plot_index = 0
-            else:
-                try:
-                    plot_index = plot['x'].index(baseline_index)
-                # if the value is not found, then we cannot normalize
-                except ValueError:
-                    raise ValidationError({
-                        'Normalize' : ('%s does not have a value for %s'
-                                       % (plot['label'], normalize_to[3:]))
-                        })
-            base_values = [plot['y'][plot_index]] * len(plot['y'])
-            if plot['errors']:
-                base_errors = [plot['errors'][plot_index]] * len(plot['errors'])
-            plot['y'], plot['errors'] = _normalize(plot['y'], plot['errors'],
-                                                   base_values,
-                                                   None or base_errors)
-
-    elif normalize_to.startswith('series__'):
-        base_series = normalize_to[8:]
-        _normalize_to_series(plots, base_series)
-
-    # Call the appropriate function to draw the line or bar plot
-    if plot_info.is_line:
-        figure, area_data = _create_line(plots, labels, plot_info)
-    else:
-        figure, area_data = _create_bar(plots, labels, plot_info)
-
-    # TODO(showard): extract these magic numbers to named constants
-    if extra_text:
-        text_y = .95 - .0075 * len(plots)
-        figure.text(.1, text_y, extra_text, size='xx-small')
-
-    return (figure, area_data)
-
-
-def create_metrics_plot(query_dict, plot_type, inverted_series, normalize_to,
-                        drilldown_callback, extra_text=None):
-    plot_info = MetricsPlot(query_dict, plot_type, inverted_series,
-                            normalize_to, drilldown_callback)
-    figure, area_data = _create_metrics_plot_helper(plot_info, extra_text)
-    return _create_image_html(figure, area_data, plot_info)
-
-
-def _get_hostnames_in_bucket(hist_data, bucket):
-    """\
-    Get all the hostnames that constitute a particular bucket in the histogram.
-
-    hist_data: list containing tuples of (hostname, pass_rate)
-    bucket: tuple containing the (low, high) values of the target bucket
-    """
-
-    return [hostname for hostname, pass_rate in hist_data
-            if bucket[0] <= pass_rate < bucket[1]]
-
-
-def _create_qual_histogram_helper(plot_info, extra_text=None):
-    """\
-    Create a machine qualification histogram of the given data.
-
-    plot_info: a QualificationHistogram
-    extra_text: text to show at the upper-left of the graph
-
-    TODO(showard): move much or all of this into methods on
-    QualificationHistogram
-    """
-    cursor = readonly_connection.cursor()
-    cursor.execute(plot_info.query)
-
-    if not cursor.rowcount:
-        raise NoDataError('query did not return any data')
-
-    # Lists to store the plot data.
-    # hist_data store tuples of (hostname, pass_rate) for machines that have
-    #     pass rates between 0 and 100%, exclusive.
-    # no_tests is a list of machines that have run none of the selected tests
-    # no_pass is a list of machines with 0% pass rate
-    # perfect is a list of machines with a 100% pass rate
-    hist_data = []
-    no_tests = []
-    no_pass = []
-    perfect = []
-
-    # Construct the lists of data to plot
-    for hostname, total, good in cursor.fetchall():
-        if total == 0:
-            no_tests.append(hostname)
-            continue
-
-        if good == 0:
-            no_pass.append(hostname)
-        elif good == total:
-            perfect.append(hostname)
-        else:
-            percentage = 100.0 * good / total
-            hist_data.append((hostname, percentage))
-
-    interval = plot_info.interval
-    bins = range(0, 100, interval)
-    if bins[-1] != 100:
-        bins.append(bins[-1] + interval)
-
-    figure, height = _create_figure(_SINGLE_PLOT_HEIGHT)
-    subplot = figure.add_subplot(1, 1, 1)
-
-    # Plot the data and get all the bars plotted
-    _,_, bars = subplot.hist([data[1] for data in hist_data],
-                         bins=bins, align='left')
-    bars += subplot.bar([-interval], len(no_pass),
-                    width=interval, align='center')
-    bars += subplot.bar([bins[-1]], len(perfect),
-                    width=interval, align='center')
-    bars += subplot.bar([-3 * interval], len(no_tests),
-                    width=interval, align='center')
-
-    buckets = [(bin, min(bin + interval, 100)) for bin in bins[:-1]]
-    # set the x-axis range to cover all the normal bins plus the three "special"
-    # ones - N/A (3 intervals left), 0% (1 interval left) ,and 100% (far right)
-    subplot.set_xlim(-4 * interval, bins[-1] + interval)
-    subplot.set_xticks([-3 * interval, -interval] + bins + [100 + interval])
-    subplot.set_xticklabels(['N/A', '0%'] +
-                        ['%d%% - <%d%%' % bucket for bucket in buckets] +
-                        ['100%'], rotation=90, size='small')
-
-    # Find the coordinates on the image for each bar
-    x = []
-    y = []
-    for bar in bars:
-        x.append(bar.get_x())
-        y.append(bar.get_height())
-    f = subplot.plot(x, y, linestyle='None')[0]
-    upper_left_coords = f.get_transform().transform(zip(x, y))
-    bottom_right_coords = f.get_transform().transform(
-        [(x_val + interval, 0) for x_val in x])
-
-    # Set the title attributes
-    titles = ['%d%% - <%d%%: %d machines' % (bucket[0], bucket[1], y_val)
-              for bucket, y_val in zip(buckets, y)]
-    titles.append('0%%: %d machines' % len(no_pass))
-    titles.append('100%%: %d machines' % len(perfect))
-    titles.append('N/A: %d machines' % len(no_tests))
-
-    # Get the hostnames for each bucket in the histogram
-    names_list = [_get_hostnames_in_bucket(hist_data, bucket)
-                  for bucket in buckets]
-    names_list += [no_pass, perfect]
-
-    if plot_info.filter_string:
-        plot_info.filter_string += ' AND '
-
-    # Construct the list of drilldown parameters to be passed when the user
-    # clicks on the bar.
-    params = []
-    for names in names_list:
-        if names:
-            hostnames = ','.join(_quote(hostname) for hostname in names)
-            hostname_filter = 'hostname IN (%s)' % hostnames
-            full_filter = plot_info.filter_string + hostname_filter
-            params.append({'type': 'normal',
-                           'filterString': full_filter})
-        else:
-            params.append({'type': 'empty'})
-
-    params.append({'type': 'not_applicable',
-                   'hosts': '<br />'.join(no_tests)})
-
-    area_data = [dict(left=ulx, top=height - uly,
-                      right=brx, bottom=height - bry,
-                      title=title, callback=plot_info.drilldown_callback,
-                      callback_arguments=param_dict)
-                 for (ulx, uly), (brx, bry), title, param_dict
-                 in zip(upper_left_coords, bottom_right_coords, titles, params)]
-
-    # TODO(showard): extract these magic numbers to named constants
-    if extra_text:
-        figure.text(.1, .95, extra_text, size='xx-small')
-
-    return (figure, area_data)
-
-
-def create_qual_histogram(query, filter_string, interval, drilldown_callback,
-                          extra_text=None):
-    plot_info = QualificationHistogram(query, filter_string, interval,
-                                       drilldown_callback)
-    figure, area_data = _create_qual_histogram_helper(plot_info, extra_text)
-    return _create_image_html(figure, area_data, plot_info)
-
-
-def create_embedded_plot(model, update_time):
-    """\
-    Given an EmbeddedGraphingQuery object, generate the PNG image for it.
-
-    model: EmbeddedGraphingQuery object
-    update_time: 'Last updated' time
-    """
-
-    params = pickle.loads(model.params)
-    extra_text = 'Last updated: %s' % update_time
-
-    if model.graph_type == 'metrics':
-        plot_info = MetricsPlot(query_dict=params['queries'],
-                                plot_type=params['plot'],
-                                inverted_series=params['invert'],
-                                normalize_to=None,
-                                drilldown_callback='')
-        figure, areas_unused = _create_metrics_plot_helper(plot_info,
-                                                           extra_text)
-    elif model.graph_type == 'qual':
-        plot_info = QualificationHistogram(
-            query=params['query'], filter_string=params['filter_string'],
-            interval=params['interval'], drilldown_callback='')
-        figure, areas_unused = _create_qual_histogram_helper(plot_info,
-                                                             extra_text)
-    else:
-        raise ValueError('Invalid graph_type %s' % model.graph_type)
-
-    image, bounding_box_unused = _create_png(figure)
-    return image
-
-
-_cache_timeout = global_config.global_config.get_config_value(
-    'AUTOTEST_WEB', 'graph_cache_creation_timeout_minutes')
-
-
-def handle_plot_request(id, max_age):
-    """\
-    Given the embedding id of a graph, generate a PNG of the embedded graph
-    associated with that id.
-
-    id: id of the embedded graph
-    max_age: maximum age, in minutes, that a cached version should be held
-    """
-    model = models.EmbeddedGraphingQuery.objects.get(id=id)
-
-    # Check if the cached image needs to be updated
-    now = datetime.datetime.now()
-    update_time = model.last_updated + datetime.timedelta(minutes=int(max_age))
-    if now > update_time:
-        cursor = django.db.connection.cursor()
-
-        # We want this query to update the refresh_time only once, even if
-        # multiple threads are running it at the same time. That is, only the
-        # first thread will win the race, and it will be the one to update the
-        # cached image; all other threads will show that they updated 0 rows
-        query = """
-            UPDATE embedded_graphing_queries
-            SET refresh_time = NOW()
-            WHERE id = %s AND (
-                refresh_time IS NULL OR
-                refresh_time + INTERVAL %s MINUTE < NOW()
-            )
-        """
-        cursor.execute(query, (id, _cache_timeout))
-
-        # Only refresh the cached image if we were successful in updating the
-        # refresh time
-        if cursor.rowcount:
-            model.cached_png = create_embedded_plot(model, now.ctime())
-            model.last_updated = now
-            model.refresh_time = None
-            model.save()
-
-    return model.cached_png
diff --git a/frontend/tko/models.py b/frontend/tko/models.py
index 81e2928..de0c3ae 100644
--- a/frontend/tko/models.py
+++ b/frontend/tko/models.py
@@ -309,25 +309,6 @@
         db_table = 'tko_saved_queries'
 
 
-class EmbeddedGraphingQuery(dbmodels.Model, model_logic.ModelExtensions):
-    """Models an embedded graphing query."""
-    url_token = dbmodels.TextField(null=False, blank=False)
-    graph_type = dbmodels.CharField(max_length=16, null=False, blank=False)
-    params = dbmodels.TextField(null=False, blank=False)
-    last_updated = dbmodels.DateTimeField(null=False, blank=False,
-                                          editable=False)
-    # refresh_time shows the time at which a thread is updating the cached
-    # image, or NULL if no one is updating the image. This is used so that only
-    # one thread is updating the cached image at a time (see
-    # graphing_utils.handle_plot_request).
-    refresh_time = dbmodels.DateTimeField(editable=False)
-    cached_png = dbmodels.TextField(editable=False)
-
-    class Meta:
-        """Metadata for class EmbeddedGraphingQuery."""
-        db_table = 'tko_embedded_graphing_queries'
-
-
 # Views.
 
 class TestViewManager(TempManager):
diff --git a/frontend/tko/views.py b/frontend/tko/views.py
index 2b29c9f..2ea64b7 100644
--- a/frontend/tko/views.py
+++ b/frontend/tko/views.py
@@ -1,7 +1,6 @@
-import django.http
-from autotest_lib.frontend.tko import rpc_interface, graphing_utils
+from autotest_lib.frontend.tko import rpc_interface
 from autotest_lib.frontend.tko import csv_encoder
-from autotest_lib.frontend.afe import rpc_handler, rpc_utils
+from autotest_lib.frontend.afe import rpc_handler
 
 rpc_handler_obj = rpc_handler.RpcHandler((rpc_interface,),
                                          document_module=rpc_interface)
@@ -27,7 +26,4 @@
 
 
 def handle_plot(request):
-    id = request.GET['id']
-    max_age = request.GET['max_age']
-    return django.http.HttpResponse(
-        graphing_utils.handle_plot_request(id, max_age), mimetype='image/png')
+    raise DeprecationWarning()
