diff --git a/static/js/tracker/ac.js b/static/js/tracker/ac.js
new file mode 100644
index 0000000..4c0bf2b
--- /dev/null
+++ b/static/js/tracker/ac.js
@@ -0,0 +1,1010 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+/**
+ * An autocomplete library for javascript.
+ * Public API
+ * - _ac_install() install global handlers required for everything else to
+ *   function.
+ * - _ac_register(SC) register a store constructor (see below)
+ * - _ac_isCompleting() true iff focus is in an auto complete box and the user
+ *   has triggered completion with a keystroke, and completion has not been
+ *   cancelled (programatically or otherwise).
+ * - _ac_isCompleteListShowing() true if _as_isCompleting and the complete list
+ *   is visible to the user.
+ * - _ac_cancel() if completing, stop it, otherwise a no-op.
+ *
+ *
+ * A quick example
+ *     // an auto complete store
+ *     var myFavoritestAutoCompleteStore = new _AC_SimpleStore(
+ *       ['some', 'strings', 'to', 'complete']);
+ *
+ *     // a store constructor
+ *     _ac_register(function (inputNode, keyEvent) {
+ *         if (inputNode.id == 'my-auto-completing-check-box') {
+ *           return myFavoritestAutoCompleteStore;
+ *         }
+ *         return null;
+ *       });
+ *
+ *     <html>
+ *       <head>
+ *         <script type=text/javascript src=ac.js></script>
+ *       </head>
+ *       <body onload=_ac_install()>
+ *         <!-- the constructor above looks at the id.  It could as easily
+ *            - look at the class, name, or value.
+ *            - The autocomplete=off stops browser autocomplete from
+ *            - interfering with our autocomplete
+ *           -->
+ *         <input type=text id="my-auto-completing-check-box"
+ *          autocomplete=off>
+ *       </body>
+ *     </html>
+ *
+ *
+ * Concepts
+ * - Store Constructor function
+ *   A store constructor is a policy function with the signature
+ *     _AC_Store myStoreConstructor(
+ *       HtmlInputElement|HtmlTextAreaElement inputNode, Event keyEvent)
+ *   When a key event is received on a text input or text area, the autocomplete
+ *   library will try each of the store constructors in turn until it finds one
+ *   that returns an AC_Store which will be used for auto-completion of that
+ *   text box until focus is lost.
+ *
+ * - interface _AC_Store
+ *   An autocomplete store encapsulates all operations that affect how a
+ *   particular text node is autocompleted.  It has the following operations:
+ *   - String completable(String inputValue, int caret)
+ *     This method returns null if not completable or the section of inputValue
+ *     that is subject to completion.  If autocomplete works on items in a
+ *     comma separated list, then the input value "foo, ba" might yield "ba"
+ *     as the completable chunk since it is separated from its predecessor by
+ *     a comma.
+ *     caret is the position of the text cursor (caret) in the text input.
+ *   - _AC_Completion[] completions(String completable,
+ *                                  _AC_Completion[] toFilter)
+ *     This method returns null if there are no completions.  If toFilter is
+ *     not null or undefined, then this method may assume that toFilter was
+ *     returned as a set of completions that contain completable.
+ *   - String substitute(String inputValue, int caret,
+ *                       String completable, _AC_Completion completion)
+ *     returns the inputValue with the given completion substituted for the
+ *     given completable.  caret has the same meaning as in the
+ *     completable operation.
+ *   - String oncomplete(boolean completed, String key,
+ *                       HTMLElement element, String text)
+ *     This method is called when the user hits a completion key. The default
+ *     value is to do nothing, but you can override it if you want. Note that
+ *     key will be null if the user clicked on it to select
+ *   - Boolean autoselectFirstRow()
+ *     This method returns True by default, but subclasses can override it
+ *     to make autocomplete fields that require the user to press the down
+ *     arrow or do a mouseover once before any completion option is considered
+ *     to be selected.
+ *
+ * - class _AC_SimpleStore
+ *   An implementation of _AC_Store that completes a set of strings given at
+ *   construct time in a text field with a comma separated value.
+ *
+ * - struct _AC_Completion
+ *   a struct with two fields
+ *   - String value : the plain text completion value
+ *   - String html : the value, as html, with the completable in bold.
+ *
+ * Key Handling
+ * Several keys affect completion in an autocompleted input.
+ * ESC - the escape key cancels autocompleting.  The autocompletion will have
+ *   no effect on the focused textbox until it loses focus, regains it, and
+ *   a key is pressed.
+ * ENTER - completes using the currently selected completion, or if there is
+ *   only one, uses that completion.
+ * UP ARROW - selects the completion above the current selection.
+ * DOWN ARROW - selects the completion below the current selection.
+ *
+ *
+ * CSS styles
+ * The following CSS selector rules can be used to change the completion list
+ * look:
+ * #ac-list               style of the auto-complete list
+ * #ac-list .selected     style of the selected item
+ * #ac-list b             style of the matching text in a candidate completion
+ *
+ * Dependencies
+ * The library depends on the following libraries:
+ * javascript:base for definition of key constants and SetCursorPos
+ * javascript:shapes for nodeBounds()
+ */
+
+/**
+ * install global handlers required for the rest of the module to function.
+ */
+function _ac_install() {
+  ac_addHandler_(document.body, 'onkeydown', ac_keyevent_);
+  ac_addHandler_(document.body, 'onkeypress', ac_keyevent_);
+}
+
+/**
+ * register a store constructor
+ * @param storeConstructor a function like
+ *   _AC_Store myStoreConstructor(HtmlInputElement|HtmlTextArea, Event)
+ */
+function _ac_register(storeConstructor) {
+  // check that not already registered
+  for (let i = ac_storeConstructors.length; --i >= 0;) {
+    if (ac_storeConstructors[i] === storeConstructor) {
+      return;
+    }
+  }
+  ac_storeConstructors.push(storeConstructor);
+}
+
+/**
+ * may be attached as an onfocus handler to a text input to popup autocomplete
+ * immediately on the box gaining focus.
+ */
+function _ac_onfocus(event) {
+  ac_keyevent_(event);
+}
+
+/**
+ * true iff the autocomplete widget is currently active.
+ */
+function _ac_isCompleting() {
+  return !!ac_store && !ac_suppressCompletions;
+}
+
+/**
+ * true iff the completion list is displayed.
+ */
+function _ac_isCompleteListShowing() {
+  return !!ac_store && !ac_suppressCompletions && ac_completions &&
+    ac_completions.length;
+}
+
+/**
+ * cancel any autocomplete in progress.
+ */
+function _ac_cancel() {
+  ac_suppressCompletions = true;
+  ac_updateCompletionList(false);
+}
+
+/** add a handler without whacking any existing handler. @private */
+function ac_addHandler_(node, handlerName, handler) {
+  const oldHandler = node[handlerName];
+  if (!oldHandler) {
+    node[handlerName] = handler;
+  } else {
+    node[handlerName] = ac_fnchain_(node[handlerName], handler);
+  }
+  return oldHandler;
+}
+
+/** cancel the event. @private */
+function ac_cancelEvent_(event) {
+  if ('stopPropagation' in event) {
+    event.stopPropagation();
+  } else {
+    event.cancelBubble = true;
+  }
+
+  // This is handled in IE by returning false from the handler
+  if ('preventDefault' in event) {
+    event.preventDefault();
+  }
+}
+
+/** Call two functions, a and b, and return false if either one returns
+    false.  This is used as a primitive way to attach multiple event
+    handlers to an element without using addEventListener().   This
+    library predates the availablity of addEventListener().
+    @private
+*/
+function ac_fnchain_(a, b) {
+  return function() {
+    const ar = a.apply(this, arguments);
+    const br = b.apply(this, arguments);
+
+    // NOTE 1: (undefined && false) -> undefined
+    // NOTE 2: returning FALSE from a onkeypressed cancels it,
+    //         returning UNDEFINED does not.
+    // As such, we specifically look for falses here
+    if (ar === false || br === false) {
+      return false;
+    } else {
+      return true;
+    }
+  };
+}
+
+/** key press handler.  @private */
+function ac_keyevent_(event) {
+  event = event || window.event;
+
+  const source = getTargetFromEvent(event);
+  const isInput = 'INPUT' == source.tagName &&
+    source.type.match(/^text|email$/i);
+  const isTextarea = 'TEXTAREA' == source.tagName;
+  if (!isInput && !isTextarea) return true;
+
+  const key = event.key;
+  const isDown = event.type == 'keydown';
+  const isShiftKey = event.shiftKey;
+  let storeFound = true;
+
+  if ((source !== ac_focusedInput) || (ac_store === null)) {
+    ac_focusedInput = source;
+    storeFound = false;
+    if (ENTER_KEYNAME !== key && ESC_KEYNAME !== key) {
+      for (let i = 0; i < ac_storeConstructors.length; ++i) {
+        const store = (ac_storeConstructors[i])(source, event);
+        if (store) {
+          ac_store = store;
+          ac_store.setAvoid(event);
+          ac_oldBlurHandler = ac_addHandler_(
+              ac_focusedInput, 'onblur', _ac_ob);
+          storeFound = true;
+          break;
+        }
+      }
+
+      // There exists an odd condition where an edit box with autocomplete
+      // attached can be removed from the DOM without blur being called
+      // In which case we are left with a store around that will try to
+      // autocomplete the next edit box to receive focus. We need to clean
+      // this up
+
+      // If we can't find a store, force a blur
+      if (!storeFound) {
+        _ac_ob(null);
+      }
+    }
+    // ac-table rows need to be removed when switching to another input.
+    ac_updateCompletionList(false);
+  }
+  // If the user typed Esc when the auto-complete menu was not shown,
+  // then blur the input text field so that the user can use keyboard
+  // shortcuts.
+  const acList = document.getElementById('ac-list');
+  if (ESC_KEYNAME == key &&
+      (!acList || acList.style.display == 'none')) {
+    ac_focusedInput.blur();
+  }
+
+  if (!storeFound) return true;
+
+  const isCompletion = ac_store.isCompletionKey(key, isDown, isShiftKey);
+  const hasResults = ac_completions && (ac_completions.length > 0);
+  let cancelEvent = false;
+
+  if (isCompletion && hasResults) {
+    // Cancel any enter keystrokes if something is selected so that the
+    // browser doesn't go submitting the form.
+    cancelEvent = (!ac_suppressCompletions && !!ac_completions &&
+                      (ac_selected != -1));
+    window.setTimeout(function() {
+      if (ac_store) {
+        ac_handleKey_(key, isDown, isShiftKey);
+      }
+    }, 0);
+  } else if (!isCompletion) {
+    // Don't want to also blur the field. Up and down move the cursor (in
+    // Firefox) to the start/end of the field. We also don't want that while
+    // the list is showing.
+    cancelEvent = (key == ESC_KEYNAME ||
+                  key == DOWN_KEYNAME ||
+                  key == UP_KEYNAME);
+
+    window.setTimeout(function() {
+      if (ac_store) {
+        ac_handleKey_(key, isDown, isShiftKey);
+      }
+    }, 0);
+  } else { // implicit if (isCompletion && !hasResults)
+    if (ac_store.oncomplete) {
+      ac_store.oncomplete(false, key, ac_focusedInput, undefined);
+    }
+  }
+
+  if (cancelEvent) {
+    ac_cancelEvent_(event);
+  }
+
+  return !cancelEvent;
+}
+
+/** Autocomplete onblur handler. */
+function _ac_ob(event) {
+  if (ac_focusedInput) {
+    ac_focusedInput.onblur = ac_oldBlurHandler;
+  }
+  ac_store = null;
+  ac_focusedInput = null;
+  ac_everTyped = false;
+  ac_oldBlurHandler = null;
+  ac_suppressCompletions = false;
+  ac_updateCompletionList(false);
+}
+
+/** @constructor */
+function _AC_Store() {
+}
+/** returns the chunk of the input to treat as completable. */
+_AC_Store.prototype.completable = function(inputValue, caret) {
+  console.log('UNIMPLEMENTED completable');
+};
+/** returns the chunk of the input to treat as completable. */
+_AC_Store.prototype.completions = function(prefix, tofilter) {
+  console.log('UNIMPLEMENTED completions');
+};
+/** returns the chunk of the input to treat as completable. */
+_AC_Store.prototype.oncomplete = function(completed, key, element, text) {
+  // Call the onkeyup handler so that choosing an autocomplete option has
+  // the same side-effect as typing.  E.g., exposing the next row of input
+  // fields.
+  element.dispatchEvent(new Event('keyup'));
+  _ac_ob();
+};
+/** substitutes a completion for a completable in a text input's value. */
+_AC_Store.prototype.substitute =
+  function(inputValue, caret, completable, completion) {
+    console.log('UNIMPLEMENTED substitute');
+  };
+/** true iff hitting a comma key should complete. */
+_AC_Store.prototype.commaCompletes = true;
+/**
+ * true iff the given keystroke should cause a completion (and be consumed in
+ * the process.
+ */
+_AC_Store.prototype.isCompletionKey = function(key, isDown, isShiftKey) {
+  if (!isDown && (ENTER_KEYNAME === key ||
+                  (COMMA_KEYNAME == key && this.commaCompletes))) {
+    return true;
+  }
+  if (TAB_KEYNAME === key && !isShiftKey) {
+    // IE doesn't fire an event for tab on click in a text field, and firefox
+    // requires that the onkeypress event for tab be consumed or it navigates
+    // to next field.
+    return false;
+    // JER: return isDown == BR_IsIE();
+  }
+  return false;
+};
+
+_AC_Store.prototype.setAvoid = function(event) {
+  if (event && event.avoidValues) {
+    ac_avoidValues = event.avoidValues;
+  } else {
+    ac_avoidValues = this.computeAvoid();
+  }
+  ac_avoidValues = ac_avoidValues.map((val) => val.toLowerCase());
+};
+
+/* Subclasses may implement this to compute values to avoid
+   offering in the current input field, i.e., because those
+   values are already used. */
+_AC_Store.prototype.computeAvoid = function() {
+  return [];
+};
+
+
+function _AC_AddItemToFirstCharMap(firstCharMap, ch, s) {
+  let l = firstCharMap[ch];
+  if (!l) {
+    l = firstCharMap[ch] = [];
+  } else if (l[l.length - 1].value == s) {
+    return;
+  }
+  l.push(new _AC_Completion(s, null, ''));
+}
+
+/**
+ * an _AC_Store implementation suitable for completing lists of email
+ * addresses.
+ * @constructor
+ */
+function _AC_SimpleStore(strings, opt_docStrings) {
+  this.firstCharMap_ = {};
+
+  for (let i = 0; i < strings.length; ++i) {
+    let s = strings[i];
+    if (!s) {
+      continue;
+    }
+    if (opt_docStrings && opt_docStrings[s]) {
+      s = s + ' ' + opt_docStrings[s];
+    }
+
+    const parts = s.split(/\W+/);
+    for (let j = 0; j < parts.length; ++j) {
+      if (parts[j]) {
+        _AC_AddItemToFirstCharMap(
+            this.firstCharMap_, parts[j].charAt(0).toLowerCase(), strings[i]);
+      }
+    }
+  }
+
+  // The maximimum number of results that we are willing to show
+  this.countThreshold = 2500;
+  this.docstrings = opt_docStrings || {};
+}
+_AC_SimpleStore.prototype = new _AC_Store();
+_AC_SimpleStore.prototype.constructor = _AC_SimpleStore;
+
+_AC_SimpleStore.prototype.completable =
+  function(inputValue, caret) {
+  // complete after the last comma not inside ""s
+    let start = 0;
+    let state = 0;
+    for (let i = 0; i < caret; ++i) {
+      const ch = inputValue.charAt(i);
+      switch (state) {
+        case 0:
+          if ('"' == ch) {
+            state = 1;
+          } else if (',' == ch || ' ' == ch) {
+            start = i + 1;
+          }
+          break;
+        case 1:
+          if ('"' == ch) {
+            state = 0;
+          }
+          break;
+      }
+    }
+    while (start < caret &&
+         ' \t\r\n'.indexOf(inputValue.charAt(start)) >= 0) {
+      ++start;
+    }
+    return inputValue.substring(start, caret);
+  };
+
+
+/** Simple function to create a <span> with matching text in bold.
+ */
+function _AC_CreateSpanWithMatchHighlighted(match) {
+  const span = document.createElement('span');
+  span.appendChild(document.createTextNode(match[1] || ''));
+  const bold = document.createElement('b');
+  span.appendChild(bold);
+  bold.appendChild(document.createTextNode(match[2]));
+  span.appendChild(document.createTextNode(match[3] || ''));
+  return span;
+};
+
+
+/**
+ * Get all completions matching the given prefix.
+ * @param {string} prefix The prefix of the text to autocomplete on.
+ * @param {List.<string>?} toFilter Optional list to filter on. Otherwise will
+ *     use this.firstCharMap_ using the prefix's first character.
+ * @return {List.<_AC_Completion>} The computed list of completions.
+ */
+_AC_SimpleStore.prototype.completions = function(prefix) {
+  if (!prefix) {
+    return [];
+  }
+  toFilter = this.firstCharMap_[prefix.charAt(0).toLowerCase()];
+
+  // Since we use prefix to build a regular expression, we need to escape RE
+  // characters. We match '-', '{', '$' and others in the prefix and convert
+  // them into "\-", "\{", "\$".
+  const regexForRegexCharacters = /([\^*+\-\$\\\{\}\(\)\[\]\#?\.])/g;
+  const modifiedPrefix = prefix.replace(regexForRegexCharacters, '\\$1');
+
+  // Match the modifiedPrefix anywhere as long as it is either at the very
+  // beginning "Th" -> "The Hobbit", or comes immediately after a word separator
+  // such as "Ga" -> "The-Great-Gatsby".
+  const patternRegex = '^(.*\\W)?(' + modifiedPrefix + ')(.*)';
+  const pattern = new RegExp(patternRegex, 'i' /* ignore case */);
+
+  // We keep separate lists of possible completions that were generated
+  // by matching a value or generated by matching a docstring.  We return
+  // a concatenated list so that value matches all come before docstring
+  // matches.
+  const completions = [];
+  const docCompletions = [];
+
+  if (toFilter) {
+    const toFilterLength = toFilter.length;
+    for (let i = 0; i < toFilterLength; ++i) {
+      const docStr = this.docstrings[toFilter[i].value];
+      let compSpan = null;
+      let docSpan = null;
+      const matches = toFilter[i].value.match(pattern);
+      const docMatches = docStr && docStr.match(pattern);
+      if (matches) {
+        compSpan = _AC_CreateSpanWithMatchHighlighted(matches);
+        if (docStr) docSpan = document.createTextNode(docStr);
+      } else if (docMatches) {
+        compSpan = document.createTextNode(toFilter[i].value);
+        docSpan = _AC_CreateSpanWithMatchHighlighted(docMatches);
+      }
+
+      if (compSpan) {
+        const newCompletion = new _AC_Completion(
+            toFilter[i].value, compSpan, docSpan);
+
+        if (matches) {
+          completions.push(newCompletion);
+        } else {
+          docCompletions.push(newCompletion);
+        }
+        if (completions.length + docCompletions.length > this.countThreshold) {
+          break;
+        }
+      }
+    }
+  }
+
+  return completions.concat(docCompletions);
+};
+
+// Normally, when the user types a few characters, we aggressively
+// select the first possible completion (if any).  When the user
+// hits ENTER, that first completion is substituted.  When that
+// behavior is not desired, override this to return false.
+_AC_SimpleStore.prototype.autoselectFirstRow = function() {
+  return true;
+};
+
+// Comparison function for _AC_Completion
+function _AC_CompareACCompletion(a, b) {
+  // convert it to lower case and remove all leading junk
+  const aval = a.value.toLowerCase().replace(/^\W*/, '');
+  const bval = b.value.toLowerCase().replace(/^\W*/, '');
+
+  if (a.value === b.value) {
+    return 0;
+  } else if (aval < bval) {
+    return -1;
+  } else {
+    return 1;
+  }
+}
+
+_AC_SimpleStore.prototype.substitute =
+function(inputValue, caret, completable, completion) {
+  return inputValue.substring(0, caret - completable.length) +
+    completion.value + ', ' + inputValue.substring(caret);
+};
+
+/**
+ * a possible completion.
+ * @constructor
+ */
+function _AC_Completion(value, compSpan, docSpan) {
+  /** plain text. */
+  this.value = value;
+  if (typeof compSpan == 'string') compSpan = document.createTextNode(compSpan);
+  this.compSpan = compSpan;
+  if (typeof docSpan == 'string') docSpan = document.createTextNode(docSpan);
+  this.docSpan = docSpan;
+}
+_AC_Completion.prototype.toString = function() {
+  return '(AC_Completion: ' + this.value + ')';
+};
+
+/** registered store constructors.  @private */
+var ac_storeConstructors = [];
+/**
+ * the focused text input or textarea whether store is null or not.
+ * A text input may have focus and this may be null iff no key has been typed in
+ * the text input.
+ */
+var ac_focusedInput = null;
+/**
+ * null or the autocomplete store used to complete ac_focusedInput.
+ * @private
+ */
+var ac_store = null;
+/** store handler from ac_focusedInput. @private */
+var ac_oldBlurHandler = null;
+/**
+ * true iff user has indicated completions are unwanted (via ESC key)
+ * @private
+ */
+var ac_suppressCompletions = false;
+/**
+ * chunk of completable text seen last keystroke.
+ * Used to generate ac_completions.
+ * @private
+ */
+let ac_lastCompletable = null;
+/** an array of _AC_Completions.  @private */
+var ac_completions = null;
+/** -1 or in [0, _AC_Completions.length).  @private */
+var ac_selected = -1;
+
+/** Maximum number of options displayed in menu. @private */
+const ac_max_options = 100;
+
+/** Don't offer these values because they are already used. @private */
+let ac_avoidValues = [];
+
+/**
+ * handles all the key strokes, updating the completion list, tracking selected
+ * element, performing substitutions, etc.
+ * @private
+ */
+function ac_handleKey_(key, isDown, isShiftKey) {
+  // check completions
+  ac_checkCompletions();
+  let show = true;
+  const numCompletions = ac_completions ? ac_completions.length : 0;
+  // handle enter and tab on key press and the rest on key down
+  if (ac_store.isCompletionKey(key, isDown, isShiftKey)) {
+    if (ac_selected < 0 && numCompletions >= 1 &&
+        ac_store.autoselectFirstRow()) {
+      ac_selected = 0;
+    }
+    if (ac_selected >= 0) {
+      const backupInput = ac_focusedInput;
+      const completeValue = ac_completions[ac_selected].value;
+      ac_complete();
+      if (ac_store.oncomplete) {
+        ac_store.oncomplete(true, key, backupInput, completeValue);
+      }
+    }
+  } else {
+    switch (key) {
+      case ESC_KEYNAME: // escape
+      // JER?? ac_suppressCompletions = true;
+        ac_selected = -1;
+        show = false;
+        break;
+      case UP_KEYNAME: // up
+        if (isDown) {
+        // firefox fires arrow events on both down and press, but IE only fires
+        // then on press.
+          ac_selected = Math.max(numCompletions >= 0 ? 0 : -1, ac_selected - 1);
+        }
+        break;
+      case DOWN_KEYNAME: // down
+        if (isDown) {
+          ac_selected = Math.min(
+              ac_max_options - 1, Math.min(numCompletions - 1, ac_selected + 1));
+        }
+        break;
+    }
+
+    if (isDown) {
+      switch (key) {
+        case ESC_KEYNAME:
+        case ENTER_KEYNAME:
+        case UP_KEYNAME:
+        case DOWN_KEYNAME:
+        case RIGHT_KEYNAME:
+        case LEFT_KEYNAME:
+        case TAB_KEYNAME:
+        case SHIFT_KEYNAME:
+        case BACKSPACE_KEYNAME:
+        case DELETE_KEYNAME:
+          break;
+        default: // User typed some new characters.
+          ac_everTyped = true;
+      }
+    }
+  }
+
+  if (ac_focusedInput) {
+    ac_updateCompletionList(show);
+  }
+}
+
+/**
+ * called when an option is clicked on to select that option.
+ */
+function _ac_select(optionIndex) {
+  ac_selected = optionIndex;
+  ac_complete();
+  if (ac_store.oncomplete) {
+    ac_store.oncomplete(true, null, ac_focusedInput, ac_focusedInput.value);
+  }
+
+  // check completions
+  ac_checkCompletions();
+  ac_updateCompletionList(true);
+}
+
+function _ac_mouseover(optionIndex) {
+  ac_selected = optionIndex;
+  ac_updateCompletionList(true);
+}
+
+/** perform the substitution of the currently selected item. */
+function ac_complete() {
+  const caret = ac_getCaretPosition_(ac_focusedInput);
+  const completion = ac_completions[ac_selected];
+
+  ac_focusedInput.value = ac_store.substitute(
+      ac_focusedInput.value, caret,
+      ac_lastCompletable, completion);
+  // When the prefix starts with '*' we want to return the complete set of all
+  // possible completions. We treat the ac_lastCompletable value as empty so
+  // that the caret is correctly calculated (i.e. the caret should not consider
+  // placeholder values like '*member').
+  let new_caret = caret + completion.value.length;
+  if (!ac_lastCompletable.startsWith('*')) {
+    // Only consider the ac_lastCompletable length if it does not start with '*'
+    new_caret = new_caret - ac_lastCompletable.length;
+  }
+  // If we inserted something ending in two quotation marks, position
+  // the cursor between the quotation marks. If we inserted a complete term,
+  // skip over the trailing space so that the user is ready to enter the next
+  // term.  If we inserted just a search operator, leave the cursor immediately
+  // after the colon or equals and don't skip over the space.
+  if (completion.value.substring(completion.value.length - 2) == '""') {
+    new_caret--;
+  } else if (completion.value.substring(completion.value.length - 1) != ':' &&
+             completion.value.substring(completion.value.length - 1) != '=') {
+    new_caret++; // To account for the comma.
+    new_caret++; // To account for the space after the comma.
+  }
+  ac_selected = -1;
+  ac_completions = null;
+  ac_lastCompletable = null;
+  ac_everTyped = false;
+  SetCursorPos(window, ac_focusedInput, new_caret);
+}
+
+/**
+ * True if the user has ever typed any actual characters in the currently
+ * focused text field.  False if they have only clicked, backspaced, and
+ * used the arrow keys.
+ */
+var ac_everTyped = false;
+
+/**
+ * maintains ac_completions, ac_selected, ac_lastCompletable.
+ * @private
+ */
+function ac_checkCompletions() {
+  if (ac_focusedInput && !ac_suppressCompletions) {
+    const caret = ac_getCaretPosition_(ac_focusedInput);
+    const completable = ac_store.completable(ac_focusedInput.value, caret);
+
+    // If we already have completed, then our work here is done.
+    if (completable == ac_lastCompletable) {
+      return;
+    }
+
+    ac_completions = null;
+    ac_selected = -1;
+
+    const oldSelected =
+      ((ac_selected >= 0 && ac_selected < ac_completions.length) ?
+        ac_completions[ac_selected].value : null);
+    ac_completions = ac_store.completions(completable);
+    // Don't offer options for values that the user has already used
+    // in another part of the current form.
+    ac_completions = ac_completions.filter((comp) =>
+      FindInArray(ac_avoidValues, comp.value.toLowerCase()) === -1);
+
+    ac_selected = oldSelected ? 0 : -1;
+    ac_lastCompletable = completable;
+    return;
+  }
+  ac_lastCompletable = null;
+  ac_completions = null;
+  ac_selected = -1;
+}
+
+/**
+ * maintains the completion list GUI.
+ * @private
+ */
+function ac_updateCompletionList(show) {
+  let clist = document.getElementById('ac-list');
+  const input = ac_focusedInput;
+  if (input) {
+    input.setAttribute('aria-activedescendant', 'ac-status-row-none');
+  }
+  let tableEl;
+  let tableBody;
+  if (show && ac_completions && ac_completions.length) {
+    if (!clist) {
+      clist = document.createElement('DIV');
+      clist.id = 'ac-list';
+      clist.style.position = 'absolute';
+      clist.style.display = 'none';
+      // with 'listbox' and 'option' roles, screenreader narrates total
+      // number of options eg. 'New = issue has not .... 1 of 9'
+      document.body.appendChild(clist);
+      tableEl = document.createElement('table');
+      tableEl.setAttribute('cellpadding', 0);
+      tableEl.setAttribute('cellspacing', 0);
+      tableEl.id = 'ac-table';
+      tableEl.setAttribute('role', 'presentation');
+      tableBody = document.createElement('tbody');
+      tableBody.id = 'ac-table-body';
+      tableEl.appendChild(tableBody);
+      tableBody.setAttribute('role', 'listbox');
+      clist.appendChild(tableEl);
+      input.setAttribute('aria-controls', 'ac-table');
+      input.setAttribute('aria-haspopup', 'grid');
+    } else {
+      tableEl = document.getElementById('ac-table');
+      tableBody = document.getElementById('ac-table-body');
+      while (tableBody.childNodes.length) {
+        tableBody.removeChild(tableBody.childNodes[0]);
+      }
+    }
+
+    // If no choice is selected, then select the first item, if desired.
+    if (ac_selected < 0 && ac_store && ac_store.autoselectFirstRow()) {
+      ac_selected = 0;
+    }
+
+    let headerCount= 0;
+    for (let i = 0; i < Math.min(ac_max_options, ac_completions.length); ++i) {
+      if (ac_completions[i].heading) {
+        var rowEl = document.createElement('tr');
+        tableBody.appendChild(rowEl);
+        const cellEl = document.createElement('th');
+        rowEl.appendChild(cellEl);
+        cellEl.setAttribute('colspan', 2);
+        if (headerCount) {
+          cellEl.appendChild(document.createElement('br'));
+        }
+        cellEl.appendChild(
+            document.createTextNode(ac_completions[i].heading));
+        headerCount++;
+      } else {
+        var rowEl = document.createElement('tr');
+        tableBody.appendChild(rowEl);
+        if (i == ac_selected) {
+          rowEl.className = 'selected';
+        }
+        rowEl.id = `ac-status-row-${i}`;
+        rowEl.setAttribute('data-index', i);
+        rowEl.setAttribute('role', 'option');
+        rowEl.addEventListener('mousedown', function(event) {
+          event.preventDefault();
+        });
+        rowEl.addEventListener('mouseup', function(event) {
+          let target = event.target;
+          while (target && target.tagName != 'TR') {
+            target = target.parentNode;
+          }
+          const idx = Number(target.getAttribute('data-index'));
+          try {
+            _ac_select(idx);
+          } finally {
+            return false;
+          }
+        });
+        rowEl.addEventListener('mouseover', function(event) {
+          let target = event.target;
+          while (target && target.tagName != 'TR') {
+            target = target.parentNode;
+          }
+          const idx = Number(target.getAttribute('data-index'));
+          _ac_mouseover(idx);
+        });
+        const valCellEl = document.createElement('td');
+        rowEl.appendChild(valCellEl);
+        if (ac_completions[i].compSpan) {
+          valCellEl.appendChild(ac_completions[i].compSpan);
+        }
+        const docCellEl = document.createElement('td');
+        rowEl.appendChild(docCellEl);
+        if (ac_completions[i].docSpan &&
+            ac_completions[i].docSpan.textContent) {
+          docCellEl.appendChild(document.createTextNode(' = '));
+          docCellEl.appendChild(ac_completions[i].docSpan);
+        }
+      }
+    }
+
+    // position
+    const inputBounds = nodeBounds(ac_focusedInput);
+    clist.style.left = inputBounds.x + 'px';
+    clist.style.top = (inputBounds.y + inputBounds.h) + 'px';
+
+    window.setTimeout(ac_autoscroll, 100);
+    input.setAttribute('aria-activedescendant', `ac-status-row-${ac_selected}`);
+    // Note - we use '' instead of 'block', since 'block' has odd effects on
+    // the screen in IE, and causes scrollbars to resize
+    clist.style.display = '';
+  } else {
+    tableBody = document.getElementById('ac-table-body');
+    if (clist && tableBody) {
+      clist.style.display = 'none';
+      while (tableBody.childNodes.length) {
+        tableBody.removeChild(tableBody.childNodes[0]);
+      }
+    }
+  }
+}
+
+// TODO(jrobbins): make arrow keys and mouse not conflict if they are
+// used at the same time.
+
+
+/** Scroll the autocomplete menu to show the currently selected row. */
+function ac_autoscroll() {
+  const acList = document.getElementById('ac-list');
+  const acSelRow = acList.getElementsByClassName('selected')[0];
+  const acSelRowTop = acSelRow ? acSelRow.offsetTop : 0;
+  const acSelRowHeight = acSelRow ? acSelRow.offsetHeight : 0;
+
+
+  const EXTRA = 8; // Go an extra few pixels so the next row is partly exposed.
+
+  if (!acList || !acSelRow) return;
+
+  // Autoscroll upward if the selected item is above the visible area,
+  // else autoscroll downward if the selected item is below the visible area.
+  if (acSelRowTop < acList.scrollTop) {
+    acList.scrollTop = acSelRowTop - EXTRA;
+  } else if (acSelRowTop + acSelRowHeight + EXTRA >
+             acList.scrollTop + acList.offsetHeight) {
+    acList.scrollTop = (acSelRowTop + acSelRowHeight -
+                        acList.offsetHeight + EXTRA);
+  }
+}
+
+
+/** the position of the text caret in the given text field.
+ *
+ * @param textField an INPUT node with type=text or a TEXTAREA node
+ * @return an index in [0, textField.value.length]
+ */
+function ac_getCaretPosition_(textField) {
+  if ('INPUT' == textField.tagName) {
+    let caret = textField.value.length;
+
+    // chrome/firefox
+    if (undefined != textField.selectionStart) {
+      caret = textField.selectionEnd;
+
+      // JER: Special treatment for issue status field that makes all
+      // options show up more often
+      if (textField.id.startsWith('status')) {
+        caret = textField.selectionStart;
+      }
+      // ie
+    } else if (document.selection) {
+      // get an empty selection range
+      const range = document.selection.createRange();
+      const origSelectionLength = range.text.length;
+      // Force selection start to 0 position
+      range.moveStart('character', -caret);
+      // the caret end position is the new selection length
+      caret = range.text.length;
+
+      // JER: Special treatment for issue status field that makes all
+      // options show up more often
+      if (textField.id.startsWith('status')) {
+        // The amount that the selection grew when we forced start to
+        // position 0 is == the original start position.
+        caret = range.text.length - origSelectionLength;
+      }
+    }
+
+    return caret;
+  } else {
+    // a textarea
+
+    return GetCursorPos(window, textField);
+  }
+}
+
+function getTargetFromEvent(event) {
+  let targ = event.target || event.srcElement;
+  if (targ.shadowRoot) {
+    // Find the element within the shadowDOM.
+    const path = event.path || event.composedPath();
+    targ = path[0];
+  }
+  return targ;
+}
diff --git a/static/js/tracker/ac_test.js b/static/js/tracker/ac_test.js
new file mode 100644
index 0000000..30eedc5
--- /dev/null
+++ b/static/js/tracker/ac_test.js
@@ -0,0 +1,40 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+var firstCharMap;
+
+function setUp() {
+  firstCharMap = new Object();
+}
+
+function testAddItemToFirstCharMap_OneWordLabel() {
+  _AC_AddItemToFirstCharMap(firstCharMap, 'h', 'Hot');
+  let hArray = firstCharMap['h'];
+  assertEquals(1, hArray.length);
+  assertEquals('Hot', hArray[0].value);
+
+  _AC_AddItemToFirstCharMap(firstCharMap, '-', '-Hot');
+  _AC_AddItemToFirstCharMap(firstCharMap, 'h', '-Hot');
+  let minusArray = firstCharMap['-'];
+  assertEquals(1, minusArray.length);
+  assertEquals('-Hot', minusArray[0].value);
+  hArray = firstCharMap['h'];
+  assertEquals(2, hArray.length);
+  assertEquals('Hot', hArray[0].value);
+  assertEquals('-Hot', hArray[1].value);
+}
+
+function testAddItemToFirstCharMap_KeyValueLabels() {
+  _AC_AddItemToFirstCharMap(firstCharMap, 'p', 'Priority-High');
+  _AC_AddItemToFirstCharMap(firstCharMap, 'h', 'Priority-High');
+  let pArray = firstCharMap['p'];
+  assertEquals(1, pArray.length);
+  assertEquals('Priority-High', pArray[0].value);
+  let hArray = firstCharMap['h'];
+  assertEquals(1, hArray.length);
+  assertEquals('Priority-High', hArray[0].value);
+}
diff --git a/static/js/tracker/externs.js b/static/js/tracker/externs.js
new file mode 100644
index 0000000..2a92f58
--- /dev/null
+++ b/static/js/tracker/externs.js
@@ -0,0 +1,115 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+/* eslint-disable no-var */
+
+// Defined in framework/js:core_scripts
+var _hideID;
+var _showID;
+var _hideEl;
+var _showEl;
+var _showInstead;
+var _toggleHidden;
+
+var _selectAllIssues;
+var _selectNoneIssues;
+
+var _toggleRows;
+var _toggleColumn;
+var _toggleColumnUpdate;
+var _addGroupBy;
+var _addcol;
+var _checkRangeSelect;
+var _setRowLinks;
+var _makeIssueLink;
+
+var _onload;
+
+var _handleListActions;
+var _handleDetailActions;
+
+var _loadStatusSelect;
+var _fetchOptions;
+var _setACOptions;
+var _openIssueUpdateForm;
+var _addAttachmentFields;
+var _ignoreWidgetIfOpIsClear;
+
+var _formatContextQueryArgs;
+var _ctxArgs;
+var _ctxCan;
+var _ctxQuery;
+var _ctxSortspec;
+var _ctxGroupBy;
+var _ctxDefaultColspec;
+var _ctxStart;
+var _ctxNum;
+var _ctxResultsPerPage;
+
+var _filterTo;
+var _sortUp;
+var _sortDown;
+
+var _closeAllPopups;
+var _closeSubmenus;
+var _showRight;
+var _showBelow;
+var _highlightRow;
+var _highlightRowCallback;
+var _allColumnNames;
+
+var _setFieldIDs;
+var _selectTemplate;
+var _saveTemplate;
+var _newTemplate;
+var _deleteTemplate;
+var _switchTemplate;
+var _templateNames;
+
+var _confirmNovelStatus;
+var _confirmNovelLabel;
+var _lfidprefix;
+var _allOrigLabels;
+var _vallab;
+var _exposeExistingLabelFields;
+var _confirmDiscardEntry;
+var _confirmDiscardUpdate;
+var _checkPlusOne;
+var _checkUnrestrict;
+
+var _clearOnFirstEvent;
+var _forceProperTableWidth;
+
+var _acof;
+var _acmo;
+var _acse;
+var _acstore;
+var _acreg;
+var _accomp;
+var _acrob;
+
+var _d;
+
+var _getColspec;
+
+var issueRefs;
+
+var kibbles;
+var _setupKibblesOnEntryPage;
+var _setupKibblesOnListPage;
+var _setupKibblesOnDetailPage;
+
+var CS_env;
+
+var _checkFieldNameOnServer;
+var _checkLeafName;
+
+var _addMultiFieldValueWidget;
+var _removeMultiFieldValueWidget;
+var console;
+var _trimCommas;
+
+var _initDragAndDrop;
diff --git a/static/js/tracker/render-hotlist-table.js b/static/js/tracker/render-hotlist-table.js
new file mode 100644
index 0000000..5004296
--- /dev/null
+++ b/static/js/tracker/render-hotlist-table.js
@@ -0,0 +1,436 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+/**
+ * This file contains JS functions used in rendering a hotlistissues table
+ */
+
+
+/**
+ * Helper function to set several attributes of an element at once.
+ * @param {Element} el element that is getting the attributes
+ * @param {dict} attrs Dictionary of {attrName: attrValue, ..}
+ */
+function setAttributes(el, attrs) {
+  for (let key in attrs) {
+    el.setAttribute(key, attrs[key]);
+  }
+}
+
+// TODO(jojwang): readOnly is currently empty string, figure out what it should be
+// ('True'/'False' 'yes'/'no'?).
+
+/**
+ * Helper function for creating a <td> element that contains the widgets of the row.
+ * @param {dict} tableRow dictionary {'projectName': 'name', .. } of relevant row info.
+ * @param {} readOnly.
+ * @param {boolean} userLoggedIn is the current user logged in.
+ * @return an element containing the widget elements
+ */
+function createWidgets(tableRow, readOnly, userLoggedIn) {
+  let widgets = document.createElement('td');
+  widgets.setAttribute('class', 'rowwidgets nowrap');
+
+  let gripper = document.createElement('i');
+  gripper.setAttribute('class', 'material-icons gripper');
+  gripper.setAttribute('title', 'Drag issue');
+  gripper.textContent = 'drag_indicator';
+  widgets.appendChild(gripper);
+
+  if (!readOnly) {
+    if (userLoggedIn) {
+      // TODO(jojwang): for bulk edit, only show a checkbox next to an issue that
+      // the user has permission to edit.
+      let checkbox = document.createElement('input');
+      setAttributes(checkbox, {'class': 'checkRangeSelect',
+        'id': 'cb_' + tableRow['issueRef'],
+        'type': 'checkbox'});
+      widgets.appendChild(checkbox);
+      widgets.appendChild(document.createTextNode(' '));
+
+      let star = document.createElement('a');
+      let starColor = tableRow['isStarred'] ? 'cornflowerblue' : 'gray';
+      let starred = tableRow['isStarred'] ? 'Un-s' : 'S';
+      setAttributes(star, {'class': 'star',
+        'id': 'star-' + tableRow['projectName'] + tableRow['localID'],
+        'style': 'color:' + starColor,
+        'title': starred + 'tar this issue',
+        'data-project-name': tableRow['projectName'],
+        'data-local-id': tableRow['localID']});
+      star.textContent = (tableRow['isStarred'] ? '\u2605' : '\u2606');
+      widgets.appendChild(star);
+    }
+  }
+  return widgets;
+}
+
+
+/**
+ * Helper function to set attributes and add Nodes for an ID cell.
+ * @param {Element} td element to be added to current row in table.
+ * @param {dict} tableRow dictionary {'projectName': 'name', .. } of relevant row info.
+ * @param {boolean} isCrossProject are issues in the table from more than one project.
+*/
+function createIDCell(td, tableRow, isCrossProject) {
+  td.classList.add('id');
+  let aLink = document.createElement('a');
+  aLink.setAttribute('href', tableRow['issueCleanURL']);
+  aLink.setAttribute('class', 'computehref');
+  let aLinkContent = (isCrossProject ? (tableRow['projectName'] + ':') : '' ) + tableRow['localID'];
+  aLink.textContent = aLinkContent;
+  td.appendChild(aLink);
+}
+
+function createProjectCell(td, tableRow) {
+  td.classList.add('project');
+  let aLink = document.createElement('a');
+  aLink.setAttribute('href', tableRow['projectURL']);
+  aLink.textContent = tableRow['projectName'];
+  td.appendChild(aLink);
+}
+
+function createEditableNoteCell(td, cell, projectName, localID, hotlistID) {
+  let textBox = document.createElement('textarea');
+  setAttributes(textBox, {
+    'id': `itemnote_${projectName}_${localID}`,
+    'placeholder': '---',
+    'class': 'itemnote rowwidgets',
+    'projectname': projectName,
+    'localid': localID,
+    'style': 'height:15px',
+  });
+  if (cell['values'].length > 0) {
+    textBox.value = cell['values'][0]['item'];
+  }
+  textBox.addEventListener('blur', function(e) {
+    saveNote(e.target, hotlistID);
+  });
+  debouncedKeyHandler = debounce(function(e) {
+    saveNote(e.target, hotlistID);
+  });
+  textBox.addEventListener('keyup', debouncedKeyHandler, false);
+  td.appendChild(textBox);
+}
+
+function enter_detector(e) {
+  if (e.which==13||e.keyCode==13) {
+    this.blur();
+  }
+}
+
+
+/**
+ * Helper function to set attributes and add Nodes for an Summary cell.
+ * @param {Element} td element to be added to current row in table.
+ * @param {dict} cell dictionary {'values': [], .. } of relevant cell info.
+ * @param {string=} projectName The name of the project the summary references.
+*/
+function createSummaryCell(td, cell, projectName) {
+  // TODO(jojwang): detect when links are present and make clicking on cell go
+  // to link, not issue details page
+  td.setAttribute('style', 'width:100%');
+  fillValues(td, cell['values']);
+  fillNonColumnLabels(td, cell['nonColLabels'], projectName);
+}
+
+
+/**
+ * Helper function to set attributes and add Nodes for an Attribute or Unfilterable cell.
+ * @param {Element} td element to be added to current row in table.
+ * @param {dict} cell dictionary {'type': 'Summary', .. } of relevant cell info.
+*/
+function createAttrAndUnfiltCell(td, cell) {
+  if (cell['noWrap'] == 'yes') {
+    td.className += ' nowrapspan';
+  }
+  if (cell['align']) {
+    td.setAttribute('align', cell['align']);
+  }
+  fillValues(td, cell['values']);
+}
+
+function createUrlCell(td, cell) {
+  td.classList.add('url');
+  cell.values.forEach((value) => {
+    let aLink = document.createElement('a');
+    aLink.href = value['item'];
+    aLink.target = '_blank';
+    aLink.rel = 'nofollow';
+    aLink.textContent = value['item'];
+    aLink.classList.add('fieldvalue_url');
+    td.appendChild(aLink);
+  });
+}
+
+function createIssuesCell(td, cell) {
+  td.classList.add('url');
+  if (cell.values.length > 0) {
+    cell.values.forEach( function(value, index, array) {
+      const span = document.createElement('span');
+      if (value['isDerived']) {
+        span.className = 'derived';
+      }
+      const a = document.createElement('a');
+      a.href = value['href'];
+      a.rel = 'nofollow"';
+      if (value['title']) {
+        a.title = value['title'];
+      }
+      if (value['closed']) {
+        a.style.textDecoration = 'line-through';
+      }
+      a.textContent = value['id'];
+      span.appendChild(a);
+      td.appendChild(span);
+      if (index != array.length-1) {
+        td.appendChild(document.createTextNode(', '));
+      }
+    });
+  } else {
+    td.textContent = '---';
+  }
+}
+
+/**
+ * Helper function to fill a td element with a cell's non-column labels.
+ * @param {Element} td element to be added to current row in table.
+ * @param {list} labels list of dictionaries with relevant (key, value) for
+ *   each label
+ * @param {string=} projectName The name of the project the labels reference.
+ */
+function fillNonColumnLabels(td, labels, projectName) {
+  labels.forEach( function(label) {
+    const aLabel = document.createElement('a');
+    setAttributes(aLabel,
+        {
+          'class': 'label',
+          'href': `/p/${projectName}/issues/list?q=label:${label['value']}`,
+        });
+    if (label['isDerived']) {
+      const i = document.createElement('i');
+      i.textContent = label['value'];
+      aLabel.appendChild(i);
+    } else {
+      aLabel.textContent = label['value'];
+    }
+    td.appendChild(document.createTextNode(' '));
+    td.appendChild(aLabel);
+  });
+}
+
+
+/**
+ * Helper function to fill a td element with a cell's value(s).
+ * @param {Element} td element to be added to current row in table.
+ * @param {list} values list of dictionaries with relevant (key, value) for each value
+ */
+function fillValues(td, values) {
+  if (values.length > 0) {
+    values.forEach( function(value, index, array) {
+      let span = document.createElement('span');
+      if (value['isDerived']) {
+        span.className = 'derived';
+      }
+      span.textContent = value['item'];
+      td.appendChild(span);
+      if (index != array.length-1) {
+        td.appendChild(document.createTextNode(', '));
+      }
+    });
+  } else {
+    td.textContent = '---';
+  }
+}
+
+
+/**
+ * Helper function to create a table row.
+ * @param {dict} tableRow dictionary {'projectName': 'name', .. } of relevant row info.
+ * @param {dict} pageSettings dict of relevant settings for the hotlist and user viewing the page.
+ */
+function renderHotlistRow(tableRow, pageSettings) {
+  let tr = document.createElement('tr');
+  if (pageSettings['cursor'] == tableRow['issueRef']) {
+    tr.setAttribute('class', 'ifOpened hoverTarget cursor_on drag_item');
+  } else {
+    tr.setAttribute('class', 'ifOpened hoverTarget cursor_off drag_item');
+  }
+
+  setAttributes(tr, {'data-idx': tableRow['idx'], 'data-id': tableRow['issueID'], 'issue-context-url': tableRow['issueContextURL']});
+  widgets = createWidgets(tableRow, pageSettings['readOnly'],
+    pageSettings['userLoggedIn']);
+  tr.appendChild(widgets);
+  tableRow['cells'].forEach(function(cell) {
+    let td = document.createElement('td');
+    td.setAttribute('class', 'col_' + cell['colIndex']);
+    if (cell['type'] == 'ID') {
+      createIDCell(td, tableRow, (pageSettings['isCrossProject'] == 'True'));
+    } else if (cell['type'] == 'summary') {
+      createSummaryCell(td, cell, tableRow['projectName']);
+    } else if (cell['type'] == 'note') {
+      if (pageSettings['ownerPerm'] || pageSettings['editorPerm']) {
+        createEditableNoteCell(
+          td, cell, tableRow['projectName'], tableRow['localID'],
+          pageSettings['hotlistID']);
+      } else {
+        createSummaryCell(td, cell, tableRow['projectName']);
+      }
+    } else if (cell['type'] == 'project') {
+      createProjectCell(td, tableRow);
+    } else if (cell['type'] == 'url') {
+      createUrlCell(td, cell);
+    } else if (cell['type'] == 'issues') {
+      createIssuesCell(td, cell);
+    } else {
+      createAttrAndUnfiltCell(td, cell);
+    }
+    tr.appendChild(td);
+  });
+  let directLinkURL = tableRow['issueCleanURL'];
+  let directLink = document.createElement('a');
+  directLink.setAttribute('class', 'directlink material-icons');
+  directLink.setAttribute('href', directLinkURL);
+  directLink.textContent = 'link'; // Renders as a link icon.
+  let lastCol = document.createElement('td');
+  lastCol.appendChild(directLink);
+  tr.appendChild(lastCol);
+  return tr;
+}
+
+
+/**
+ * Helper function to create the group header row
+ * @param {dict} group dict of relevant values for the current group
+ * @return a <tr> element to be added to the current <tbody>
+ */
+function renderGroupRow(group) {
+  let tr = document.createElement('tr');
+  tr.setAttribute('class', 'group_row');
+  let td = document.createElement('td');
+  setAttributes(td, {'colspan': '100', 'class': 'toggleHidden'});
+  let whenClosedImg = document.createElement('img');
+  setAttributes(whenClosedImg, {'class': 'ifClosed', 'src': '/static/images/plus.gif'});
+  td.appendChild(whenClosedImg);
+  let whenOpenImg = document.createElement('img');
+  setAttributes(whenOpenImg, {'class': 'ifOpened', 'src': '/static/images/minus.gif'});
+  td.appendChild(whenOpenImg);
+  tr.appendChild(td);
+
+  div = document.createElement('div');
+  div.textContent += group['rowsInGroup'];
+
+  div.textContent += (group['rowsInGroup'] == '1' ? ' issue:': ' issues:');
+
+  group['cells'].forEach(function(cell) {
+    let hasValue = false;
+    cell['values'].forEach(function(value) {
+      if (value['item'] !== 'None') {
+        hasValue = true;
+      }
+    });
+    if (hasValue) {
+      cell.values.forEach(function(value) {
+        div.textContent += (' ' + cell['groupName'] + '=' + value['item']);
+      });
+    } else {
+      div.textContent += (' -has:' + cell['groupName']);
+    }
+  });
+  td.appendChild(div);
+  return tr;
+}
+
+
+/**
+ * Builds the body of a hotlistissues table.
+ * @param {dict} tableData dict of relevant values from 'table_data'
+ * @param {dict} pageSettings dict of relevant settings for the hotlist and user viewing the page.
+ */
+function renderHotlistTable(tableData, pageSettings) {
+  let tbody;
+  let table = $('resultstable');
+
+  // TODO(jojwang): this would not work if grouping did not require a page refresh
+  // that wiped the table of all its children. This should be redone to be more
+  // robust.
+  // This loop only does anything when reranking is enabled.
+  for (i=0; i < table.childNodes.length; i++) {
+    if (table.childNodes[i].tagName == 'TBODY') {
+      table.removeChild(table.childNodes[i]);
+    }
+  }
+
+  tableData.forEach(function(tableRow) {
+    if (tableRow['group'] !== 'no') {
+      // add current tbody to table, need a new tbody with group row
+      if (typeof tbody !== 'undefined') {
+        table.appendChild(tbody);
+      }
+      tbody = document.createElement('tbody');
+      tbody.setAttribute('class', 'opened');
+      tbody.appendChild(renderGroupRow(tableRow['group']));
+    }
+    if (typeof tbody == 'undefined') {
+      tbody = document.createElement('tbody');
+    }
+    tbody.appendChild(renderHotlistRow(tableRow, pageSettings));
+  });
+  tbody.appendChild(document.createElement('tr'));
+  table.appendChild(tbody);
+
+  let stars = document.getElementsByClassName('star');
+  for (var i = 0; i < stars.length; ++i) {
+    let star = stars[i];
+    star.addEventListener('click', function(event) {
+      let projectName = event.target.getAttribute('data-project-name');
+      let localID = event.target.getAttribute('data-local-id');
+      _TKR_toggleStar(event.target, projectName, localID, null, null, null);
+    });
+  }
+}
+
+
+/**
+ * Activates the drag and drop functionality of the hotlistissues table.
+ * @param {dict} tableData dict of relevant values from the 'table_data' of
+ *  hotlistissues servlet. This is used when a drag and drop motion does not
+ *  result in any changes in the ordering of the issues.
+ * @param {dict} pageSettings dict of relevant settings for the hotlist and user
+ *  viewing the page.
+ * @param {str} hotlistID the number ID of the current hotlist
+*/
+function activateDragDrop(tableData, pageSettings, hotlistID) {
+  function onHotlistRerank(srcID, targetID, position) {
+    let data = {
+      target_id: targetID,
+      moved_ids: srcID,
+      split_above: position == 'above',
+      colspec: pageSettings['colSpec'],
+      can: pageSettings['can'],
+    };
+    CS_doPost(hotlistID + '/rerank.do', onHotlistResponse, data);
+  }
+
+  function onHotlistResponse(event) {
+    let xhr = event.target;
+    if (xhr.readyState != 4) {
+      return;
+    }
+    if (xhr.status != 200) {
+      window.console.error('200 page error');
+      // TODO(jojwang): fill this in more
+      return;
+    }
+    let response = CS_parseJSON(xhr);
+    renderHotlistTable(
+      (response['table_data'] == '' ? tableData : response['table_data']),
+      pageSettings);
+    // TODO(jojwang): pass pagination state to server
+    _initDragAndDrop($('resultstable'), onHotlistRerank, true);
+  }
+  _initDragAndDrop($('resultstable'), onHotlistRerank, true);
+}
diff --git a/static/js/tracker/tracker-ac.js b/static/js/tracker/tracker-ac.js
new file mode 100644
index 0000000..4d98ac1
--- /dev/null
+++ b/static/js/tracker/tracker-ac.js
@@ -0,0 +1,1285 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+/* eslint-disable camelcase */
+/* eslint-disable no-unused-vars */
+
+/**
+ * This file contains the autocomplete configuration logic that is
+ * specific to the issue fields of Monorail.  It depends on ac.js, our
+ * modified version of the autocomplete library.
+ */
+
+/**
+ * This is an autocomplete store that holds the hotlists of the current user.
+ */
+let TKR_hotlistsStore;
+
+/**
+ * This is an autocomplete store that holds well-known issue label
+ * values for the current project.
+ */
+let TKR_labelStore;
+
+/**
+ * Like TKR_labelStore but stores only label prefixes.
+ */
+let TKR_labelPrefixStore;
+
+/**
+ * Like TKR_labelStore but adds a trailing comma instead of replacing.
+ */
+let TKR_labelMultiStore;
+
+/**
+ * This is an autocomplete store that holds issue components.
+ */
+let TKR_componentStore;
+
+/**
+ * Like TKR_componentStore but adds a trailing comma instead of replacing.
+ */
+let TKR_componentListStore;
+
+/**
+ * This is an autocomplete store that holds many different kinds of
+ * items that can be shown in the artifact search autocomplete.
+ */
+let TKR_searchStore;
+
+/**
+ * This is similar to TKR_searchStore, but does not include any suggestions
+ * to use the "me" keyword. Using "me" is not a good idea for project canned
+ * queries and filter rules.
+ */
+let TKR_projectQueryStore;
+
+/**
+ * This is an autocomplete store that holds items for the quick edit
+ * autocomplete.
+ */
+// TODO(jrobbins): add options for fields and components.
+let TKR_quickEditStore;
+
+/**
+ * This is a list of label prefixes that each issue should only use once.
+ * E.g., each issue should only have one Priority-* label.  We do not prevent
+ * the user from using multiple such labels, we just warn the user before
+ * they submit.
+ */
+let TKR_exclPrefixes = [];
+
+/**
+ * This is an autocomplete store that holds custom permission names that
+ * have already been used in this project.
+ */
+let TKR_customPermissionsStore;
+
+
+/**
+ * This is an autocomplete store that holds well-known issue status
+ * values for the current project.
+ */
+let TKR_statusStore;
+
+
+/**
+ * This is an autocomplete store that holds the usernames of all the
+ * members of the current project.  This is used for autocomplete in
+ * the cc-list of an issue, where many user names can entered with
+ * commas between them.
+ */
+let TKR_memberListStore;
+
+
+/**
+ * This is an autocomplete store that holds the projects that the current
+ * user is contributor/member/owner of.
+ */
+let TKR_projectStore;
+
+/**
+ * This is an autocomplete store that holds the usernames of possible
+ * issue owners in the current project.  The list of possible issue
+ * owners is the same as the list of project members, but the behavior
+ * of this autocompete store is different because the issue owner text
+ * field can only accept one value.
+ */
+let TKR_ownerStore;
+
+
+/**
+ * This is an autocomplete store that holds any list of string for choices.
+ */
+let TKR_autoCompleteStore;
+
+
+/**
+ * An array of autocomplete stores used for user-type custom fields.
+ */
+const TKR_userAutocompleteStores = [];
+
+
+/**
+ * This boolean controls whether odd-ball status and labels are treated as
+ * a warning or an error.  Normally, it is False.
+ */
+// TODO(jrobbins): split this into one option for statuses and one for labels.
+let TKR_restrict_to_known;
+
+/**
+ * This substitute function should be used for multi-valued autocomplete fields
+ * that are delimited by commas. When we insert an autocomplete value, replace
+ * an entire search term. Add a comma and a space after it if it is a complete
+ * search term.
+ */
+function TKR_acSubstituteWithComma(inputValue, caret, completable, completion) {
+  let nextTerm = caret;
+
+  // Subtract one in case the cursor is at the end of the input, before a comma.
+  let prevTerm = caret - 1;
+  while (nextTerm < inputValue.length - 1 && inputValue.charAt(nextTerm) !== ',') {
+    nextTerm++;
+  }
+  // Set this at the position after the found comma.
+  nextTerm++;
+
+  while (prevTerm > 0 && ![',', ' '].includes(inputValue.charAt(prevTerm))) {
+    prevTerm--;
+  }
+  if (prevTerm > 0) {
+    // Set this boundary after the found space/comma if it's not the beginning
+    // of the field.
+    prevTerm++;
+  }
+
+  return inputValue.substring(0, prevTerm) +
+         completion.value + ', ' + inputValue.substring(nextTerm);
+}
+
+/**
+ * When the prefix starts with '*', return the complete set of all
+ * possible completions.
+ * @param {string} prefix If this starts with '*', return all possible
+ * completions.  Otherwise return null.
+ * @param {Array} labelDefs The array of label names and docstrings.
+ * @return Array of new _AC_Completions for each possible completion, or null.
+ */
+function TKR_fullComplete(prefix, labelDefs) {
+  if (!prefix.startsWith('*')) return null;
+  const out = [];
+  for (let i = 0; i < labelDefs.length; i++) {
+    out.push(new _AC_Completion(labelDefs[i].name,
+        labelDefs[i].name,
+        labelDefs[i].doc));
+  }
+  return out;
+}
+
+
+/**
+ * Constucts a list of all completions for both open and closed
+ * statuses, with a header for each group.
+ * @param {string} prefix If starts with '*', return all possible completions,
+ * else return null.
+ * @param {Array} openStatusDefs The array of open status values and
+ * docstrings.
+ * @param {Array} closedStatusDefs The array of closed status values
+ * and docstrings.
+ * @return Array of new _AC_Completions for each possible completion, or null.
+ */
+function TKR_openClosedComplete(prefix, openStatusDefs, closedStatusDefs) {
+  if (!prefix.startsWith('*')) return null;
+  const out = [];
+  out.push({heading: 'Open Statuses:'}); // TODO: i18n
+  for (var i = 0; i < openStatusDefs.length; i++) {
+    out.push(new _AC_Completion(openStatusDefs[i].name,
+        openStatusDefs[i].name,
+        openStatusDefs[i].doc));
+  }
+  out.push({heading: 'Closed Statuses:'}); // TODO: i18n
+  for (var i = 0; i < closedStatusDefs.length; i++) {
+    out.push(new _AC_Completion(closedStatusDefs[i].name,
+        closedStatusDefs[i].name,
+        closedStatusDefs[i].doc));
+  }
+  return out;
+}
+
+
+function TKR_setUpHotlistsStore(hotlists) {
+  const docdict = {};
+  const ref_strs = [];
+
+  for (let i = 0; i < hotlists.length; i++) {
+    ref_strs.push(hotlists[i]['ref_str']);
+    docdict[hotlists[i]['ref_str']] = hotlists[i]['summary'];
+  }
+
+  TKR_hotlistsStore = new _AC_SimpleStore(ref_strs, docdict);
+  TKR_hotlistsStore.substitute = TKR_acSubstituteWithComma;
+}
+
+
+/**
+ * An array of definitions of all well-known issue statuses.  Each
+ * definition has the name of the status value, and a docstring that
+ * describes its meaning.
+ */
+let TKR_statusWords = [];
+
+
+/**
+ * Constuct a new autocomplete store with all the well-known issue
+ * status values.  The store has some DIT-specific methods.
+ * TODO(jrobbins): would it be easier to define my own class to use
+ * instead of _AC_Simple_Store?
+ * @param {Array} openStatusDefs An array of definitions of the
+ * well-known open status values.  Each definition has a name and
+ * docstring.
+ * @param {Array} closedStatusDefs An array of definitions of the
+ * well-known closed status values.  Each definition has a name and
+ * docstring.
+ */
+function TKR_setUpStatusStore(openStatusDefs, closedStatusDefs) {
+  const docdict = {};
+  TKR_statusWords = [];
+  for (var i = 0; i < openStatusDefs.length; i++) {
+    var status = openStatusDefs[i];
+    TKR_statusWords.push(status.name);
+    docdict[status.name] = status.doc;
+  }
+  for (var i = 0; i < closedStatusDefs.length; i++) {
+    var status = closedStatusDefs[i];
+    TKR_statusWords.push(status.name);
+    docdict[status.name] = status.doc;
+  }
+
+  TKR_statusStore = new _AC_SimpleStore(TKR_statusWords, docdict);
+
+  TKR_statusStore.commaCompletes = false;
+
+  TKR_statusStore.substitute =
+  function(inputValue, cursor, completable, completion) {
+    return completion.value;
+  };
+
+  TKR_statusStore.completable = function(inputValue, cursor) {
+    if (!ac_everTyped) return '*status';
+    return inputValue;
+  };
+
+  TKR_statusStore.completions = function(prefix, tofilter) {
+    const fullList = TKR_openClosedComplete(prefix,
+        openStatusDefs,
+        closedStatusDefs);
+    if (fullList) return fullList;
+    return _AC_SimpleStore.prototype.completions.call(this, prefix, tofilter);
+  };
+}
+
+
+/**
+ * Simple function to add a given item to the list of items used to construct
+ * an "autocomplete store", and also update the docstring that describes
+ * that item.  They are stored separately for backward compatability with
+ * autocomplete store logic that preceeded the introduction of descriptions.
+ */
+function TKR_addACItem(items, docDict, item, docStr) {
+  items.push(item);
+  docDict[item] = docStr;
+}
+
+/**
+ * Adds a group of three items related to a date field.
+ */
+function TKR_addACDateItems(items, docDict, fieldName, humanReadable) {
+  const today = new Date();
+  const todayStr = (today.getFullYear() + '-' + (today.getMonth() + 1) + '-' +
+    today.getDate());
+  TKR_addACItem(items, docDict, fieldName + '>today-1',
+      humanReadable + ' within the last N days');
+  TKR_addACItem(items, docDict, fieldName + '>' + todayStr,
+      humanReadable + ' after the specified date');
+  TKR_addACItem(items, docDict, fieldName + '<today-1',
+      humanReadable + ' more than N days ago');
+}
+
+/**
+ * Add several autocomplete items to a word list that will be used to construct
+ * an autocomplete store.  Also, keep track of description strings for each
+ * item.  A search operator is prepended to the name of each item.  The opt_old
+ * and opt_new parameters are used to transform Key-Value labels into Key=Value
+ * search terms.
+ */
+function TKR_addACItemList(
+    items, docDict, searchOp, acDefs, opt_old, opt_new) {
+  let item;
+  for (let i = 0; i < acDefs.length; i++) {
+    const nameAndDoc = acDefs[i];
+    item = searchOp + nameAndDoc.name;
+    if (opt_old) {
+      // Preserve any leading minus-sign.
+      item = item.slice(0, 1) + item.slice(1).replace(opt_old, opt_new);
+    }
+    TKR_addACItem(items, docDict, item, nameAndDoc.doc);
+  }
+}
+
+
+/**
+ * Use information from an options feed to populate the artifact search
+ * autocomplete menu.  The order of sections is: custom fields, labels,
+ * components, people, status, special, dates.  Within each section,
+ * options are ordered semantically where possible, or alphabetically
+ * if there is no semantic ordering.  Negated options all come after
+ * all normal options.
+ */
+function TKR_setUpSearchStore(
+    labelDefs, memberDefs, openDefs, closedDefs, componentDefs, fieldDefs,
+    indMemberDefs) {
+  let searchWords = [];
+  const searchWordsNeg = [];
+  const docDict = {};
+
+  // Treat Key-Value and OneWord labels separately.
+  const keyValueLabelDefs = [];
+  const oneWordLabelDefs = [];
+  for (var i = 0; i < labelDefs.length; i++) {
+    const nameAndDoc = labelDefs[i];
+    if (nameAndDoc.name.indexOf('-') == -1) {
+      oneWordLabelDefs.push(nameAndDoc);
+    } else {
+      keyValueLabelDefs.push(nameAndDoc);
+    }
+  }
+
+  // Autocomplete for custom fields.
+  for (i = 0; i < fieldDefs.length; i++) {
+    const fieldName = fieldDefs[i]['field_name'];
+    const fieldType = fieldDefs[i]['field_type'];
+    if (fieldType == 'ENUM_TYPE') {
+      const choices = fieldDefs[i]['choices'];
+      TKR_addACItemList(searchWords, docDict, fieldName + '=', choices);
+      TKR_addACItemList(searchWordsNeg, docDict, '-' + fieldName + '=', choices);
+    } else if (fieldType == 'STR_TYPE') {
+      TKR_addACItem(searchWords, docDict, fieldName + ':',
+          fieldDefs[i]['docstring']);
+    } else if (fieldType == 'DATE_TYPE') {
+      TKR_addACItem(searchWords, docDict, fieldName + ':',
+          fieldDefs[i]['docstring']);
+      TKR_addACDateItems(searchWords, docDict, fieldName, fieldName);
+    } else {
+      TKR_addACItem(searchWords, docDict, fieldName + '=',
+          fieldDefs[i]['docstring']);
+    }
+    TKR_addACItem(searchWords, docDict, 'has:' + fieldName,
+        'Issues with any ' + fieldName + ' value');
+    TKR_addACItem(searchWordsNeg, docDict, '-has:' + fieldName,
+        'Issues with no ' + fieldName + ' value');
+  }
+
+  // Add suggestions with "me" first, because otherwise they may be impossible
+  // to reach in a project that has a lot of members with emails starting with
+  // "me".
+  if (CS_env['loggedInUserEmail']) {
+    TKR_addACItem(searchWords, docDict, 'owner:me', 'Issues owned by me');
+    TKR_addACItem(searchWordsNeg, docDict, '-owner:me', 'Issues not owned by me');
+    TKR_addACItem(searchWords, docDict, 'cc:me', 'Issues that CC me');
+    TKR_addACItem(searchWordsNeg, docDict, '-cc:me', 'Issues that don\'t CC me');
+    TKR_addACItem(searchWords, docDict, 'reporter:me', 'Issues I reported');
+    TKR_addACItem(searchWordsNeg, docDict, '-reporter:me', 'Issues reported by others');
+    TKR_addACItem(searchWords, docDict, 'commentby:me',
+        'Issues that I commented on');
+    TKR_addACItem(searchWordsNeg, docDict, '-commentby:me',
+        'Issues that I didn\'t comment on');
+  }
+
+  TKR_addACItemList(searchWords, docDict, '', keyValueLabelDefs, '-', '=');
+  TKR_addACItemList(searchWordsNeg, docDict, '-', keyValueLabelDefs, '-', '=');
+  TKR_addACItemList(searchWords, docDict, 'label:', oneWordLabelDefs);
+  TKR_addACItemList(searchWordsNeg, docDict, '-label:', oneWordLabelDefs);
+
+  TKR_addACItemList(searchWords, docDict, 'component:', componentDefs);
+  TKR_addACItemList(searchWordsNeg, docDict, '-component:', componentDefs);
+  TKR_addACItem(searchWords, docDict, 'has:component',
+      'Issues with any components specified');
+  TKR_addACItem(searchWordsNeg, docDict, '-has:component',
+      'Issues with no components specified');
+
+  TKR_addACItemList(searchWords, docDict, 'owner:', indMemberDefs);
+  TKR_addACItemList(searchWordsNeg, docDict, '-owner:', indMemberDefs);
+  TKR_addACItemList(searchWords, docDict, 'cc:', memberDefs);
+  TKR_addACItemList(searchWordsNeg, docDict, '-cc:', memberDefs);
+  TKR_addACItem(searchWords, docDict, 'has:cc',
+      'Issues with any cc\'d users');
+  TKR_addACItem(searchWordsNeg, docDict, '-has:cc',
+      'Issues with no cc\'d users');
+  TKR_addACItemList(searchWords, docDict, 'reporter:', memberDefs);
+  TKR_addACItemList(searchWordsNeg, docDict, '-reporter:', memberDefs);
+  TKR_addACItemList(searchWords, docDict, 'status:', openDefs);
+  TKR_addACItemList(searchWordsNeg, docDict, '-status:', openDefs);
+  TKR_addACItemList(searchWords, docDict, 'status:', closedDefs);
+  TKR_addACItemList(searchWordsNeg, docDict, '-status:', closedDefs);
+  TKR_addACItem(searchWords, docDict, 'has:status',
+      'Issues with any status');
+  TKR_addACItem(searchWordsNeg, docDict, '-has:status',
+      'Issues with no status');
+
+  TKR_addACItem(searchWords, docDict, 'is:blocked',
+      'Issues that are blocked');
+  TKR_addACItem(searchWordsNeg, docDict, '-is:blocked',
+      'Issues that are not blocked');
+  TKR_addACItem(searchWords, docDict, 'has:blockedon',
+      'Issues that are blocked');
+  TKR_addACItem(searchWordsNeg, docDict, '-has:blockedon',
+      'Issues that are not blocked');
+  TKR_addACItem(searchWords, docDict, 'has:blocking',
+      'Issues that are blocking other issues');
+  TKR_addACItem(searchWordsNeg, docDict, '-has:blocking',
+      'Issues that are not blocking other issues');
+  TKR_addACItem(searchWords, docDict, 'has:mergedinto',
+      'Issues that were merged into other issues');
+  TKR_addACItem(searchWordsNeg, docDict, '-has:mergedinto',
+      'Issues that were not merged into other issues');
+
+  TKR_addACItem(searchWords, docDict, 'is:starred',
+      'Starred by me');
+  TKR_addACItem(searchWordsNeg, docDict, '-is:starred',
+      'Not starred by me');
+  TKR_addACItem(searchWords, docDict, 'stars>10',
+      'More than 10 stars');
+  TKR_addACItem(searchWords, docDict, 'stars>100',
+      'More than 100 stars');
+  TKR_addACItem(searchWords, docDict, 'summary:',
+      'Search within the summary field');
+
+  TKR_addACItemList(searchWords, docDict, 'commentby:', memberDefs);
+  TKR_addACItem(searchWords, docDict, 'attachment:',
+      'Search within attachment names');
+  TKR_addACItem(searchWords, docDict, 'attachments>5',
+      'Has more than 5 attachments');
+  TKR_addACItem(searchWords, docDict, 'is:open', 'Issues that are open');
+  TKR_addACItem(searchWordsNeg, docDict, '-is:open', 'Issues that are closed');
+  TKR_addACItem(searchWords, docDict, 'has:owner',
+      'Issues with some owner');
+  TKR_addACItem(searchWordsNeg, docDict, '-has:owner',
+      'Issues with no owner');
+  TKR_addACItem(searchWords, docDict, 'has:attachments',
+      'Issues with some attachments');
+  TKR_addACItem(searchWords, docDict, 'id:1,2,3',
+      'Match only the specified issues');
+  TKR_addACItem(searchWords, docDict, 'id<100000',
+      'Issues with IDs under 100,000');
+  TKR_addACItem(searchWords, docDict, 'blockedon:1',
+      'Blocked on the specified issues');
+  TKR_addACItem(searchWords, docDict, 'blocking:1',
+      'Blocking the specified issues');
+  TKR_addACItem(searchWords, docDict, 'mergedinto:1',
+      'Merged into the specified issues');
+  TKR_addACItem(searchWords, docDict, 'is:ownerbouncing',
+      'Issues with owners we cannot contact');
+  TKR_addACItem(searchWords, docDict, 'is:spam', 'Issues classified as spam');
+  // We do not suggest -is:spam because it is implicit.
+
+  TKR_addACDateItems(searchWords, docDict, 'opened', 'Opened');
+  TKR_addACDateItems(searchWords, docDict, 'modified', 'Modified');
+  TKR_addACDateItems(searchWords, docDict, 'closed', 'Closed');
+  TKR_addACDateItems(searchWords, docDict, 'ownermodified', 'Owner field modified');
+  TKR_addACDateItems(searchWords, docDict, 'ownerlastvisit', 'Owner last visit');
+  TKR_addACDateItems(searchWords, docDict, 'statusmodified', 'Status field modified');
+  TKR_addACDateItems(
+      searchWords, docDict, 'componentmodified', 'Component field modified');
+
+  TKR_projectQueryStore = new _AC_SimpleStore(searchWords, docDict);
+
+  searchWords = searchWords.concat(searchWordsNeg);
+
+  TKR_searchStore = new _AC_SimpleStore(searchWords, docDict);
+
+  // When we insert an autocomplete value, replace an entire search term.
+  // Add just a space after it (not a comma) if it is a complete search term,
+  // or leave the caret immediately after the completion if we are just helping
+  // the user with the search operator.
+  TKR_searchStore.substitute =
+      function(inputValue, caret, completable, completion) {
+        let nextTerm = caret;
+        while (inputValue.charAt(nextTerm) != ' ' &&
+               nextTerm < inputValue.length) {
+          nextTerm++;
+        }
+        while (inputValue.charAt(nextTerm) == ' ' &&
+               nextTerm < inputValue.length) {
+          nextTerm++;
+        }
+        return inputValue.substring(0, caret - completable.length) +
+               completion.value + ' ' + inputValue.substring(nextTerm);
+      };
+  TKR_searchStore.autoselectFirstRow =
+      function() {
+        return false;
+      };
+
+  TKR_projectQueryStore.substitute = TKR_searchStore.substitute;
+  TKR_projectQueryStore.autoselectFirstRow = TKR_searchStore.autoselectFirstRow;
+}
+
+
+/**
+ * Use information from an options feed to populate the issue quick edit
+ * autocomplete menu.
+ */
+function TKR_setUpQuickEditStore(
+    labelDefs, memberDefs, openDefs, closedDefs, indMemberDefs) {
+  const qeWords = [];
+  const docDict = {};
+
+  // Treat Key-Value and OneWord labels separately.
+  const keyValueLabelDefs = [];
+  const oneWordLabelDefs = [];
+  for (let i = 0; i < labelDefs.length; i++) {
+    const nameAndDoc = labelDefs[i];
+    if (nameAndDoc.name.indexOf('-') == -1) {
+      oneWordLabelDefs.push(nameAndDoc);
+    } else {
+      keyValueLabelDefs.push(nameAndDoc);
+    }
+  }
+  TKR_addACItemList(qeWords, docDict, '', keyValueLabelDefs, '-', '=');
+  TKR_addACItemList(qeWords, docDict, '-', keyValueLabelDefs, '-', '=');
+  TKR_addACItemList(qeWords, docDict, '', oneWordLabelDefs);
+  TKR_addACItemList(qeWords, docDict, '-', oneWordLabelDefs);
+
+  TKR_addACItem(qeWords, docDict, 'owner=me', 'Make me the owner');
+  TKR_addACItem(qeWords, docDict, 'owner=----', 'Clear the owner field');
+  TKR_addACItem(qeWords, docDict, 'cc=me', 'CC me on this issue');
+  TKR_addACItem(qeWords, docDict, 'cc=-me', 'Remove me from CC list');
+  TKR_addACItemList(qeWords, docDict, 'owner=', indMemberDefs);
+  TKR_addACItemList(qeWords, docDict, 'cc=', memberDefs);
+  TKR_addACItemList(qeWords, docDict, 'cc=-', memberDefs);
+  TKR_addACItemList(qeWords, docDict, 'status=', openDefs);
+  TKR_addACItemList(qeWords, docDict, 'status=', closedDefs);
+  TKR_addACItem(qeWords, docDict, 'summary=""', 'Set the summary field');
+
+  TKR_quickEditStore = new _AC_SimpleStore(qeWords, docDict);
+
+  // When we insert an autocomplete value, replace an entire command part.
+  // Add just a space after it (not a comma) if it is a complete part,
+  // or leave the caret immediately after the completion if we are just helping
+  // the user with the command operator.
+  TKR_quickEditStore.substitute =
+      function(inputValue, caret, completable, completion) {
+        let nextTerm = caret;
+        while (inputValue.charAt(nextTerm) != ' ' &&
+               nextTerm < inputValue.length) {
+          nextTerm++;
+        }
+        while (inputValue.charAt(nextTerm) == ' ' &&
+               nextTerm < inputValue.length) {
+          nextTerm++;
+        }
+        return inputValue.substring(0, caret - completable.length) +
+               completion.value + ' ' + inputValue.substring(nextTerm);
+      };
+}
+
+
+/**
+ * Constuct a new autocomplete store with all the project
+ * custom permissions.
+ * @param {Array} customPermissions An array of custom permission names.
+ */
+function TKR_setUpCustomPermissionsStore(customPermissions) {
+  customPermissions = customPermissions || [];
+  const permWords = ['View', 'EditIssue', 'AddIssueComment', 'DeleteIssue'];
+  const docdict = {
+    'View': '', 'EditIssue': '', 'AddIssueComment': '', 'DeleteIssue': ''};
+  for (let i = 0; i < customPermissions.length; i++) {
+    permWords.push(customPermissions[i]);
+    docdict[customPermissions[i]] = '';
+  }
+
+  TKR_customPermissionsStore = new _AC_SimpleStore(permWords, docdict);
+
+  TKR_customPermissionsStore.commaCompletes = false;
+
+  TKR_customPermissionsStore.substitute =
+  function(inputValue, cursor, completable, completion) {
+    return completion.value;
+  };
+}
+
+
+/**
+ * Constuct a new autocomplete store with all the well-known project
+ * member user names and real names.  The store has some
+ * monorail-specific methods.
+ * TODO(jrobbins): would it be easier to define my own class to use
+ * instead of _AC_Simple_Store?
+ * @param {Array} memberDefs an array of member objects.
+ * @param {Array} nonGroupMemberDefs an array of member objects who are not groups.
+ */
+function TKR_setUpMemberStore(memberDefs, nonGroupMemberDefs) {
+  const memberWords = [];
+  const indMemberWords = [];
+  const docdict = {};
+
+  memberDefs.forEach((memberDef) => {
+    memberWords.push(memberDef.name);
+    docdict[memberDef.name] = null;
+  });
+  nonGroupMemberDefs.forEach((memberDef) => {
+    indMemberWords.push(memberDef.name);
+  });
+
+  TKR_memberListStore = new _AC_SimpleStore(memberWords, docdict);
+
+  TKR_memberListStore.completions = function(prefix, tofilter) {
+    const fullList = TKR_fullComplete(prefix, memberDefs);
+    if (fullList) return fullList;
+    return _AC_SimpleStore.prototype.completions.call(this, prefix, tofilter);
+  };
+
+  TKR_memberListStore.completable = function(inputValue, cursor) {
+    if (inputValue == '') return '*member';
+    return _AC_SimpleStore.prototype.completable.call(this, inputValue, cursor);
+  };
+
+  TKR_memberListStore.substitute = TKR_acSubstituteWithComma;
+
+  TKR_ownerStore = new _AC_SimpleStore(indMemberWords, docdict);
+
+  TKR_ownerStore.commaCompletes = false;
+
+  TKR_ownerStore.substitute =
+  function(inputValue, cursor, completable, completion) {
+    return completion.value;
+  };
+
+  TKR_ownerStore.completions = function(prefix, tofilter) {
+    const fullList = TKR_fullComplete(prefix, nonGroupMemberDefs);
+    if (fullList) return fullList;
+    return _AC_SimpleStore.prototype.completions.call(this, prefix, tofilter);
+  };
+
+  TKR_ownerStore.completable = function(inputValue, cursor) {
+    if (!ac_everTyped) return '*owner';
+    return inputValue;
+  };
+}
+
+
+/**
+ * Constuct one new autocomplete store for each user-valued custom
+ * field that has a needs_perm validation requirement, and thus a
+ * list of allowed user indexes.
+ * TODO(jrobbins): would it be easier to define my own class to use
+ * instead of _AC_Simple_Store?
+ * @param {Array} fieldDefs An array of field definitions, only some
+ * of which have a 'user_indexes' entry.
+ */
+function TKR_setUpUserAutocompleteStores(fieldDefs) {
+  fieldDefs.forEach((fieldDef) => {
+    if (fieldDef.qualifiedMembers) {
+      const us = makeOneUserAutocompleteStore(fieldDef);
+      TKR_userAutocompleteStores['custom_' + fieldDef['field_id']] = us;
+    }
+  });
+}
+
+function makeOneUserAutocompleteStore(fieldDef) {
+  const memberWords = [];
+  const docdict = {};
+  for (const member of fieldDef.qualifiedMembers) {
+    memberWords.push(member.name);
+    docdict[member.name] = member.doc;
+  }
+
+  const userStore = new _AC_SimpleStore(memberWords, docdict);
+  userStore.commaCompletes = false;
+
+  userStore.substitute =
+  function(inputValue, cursor, completable, completion) {
+    return completion.value;
+  };
+
+  userStore.completions = function(prefix, tofilter) {
+    const fullList = TKR_fullComplete(prefix, fieldDef.qualifiedMembers);
+    if (fullList) return fullList;
+    return _AC_SimpleStore.prototype.completions.call(this, prefix, tofilter);
+  };
+
+  userStore.completable = function(inputValue, cursor) {
+    if (!ac_everTyped) return '*custom';
+    return inputValue;
+  };
+
+  return userStore;
+}
+
+
+/**
+ * Constuct a new autocomplete store with all the components.
+ * The store has some monorail-specific methods.
+ * @param {Array} componentDefs An array of definitions of components.
+ */
+function TKR_setUpComponentStore(componentDefs) {
+  const componentWords = [];
+  const docdict = {};
+  for (let i = 0; i < componentDefs.length; i++) {
+    const component = componentDefs[i];
+    componentWords.push(component.name);
+    docdict[component.name] = component.doc;
+  }
+
+  const completions = function(prefix, tofilter) {
+    const fullList = TKR_fullComplete(prefix, componentDefs);
+    if (fullList) return fullList;
+    return _AC_SimpleStore.prototype.completions.call(this, prefix, tofilter);
+  };
+  const completable = function(inputValue, cursor) {
+    if (inputValue == '') return '*component';
+    return _AC_SimpleStore.prototype.completable.call(this, inputValue, cursor);
+  };
+
+  TKR_componentStore = new _AC_SimpleStore(componentWords, docdict);
+  TKR_componentStore.commaCompletes = false;
+  TKR_componentStore.substitute =
+  function(inputValue, cursor, completable, completion) {
+    return completion.value;
+  };
+  TKR_componentStore.completions = completions;
+  TKR_componentStore.completable = completable;
+
+  TKR_componentListStore = new _AC_SimpleStore(componentWords, docdict);
+  TKR_componentListStore.commaCompletes = false;
+  TKR_componentListStore.substitute = TKR_acSubstituteWithComma;
+  TKR_componentListStore.completions = completions;
+  TKR_componentListStore.completable = completable;
+}
+
+
+/**
+ * An array of definitions of all well-known issue labels.  Each
+ * definition has the name of the label, and a docstring that
+ * describes its meaning.
+ */
+let TKR_labelWords = [];
+
+
+/**
+ * Constuct a new autocomplete store with all the well-known issue
+ * labels for the current project.  The store has some DIT-specific methods.
+ * TODO(jrobbins): would it be easier to define my own class to use
+ * instead of _AC_Simple_Store?
+ * @param {Array} labelDefs An array of definitions of the project
+ * members.  Each definition has a name and docstring.
+ */
+function TKR_setUpLabelStore(labelDefs) {
+  TKR_labelWords = [];
+  const TKR_labelPrefixes = [];
+  const labelPrefs = new Set();
+  const docdict = {};
+  for (let i = 0; i < labelDefs.length; i++) {
+    const label = labelDefs[i];
+    TKR_labelWords.push(label.name);
+    TKR_labelPrefixes.push(label.name.split('-')[0]);
+    docdict[label.name] = label.doc;
+    labelPrefs.add(label.name.split('-')[0]);
+  }
+  const labelPrefArray = Array.from(labelPrefs);
+  const labelPrefDefs = labelPrefArray.map((s) => ({name: s, doc: ''}));
+
+  TKR_labelStore = new _AC_SimpleStore(TKR_labelWords, docdict);
+
+  TKR_labelStore.commaCompletes = false;
+  TKR_labelStore.substitute =
+  function(inputValue, cursor, completable, completion) {
+    return completion.value;
+  };
+
+  TKR_labelPrefixStore = new _AC_SimpleStore(TKR_labelPrefixes);
+
+  TKR_labelPrefixStore.commaCompletes = false;
+  TKR_labelPrefixStore.substitute =
+  function(inputValue, cursor, completable, completion) {
+    return completion.value;
+  };
+
+  TKR_labelMultiStore = new _AC_SimpleStore(TKR_labelWords, docdict);
+
+  TKR_labelMultiStore.substitute = TKR_acSubstituteWithComma;
+
+  const completable = function(inputValue, cursor) {
+    if (cursor === 0) {
+      return '*label'; // Show every well-known label that is not redundant.
+    }
+    let start = 0;
+    for (let i = cursor; --i >= 0;) {
+      const c = inputValue.charAt(i);
+      if (c === ' ' || c === ',') {
+        start = i + 1;
+        break;
+      }
+    }
+    const questionPos = inputValue.indexOf('?');
+    if (questionPos >= 0) {
+      // Ignore any "?" character and anything after it.
+      inputValue = inputValue.substring(start, questionPos);
+    }
+    let result = inputValue.substring(start, cursor);
+    if (inputValue.lastIndexOf('-') > 0 && !ac_everTyped) {
+      // Act like a menu: offer all alternative values for the same prefix.
+      result = inputValue.substring(
+          start, Math.min(cursor, inputValue.lastIndexOf('-')));
+    }
+    if (inputValue.startsWith('Restrict-') && !ac_everTyped) {
+      // If user is in the middle of 2nd part, use that to narrow the choices.
+      result = inputValue;
+      // If they completed 2nd part, give all choices matching 2-part prefix.
+      if (inputValue.lastIndexOf('-') > 8) {
+        result = inputValue.substring(
+            start, Math.min(cursor, inputValue.lastIndexOf('-') + 1));
+      }
+    }
+
+    return result;
+  };
+
+  const computeAvoid = function() {
+    const labelTextFields = Array.from(
+        document.querySelectorAll('.labelinput'));
+    const otherTextFields = labelTextFields.filter(
+        (tf) => (tf !== ac_focusedInput && tf.value));
+    return otherTextFields.map((tf) => tf.value);
+  };
+
+
+  const completions = function(labeldic) {
+    return function(prefix, tofilter) {
+      let comps = TKR_fullComplete(prefix, labeldic);
+      if (comps === null) {
+        comps = _AC_SimpleStore.prototype.completions.call(
+            this, prefix, tofilter);
+      }
+
+      const filteredComps = [];
+      for (const completion of comps) {
+        const completionLower = completion.value.toLowerCase();
+        const labelPrefix = completionLower.split('-')[0];
+        let alreadyUsed = false;
+        const isExclusive = FindInArray(TKR_exclPrefixes, labelPrefix) !== -1;
+        if (isExclusive) {
+          for (const usedLabel of ac_avoidValues) {
+            if (usedLabel.startsWith(labelPrefix + '-')) {
+              alreadyUsed = true;
+              break;
+            }
+          }
+        }
+        if (!alreadyUsed) {
+          filteredComps.push(completion);
+        }
+      }
+
+      return filteredComps;
+    };
+  };
+
+  TKR_labelStore.computeAvoid = computeAvoid;
+  TKR_labelStore.completable = completable;
+  TKR_labelStore.completions = completions(labelDefs);
+
+  TKR_labelPrefixStore.completable = completable;
+  TKR_labelPrefixStore.completions = completions(labelPrefDefs);
+
+  TKR_labelMultiStore.completable = completable;
+  TKR_labelMultiStore.completions = completions(labelDefs);
+}
+
+
+/**
+ * Constuct a new autocomplete store with the given strings as choices.
+ * @param {Array} choices An array of autocomplete choices.
+ */
+function TKR_setUpAutoCompleteStore(choices) {
+  TKR_autoCompleteStore = new _AC_SimpleStore(choices);
+  const choicesDefs = [];
+  for (let i = 0; i < choices.length; ++i) {
+    choicesDefs.push({'name': choices[i], 'doc': ''});
+  }
+
+  /**
+   * Override the default completions() function to return a list of
+   * available choices.  It proactively shows all choices when the user has
+   * not yet typed anything.  It stops offering choices if the text field
+   * has a pretty long string in it already.  It does not offer choices that
+   * have already been chosen.
+   */
+  TKR_autoCompleteStore.completions = function(prefix, tofilter) {
+    if (prefix.length > 18) {
+      return [];
+    }
+    let comps = TKR_fullComplete(prefix, choicesDefs);
+    if (comps == null) {
+      comps = _AC_SimpleStore.prototype.completions.call(
+          this, prefix, tofilter);
+    }
+
+    const usedComps = {};
+    const textFields = document.getElementsByTagName('input');
+    for (var i = 0; i < textFields.length; ++i) {
+      if (textFields[i].classList.contains('autocomplete')) {
+        usedComps[textFields[i].value] = true;
+      }
+    }
+    const unusedComps = [];
+    for (i = 0; i < comps.length; ++i) {
+      if (!usedComps[comps[i].value]) {
+        unusedComps.push(comps[i]);
+      }
+    }
+
+    return unusedComps;
+  };
+
+  /**
+   * Override the default completable() function with one that gives a
+   * special value when the user has not yet typed anything.  This
+   * causes TKR_fullComplete() to show all choices.  Also, always consider
+   * the whole textfield value as an input to completion matching.  Otherwise,
+   * it would only consider the part after the last comma (which makes sense
+   * for gmail To: and Cc: address fields).
+   */
+  TKR_autoCompleteStore.completable = function(inputValue, cursor) {
+    if (inputValue == '') {
+      return '*ac';
+    }
+    return inputValue;
+  };
+
+  /**
+   * Override the default substitute() function to completely replace the
+   * contents of the text field when the user selects a completion. Otherwise,
+   * it would append, much like the Gmail To: and Cc: fields append autocomplete
+   * selections.
+   */
+  TKR_autoCompleteStore.substitute =
+  function(inputValue, cursor, completable, completion) {
+    return completion.value;
+  };
+
+  /**
+   * We consider the whole textfield to be one value, not a comma separated
+   * list.  So, typing a ',' should not trigger an autocomplete selection.
+   */
+  TKR_autoCompleteStore.commaCompletes = false;
+}
+
+
+/**
+ * XMLHTTP object used to fetch autocomplete options from the server.
+ */
+const TKR_optionsXmlHttp = undefined;
+
+/**
+ * Contact the server to fetch the set of autocomplete options for the
+ * projects the user is contributor/member/owner of.
+ * @param {multiValue} boolean If set to true, the projectStore is configured to
+ * have support for multi-values (useful for example for saved queries where
+ * a query can apply to multiple projects).
+ */
+function TKR_fetchUserProjects(multiValue) {
+  // Set a request token to prevent XSRF leaking of user project lists.
+  const userRefs = [{displayName: window.CS_env.loggedInUserEmail}];
+  const userProjectsPromise = window.prpcClient.call(
+      'monorail.Users', 'GetUsersProjects', {userRefs});
+  userProjectsPromise.then((response) => {
+    const userProjects = response.usersProjects[0];
+    const projects = (userProjects.ownerOf || [])
+        .concat(userProjects.memberOf || [])
+        .concat(userProjects.contributorTo || []);
+    projects.sort();
+    if (projects) {
+      TKR_setUpProjectStore(projects, multiValue);
+    }
+  });
+}
+
+
+/**
+ * Constuct a new autocomplete store with all the projects that the
+ * current user has visibility into. The store has some monorail-specific
+ * methods.
+ * @param {Array} projects An array of project names.
+ * @param {boolean} multiValue Determines whether the store should support
+ *                  multiple values.
+ */
+function TKR_setUpProjectStore(projects, multiValue) {
+  const projectsDefs = [];
+  const docdict = {};
+  for (let i = 0; i < projects.length; ++i) {
+    projectsDefs.push({'name': projects[i], 'doc': ''});
+    docdict[projects[i]] = '';
+  }
+
+  TKR_projectStore = new _AC_SimpleStore(projects, docdict);
+  TKR_projectStore.commaCompletes = !multiValue;
+
+  if (multiValue) {
+    TKR_projectStore.substitute = TKR_acSubstituteWithComma;
+  } else {
+    TKR_projectStore.substitute =
+      function(inputValue, cursor, completable, completion) {
+        return completion.value;
+      };
+  }
+
+  TKR_projectStore.completions = function(prefix, tofilter) {
+    const fullList = TKR_fullComplete(prefix, projectsDefs);
+    if (fullList) return fullList;
+    return _AC_SimpleStore.prototype.completions.call(this, prefix, tofilter);
+  };
+
+  TKR_projectStore.completable = function(inputValue, cursor) {
+    if (inputValue == '') return '*project';
+    if (multiValue) {
+      return _AC_SimpleStore.prototype.completable.call(
+          this, inputValue, cursor);
+    } else {
+      return inputValue;
+    }
+  };
+}
+
+
+/**
+ * Convert the object resulting of a monorail.Projects ListStatuses to
+ * the format expected by TKR_populateAutocomplete.
+ * @param {object} statusesResponse A pRPC ListStatusesResponse object.
+ */
+function TKR_convertStatuses(statusesResponse) {
+  const statusDefs = statusesResponse.statusDefs || [];
+  const jsonData = {};
+
+  // Split statusDefs into open and closed name-doc objects.
+  jsonData.open = [];
+  jsonData.closed = [];
+  for (const s of statusDefs) {
+    if (!s.deprecated) {
+      const item = {
+        name: s.status,
+        doc: s.docstring,
+      };
+      if (s.meansOpen) {
+        jsonData.open.push(item);
+      } else {
+        jsonData.closed.push(item);
+      }
+    }
+  }
+
+  jsonData.strict = statusesResponse.restrictToKnown;
+
+  return jsonData;
+}
+
+
+/**
+ * Convert the object resulting of a monorail.Projects ListComponents to
+ * the format expected by TKR_populateAutocomplete.
+ * @param {object} componentsResponse A pRPC ListComponentsResponse object.
+ */
+function TKR_convertComponents(componentsResponse) {
+  const componentDefs = (componentsResponse.componentDefs || []);
+  const jsonData = {};
+
+  // Filter out deprecated components and normalize to name-doc object.
+  jsonData.components = [];
+  for (const c of componentDefs) {
+    if (!c.deprecated) {
+      jsonData.components.push({
+        name: c.path,
+        doc: c.docstring,
+      });
+    }
+  }
+
+  return jsonData;
+}
+
+
+/**
+ * Convert the object resulting of a monorail.Projects GetLabelOptions
+ * call to the format expected by TKR_populateAutocomplete.
+ * @param {object} labelsResponse A pRPC GetLabelOptionsResponse.
+ * @param {Array<FieldDef>=} fieldDefs FieldDefs from a project config, used to
+ *   mask labels that are used to implement custom enum fields.
+ */
+function TKR_convertLabels(labelsResponse, fieldDefs = []) {
+  const labelDefs = (labelsResponse.labelDefs || []);
+  const exclusiveLabelPrefixes = (labelsResponse.exclusiveLabelPrefixes || []);
+  const jsonData = {};
+
+  const maskedLabels = new Set();
+  fieldDefs.forEach((fd) => {
+    if (fd.enumChoices) {
+      fd.enumChoices.forEach(({label}) => {
+        maskedLabels.add(`${fd.fieldRef.fieldName}-${label}`);
+      });
+    }
+  });
+
+  jsonData.labels = labelDefs.filter(({label}) => !maskedLabels.has(label)).map(
+      (label) => ({name: label.label, doc: label.docstring}));
+
+  jsonData.excl_prefixes = exclusiveLabelPrefixes.map(
+      (prefix) => prefix.toLowerCase());
+
+  return jsonData;
+}
+
+
+/**
+ * Convert the object resulting of a monorail.Projects GetVisibleMembers
+ * call to the format expected by TKR_populateAutocomplete.
+ * @param {object?} visibleMembersResponse A pRPC GetVisibleMembersResponse.
+ * @return {{memberEmails: {name: string}, nonGroupEmails: {name: string}}}
+ */
+function TKR_convertVisibleMembers(visibleMembersResponse) {
+  if (!visibleMembersResponse) {
+    visibleMembersResponse = {};
+  }
+  const groupRefs = (visibleMembersResponse.groupRefs || []);
+  const userRefs = (visibleMembersResponse.userRefs || []);
+  const jsonData = {};
+
+  const groupEmails = new Set(groupRefs.map(
+      (groupRef) => groupRef.displayName));
+
+  jsonData.memberEmails = userRefs.map(
+      (userRef) => ({name: userRef.displayName}));
+  jsonData.nonGroupEmails = jsonData.memberEmails.filter(
+      (memberEmail) => !groupEmails.has(memberEmail));
+
+  return jsonData;
+}
+
+
+/**
+ * Convert the object resulting of a monorail.Projects ListFields to
+ * the format expected by TKR_populateAutocomplete.
+ * @param {object} fieldsResponse A pRPC ListFieldsResponse object.
+ */
+function TKR_convertFields(fieldsResponse) {
+  const fieldDefs = (fieldsResponse.fieldDefs || []);
+  const jsonData = {};
+
+  jsonData.fields = fieldDefs.map((field) =>
+    ({
+      field_id: field.fieldRef.fieldId,
+      field_name: field.fieldRef.fieldName,
+      field_type: field.fieldRef.type,
+      docstring: field.docstring,
+      choices: (field.enumChoices || []).map(
+          (choice) => ({name: choice.label, doc: choice.docstring})),
+      qualifiedMembers: (field.userChoices || []).map(
+          (userRef) => ({name: userRef.displayName})),
+    }),
+  );
+
+  return jsonData;
+}
+
+
+/**
+ * Convert the object resulting of a monorail.Features ListHotlistsByUser
+ * call to the format expected by TKR_populateAutocomplete.
+ * @param {Array<HotlistV0>} hotlists A lists of hotlists
+ * @return {Array<{ref_str: string, summary: string}>}
+ */
+function TKR_convertHotlists(hotlists) {
+  if (hotlists === undefined) {
+    return [];
+  }
+
+  const seen = new Set();
+  const ambiguousNames = new Set();
+
+  hotlists.forEach((hotlist) => {
+    if (seen.has(hotlist.name)) {
+      ambiguousNames.add(hotlist.name);
+    }
+    seen.add(hotlist.name);
+  });
+
+  return hotlists.map((hotlist) => {
+    let ref_str = hotlist.name;
+    if (ambiguousNames.has(hotlist.name)) {
+      ref_str = hotlist.owner_ref.display_name + ':' + ref_str;
+    }
+    return {ref_str: ref_str, summary: hotlist.summary};
+  });
+}
+
+
+/**
+ * Initializes hotlists in autocomplete store.
+ * @param {Array<HotlistV0>} hotlists
+ */
+function TKR_populateHotlistAutocomplete(hotlists) {
+  TKR_setUpHotlistsStore(TKR_convertHotlists(hotlists));
+}
+
+
+/**
+ * Add project config data that's already been fetched to the legacy
+ * autocomplete.
+ * @param {Config} projectConfig Returned projectConfig data.
+ * @param {GetVisibleMembersResponse} visibleMembers
+ * @param {Array<string>} customPermissions
+ */
+function TKR_populateAutocomplete(projectConfig, visibleMembers,
+    customPermissions = []) {
+  const {statusDefs, componentDefs, labelDefs, fieldDefs,
+    exclusiveLabelPrefixes, projectName} = projectConfig;
+
+  const {memberEmails, nonGroupEmails} =
+    TKR_convertVisibleMembers(visibleMembers);
+  TKR_setUpMemberStore(memberEmails, nonGroupEmails);
+  TKR_prepOwnerField(memberEmails);
+
+  const {open, closed, strict} = TKR_convertStatuses({statusDefs});
+  TKR_setUpStatusStore(open, closed);
+  TKR_restrict_to_known = strict;
+
+  const {components} = TKR_convertComponents({componentDefs});
+  TKR_setUpComponentStore(components);
+
+  const {excl_prefixes, labels} = TKR_convertLabels(
+      {labelDefs, exclusiveLabelPrefixes}, fieldDefs);
+  TKR_exclPrefixes = excl_prefixes;
+  TKR_setUpLabelStore(labels);
+
+  const {fields} = TKR_convertFields({fieldDefs});
+  TKR_setUpUserAutocompleteStores(fields);
+
+  /* QuickEdit is not yet in Monorail. crbug.com/monorail/1926
+  TKR_setUpQuickEditStore(
+      jsonData.labels, jsonData.memberEmails, jsonData.open, jsonData.closed,
+      jsonData.nonGroupEmails);
+  */
+
+  // We need to wait until both exclusive prefixes (in configPromise) and
+  // labels (in labelsPromise) have been read.
+  TKR_prepLabelAC(TKR_labelFieldIDPrefix);
+
+  TKR_setUpSearchStore(
+      labels, memberEmails, open, closed,
+      components, fields, nonGroupEmails);
+
+  TKR_setUpCustomPermissionsStore(customPermissions);
+}
diff --git a/static/js/tracker/tracker-components.js b/static/js/tracker/tracker-components.js
new file mode 100644
index 0000000..633d70b
--- /dev/null
+++ b/static/js/tracker/tracker-components.js
@@ -0,0 +1,64 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+/**
+ * This file contains JS code for editing components and component definitions.
+ */
+
+var TKR_leafNameXmlHttp;
+
+var TKR_leafNameRE = /^[a-zA-Z]([-_]?[a-zA-Z0-9])+$/;
+var TKR_oldName = '';
+
+/**
+ * Function to validate the component leaf name..
+ * @param {string} projectName Current project name.
+ * @param {string} parentPath Path to this component's parent.
+ * @param {string} originalName Original leaf name, keeping that is always OK.
+ * @param {string} token security token.
+ */
+function TKR_checkLeafName(projectName, parentPath, originalName, token) {
+  var name = $('leaf_name').value;
+  var feedback = $('leafnamefeedback');
+  if (name == originalName) {
+    $('submit_btn').disabled = '';
+    feedback.textContent = '';
+  } else if (name != TKR_oldName) {
+    $('submit_btn').disabled = 'disabled';
+    if (name == '') {
+      feedback.textContent = 'Please choose a name';
+    } else if (!TKR_leafNameRE.test(name)) {
+      feedback.textContent = 'Invalid component name';
+    } else if (name.length > 30) {
+      feedback.textContent = 'Name is too long';
+    } else {
+      TKR_checkLeafNameOnServer(projectName, parentPath, name, token);
+    }
+  }
+  TKR_oldName = name;
+}
+
+
+
+/**
+ * Function that communicates with the server.
+ * @param {string} projectName Current project name.
+ * @param {string} leafName The proposed leaf name.
+ * @param {string} token security token.
+ */
+async function TKR_checkLeafNameOnServer(projectName, parentPath, leafName) {
+  const message = {
+    project_name: projectName,
+    parent_path: parentPath,
+    component_name: leafName
+  };
+  const response = await window.prpcClient.call(
+      'monorail.Projects', 'CheckComponentName', message);
+
+  $('leafnamefeedback').textContent = response.error || '';
+  $('submit_btn').disabled = response.error ? 'disabled' : '';
+}
diff --git a/static/js/tracker/tracker-dd.js b/static/js/tracker/tracker-dd.js
new file mode 100644
index 0000000..e7b4c1e
--- /dev/null
+++ b/static/js/tracker/tracker-dd.js
@@ -0,0 +1,132 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+/**
+ * Functions used by Monorail to control drag-and-drop re-orderable lists
+ *
+ */
+
+/**
+ * Initializes the drag-and-drop functionality on the elements of a
+ * container node.
+ * TODO(lukasperaza): allow bulk drag-and-drop
+ * @param {Element} container The HTML container element to turn into
+ *    a drag-and-drop list. The items of the list must have the
+ *    class 'drag_item'
+ */
+function TKR_initDragAndDrop(container, opt_onDrop, opt_preventMultiple) {
+  let dragSrc = null;
+  let dragLocation = null;
+  let dragItems = container.getElementsByClassName('drag_item');
+  let target = null;
+
+  opt_preventMultiple = opt_preventMultiple || false;
+  opt_onDrop = opt_onDrop || function() {};
+
+  function _handleMouseDown(event) {
+    target = event.target;
+  }
+
+  function _handleDragStart(event) {
+    let el = event.currentTarget;
+    let gripper = el.getElementsByClassName('gripper');
+    if (gripper.length && !gripper[0].contains(target)) {
+      event.preventDefault();
+      return;
+    }
+    el.style.opacity = 0.4;
+    event.dataTransfer.setData('text/html', el.outerHTML);
+    event.dataTransfer.dropEffect = 'move';
+    dragSrc = el;
+  }
+
+  function inRect(rect, x, y) {
+    if (x < rect.left || x > rect.right) {
+      return '';
+    } else if (rect.top <= y && y <= rect.top + rect.height / 2) {
+      return 'top';
+    } else {
+      return 'bottom';
+    }
+  }
+
+  function _handleDragOver(event) {
+    if (dragSrc == null) {
+      return true;
+    }
+    event.preventDefault();
+    let el = event.currentTarget;
+    let rect = el.getBoundingClientRect(),
+      classes = el.classList;
+    let section = inRect(rect, event.clientX, event.clientY);
+    if (section == 'top' && !classes.contains('top')) {
+      dragLocation = 'top';
+      classes.remove('bottom');
+      classes.add('top');
+    } else if (section == 'bottom' && !classes.contains('bottom')) {
+      dragLocation = 'bottom';
+      classes.remove('top');
+      classes.add('bottom');
+    }
+    return false;
+  }
+
+  function removeClasses(el) {
+    el.classList.remove('top');
+    el.classList.remove('bottom');
+  }
+
+  function _handleDragDrop(event) {
+    let el = event.currentTarget;
+    if (dragSrc == null || el == dragSrc) {
+      return true;
+    }
+
+    if (opt_preventMultiple) {
+      let dragItems = container.getElementsByClassName('drag_item');
+      for (let i = 0; i < dragItems.length; i++) {
+        dragItems[i].setAttribute('draggable', false);
+      }
+    }
+
+    let srcID = dragSrc.getAttribute('data-id');
+    let id = el.getAttribute('data-id');
+
+    if (dragLocation == 'top') {
+      el.parentNode.insertBefore(dragSrc, el);
+      opt_onDrop(srcID, id, 'above');
+    } else if (dragLocation == 'bottom') {
+      el.parentNode.insertBefore(dragSrc, el.nextSibling);
+      opt_onDrop(srcID, id, 'below');
+    }
+    dragSrc.style.opacity = 0.4;
+    dragSrc = null;
+  }
+
+  function _handleDragEnd(event) {
+    if (dragSrc) {
+      dragSrc.style.opacity = 1;
+      dragSrc = null;
+    }
+    for (let i = 0; i < dragItems.length; i++) {
+      removeClasses(dragItems[i]);
+    }
+  }
+
+  for (let i = 0; i < dragItems.length; i++) {
+    let el = dragItems[i];
+    el.setAttribute('draggable', true);
+    el.addEventListener('mousedown', _handleMouseDown);
+    el.addEventListener('dragstart', _handleDragStart);
+    el.addEventListener('dragover', _handleDragOver);
+    el.addEventListener('drop', _handleDragDrop);
+    el.addEventListener('dragend', _handleDragEnd);
+    el.addEventListener('dragleave', function(event) {
+      removeClasses(event.currentTarget);
+    });
+  }
+}
diff --git a/static/js/tracker/tracker-display.js b/static/js/tracker/tracker-display.js
new file mode 100644
index 0000000..23b9dcf
--- /dev/null
+++ b/static/js/tracker/tracker-display.js
@@ -0,0 +1,322 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+/**
+ * Functions used by Monorail to control the display of elements on
+ * the page, rollovers, and popup menus.
+ *
+ */
+
+
+/**
+ * Show a popup menu below a specified element. Optional x and y deltas can be
+ * used to fine-tune placement.
+ * @param {string} id The HTML id of the popup menu.
+ * @param {Element} el The HTML element that the popup should appear near.
+ * @param {number} opt_deltaX Optional X offset to finetune placement.
+ * @param {number} opt_deltaY Optional Y offset to finetune placement.
+ * @param {Element} opt_menuButton The HTML element for a menu button that
+ *    was pressed to open the menu.  When a button was used, we need to ignore
+ *    the first "click" event, otherwise the menu will immediately close.
+ * @return Always returns false to indicate that the browser should handle the
+ * event normally.
+ */
+function TKR_showBelow(id, el, opt_deltaX, opt_deltaY, opt_menuButton) {
+  let popupDiv = $(id);
+  let elBounds = nodeBounds(el);
+  let startX = elBounds.x;
+  let startY = elBounds.y + elBounds.h;
+  if (BR_IsIE()) {
+    startX -= 1;
+    startY -= 2;
+  }
+  if (BR_IsSafari()) {
+    startX += 1;
+  }
+  popupDiv.style.display = 'block'; // needed so that offsetWidth != 0
+
+  popupDiv.style.left = '-2000px';
+  if (id == 'pop_dot' || id == 'redoMenu') {
+    startX = startX - popupDiv.offsetWidth + el.offsetWidth;
+  }
+  if (opt_deltaX) startX += opt_deltaX;
+  if (opt_deltaY) startY += opt_deltaY;
+  popupDiv.style.left = (startX)+'px';
+  popupDiv.style.top = (startY)+'px';
+  let popup = new TKR_MyPopup(popupDiv, opt_menuButton);
+  popup.show();
+  return false;
+}
+
+
+/**
+ * Show a popup menu to the right of a specified element. If there is not
+ * enough space to the right, then it will open to the left side instead.
+ * Optional x and y deltas can be used to fine-tune placement.
+ * TODO(jrobbins): reduce redundancy with function above.
+ * @param {string} id The HTML id of the popup menu.
+ * @param {Element} el The HTML element that the popup should appear near.
+ * @param {number} opt_deltaX Optional X offset to finetune placement.
+ * @param {number} opt_deltaY Optional Y offset to finetune placement.
+ * @return Always returns false to indicate that the browser should handle the
+ * event normally.
+ */
+function TKR_showRight(id, el, opt_deltaX, opt_deltaY) {
+  let popupDiv = $(id);
+  let elBounds = nodeBounds(el);
+  let startX = elBounds.x + elBounds.w;
+  let startY = elBounds.y;
+
+  // Calculate pageSize.w and pageSize.h
+  let docElemWidth = document.documentElement.clientWidth;
+  let docElemHeight = document.documentElement.clientHeight;
+  let pageSize = {
+    w: (window.innerWidth || docElemWidth && docElemWidth > 0 ?
+      docElemWidth : document.body.clientWidth) || 1,
+    h: (window.innerHeight || docElemHeight && docElemHeight > 0 ?
+      docElemHeight : document.body.clientHeight) || 1,
+  };
+
+  // We need to make the popupDiv visible in order to capture its width
+  popupDiv.style.display = 'block';
+  let popupDivBounds = nodeBounds(popupDiv);
+
+  // Show popup to the left
+  if (startX + popupDivBounds.w > pageSize.w) {
+    startX = elBounds.x - popupDivBounds.w;
+    if (BR_IsIE()) {
+      startX -= 4;
+      startY -= 2;
+    }
+    if (BR_IsNav()) {
+      startX -= 2;
+    }
+    if (BR_IsSafari()) {
+      startX += -1;
+    }
+
+  // Show popup to the right
+  } else {
+    if (BR_IsIE()) {
+      startY -= 2;
+    }
+    if (BR_IsNav()) {
+      startX += 2;
+    }
+    if (BR_IsSafari()) {
+      startX += 3;
+    }
+  }
+
+  popupDiv.style.left = '-2000px';
+  popupDiv.style.position = 'absolute';
+  if (opt_deltaX) startX += opt_deltaX;
+  if (opt_deltaY) startY += opt_deltaY;
+  popupDiv.style.left = (startX)+'px';
+  popupDiv.style.top = (startY)+'px';
+  let popup = new TKR_MyPopup(popupDiv);
+  popup.show();
+  return false;
+}
+
+
+/**
+ * Close the specified popup menu and unregister it with the popup
+ * controller, otherwise old leftover popup instances can mess with
+ * the future display of menus.
+ * @param {string} id The HTML ID of the element to hide.
+ */
+function TKR_closePopup(id) {
+  let e = $(id);
+  if (e) {
+    for (let i = 0; i < gPopupController.activePopups_.length; ++i) {
+      if (e === gPopupController.activePopups_[i]._div) {
+        let popup = gPopupController.activePopups_[i];
+        popup.hide();
+        gPopupController.activePopups_.splice(i, 1);
+        return;
+      }
+    }
+  }
+}
+
+
+var TKR_allColumnNames = []; // Will be defined in HTML file.
+
+/**
+ * Close all popup menus.  Also, reset the hover state of the menu item that
+ * was selected. The list of popup menu names is computed from the list of
+ * columns specified in the HTML for the issue list page.
+ * @param menuItem {Element} The menu item that the user clicked.
+ * @return Always returns false to indicate that the browser should handle the
+ * event normally.
+ */
+function TKR_closeAllPopups(menuItem) {
+  for (let col_index = 0; col_index < TKR_allColumnNames.length; col_index++) {
+    TKR_closePopup('pop_' + col_index);
+    TKR_closePopup('filter_' + col_index);
+  }
+  TKR_closePopup('pop_dot');
+  TKR_closePopup('redoMenu');
+  menuItem.classList.remove('hover');
+  return false;
+}
+
+
+/**
+ * Close all the submenus (of which, one may be currently open).
+ * @return Always returns false to indicate that the browser should handle the
+ * event normally.
+ */
+function TKR_closeSubmenus() {
+  for (let col_index = 0; col_index < TKR_allColumnNames.length; col_index++) {
+    TKR_closePopup('filter_' + col_index);
+  }
+  return false;
+}
+
+
+/**
+ * Find the enclosing HTML element that controls this section of the
+ * page and set it to use CSS class "opened".  That will make the
+ * section display in the opened state, regardless of what state is
+ * was in before.
+ * @param {Element} el The HTML element that the user clicked on.
+ * @return Always returns false to indicate that the browser should handle the
+ * event normally.
+ */
+function TKR_showHidden(el) {
+  while (el) {
+    if (el.classList.contains('closed')) {
+      el.classList.remove('closed');
+      el.classList.add('opened');
+      return false;
+    }
+    if (el.classList.contains('opened')) {
+      return false;
+    }
+    el = el.parentNode;
+  }
+}
+
+
+/**
+ * Toggle the display of a column in the issue list page.  That is
+ * done by adding or removing a CSS class of an enclosing HTML
+ * element, and by CSS rules that trigger based on that CSS class.
+ * @param {string} colName The name of the column to toggle,
+ * corresponds to a CSS class.
+ * @return Always returns false to indicate that the browser should
+ * handle the event normally.
+ */
+function TKR_toggleColumn(colName) {
+  let controlDiv = $('colcontrol');
+  if (controlDiv.classList.contains(colName)) {
+    controlDiv.classList.remove(colName);
+  } else {
+    controlDiv.classList.add(colName);
+  }
+  return false;
+}
+
+
+/**
+ * Toggle the display of a set of rows in the issue list page.  That is
+ * done by adding or removing a CSS class of an enclosing HTML
+ * element, and by CSS rules that trigger based on that CSS class.
+ * TODO(jrobbins): actually, this automatically hides the other groups.
+ * @param {string} rowClassName The name of the row group to toggle,
+ * corresponds to a CSS class.
+ * @return Always returns false to indicate that the browser should
+ * handle the event normally.
+ */
+function TKR_toggleRows(rowClassName) {
+  let controlDiv = $('colcontrol');
+  controlDiv.classList.add('hide_pri_groups');
+  controlDiv.classList.add('hide_mile_groups');
+  controlDiv.classList.add('hide_stat_groups');
+  TKR_toggleColumn(rowClassName);
+  return false;
+}
+
+
+/**
+ * A simple class that can manage the display of a popup menu.  Instances
+ * of this class are used by popup_controller.js.
+ * @param {Element} div The div that contains the popup menu.
+ * @param {Element} opt_launcherEl The button that launched the popup menu,
+ *     if any.
+ * @constructor
+ */
+function TKR_MyPopup(div, opt_launcherEl) {
+  this._div = div;
+  this._launcher = opt_launcherEl;
+  this._isVisible = false;
+}
+
+
+/**
+ * Show a popup menu.  This method registers the popup with popup_controller.
+ */
+TKR_MyPopup.prototype.show = function() {
+  this._div.style.display = 'block';
+  this._isVisible = true;
+  PC_addPopup(this);
+};
+
+
+/**
+ * Show a popup menu.  This method is called from the deactive method,
+ * which is called by popup_controller.
+ */
+TKR_MyPopup.prototype.hide = function() {
+  this._div.style.display = 'none';
+  this._isVisible = false;
+};
+
+
+/**
+ * When the popup_controller gets a user click, it calls deactive() on
+ * every active popup to check if the click should close that popup.
+ */
+TKR_MyPopup.prototype.deactivate = function(e) {
+  if (this._isVisible) {
+    let p = GetMousePosition(e);
+    if (nodeBounds(this._div).contains(p)) {
+      return false; // use clicked on popup, remain visible
+    } else if (this._launcher && nodeBounds(this._launcher).contains(p)) {
+      this._launcher = null;
+      return false; // mouseup element that launched menu, remain visible
+    } else {
+      this.hide();
+      return true; // clicked outside popup, make invisible
+    }
+  } else {
+    return true; // already deactivated, not visible
+  }
+};
+
+
+/**
+ * Highlight the issue row on the list page that contains the given
+ * checkbox.
+ * @param {Element} cb The checkbox that the user changed.
+ * @return Always returns false to indicate that the browser should
+ * handle the event normally.
+ */
+function TKR_highlightRow(el) {
+  let checked = el.checked;
+  while (el && el.tagName != 'TR') {
+    el = el.parentNode;
+  }
+  if (checked) {
+    el.classList.add('selected');
+  } else {
+    el.classList.remove('selected');
+  }
+  return false;
+}
diff --git a/static/js/tracker/tracker-editing.js b/static/js/tracker/tracker-editing.js
new file mode 100644
index 0000000..d53b515
--- /dev/null
+++ b/static/js/tracker/tracker-editing.js
@@ -0,0 +1,1823 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+/* eslint-disable no-var */
+/* eslint-disable prefer-const */
+
+/**
+ * This file contains JS functions that support various issue editing
+ * features of Monorail.  These editing features include: selecting
+ * issues on the issue list page, adding attachments, expanding and
+ * collapsing the issue editing form, and starring issues.
+ *
+ * Browser compatability: IE6, IE7, FF1.0+, Safari.
+ */
+
+
+/**
+ * Here are some string constants that are used repeatedly in the code.
+ */
+let TKR_SELECTED_CLASS = 'selected';
+let TKR_UNDEF_CLASS = 'undef';
+let TKR_NOVEL_CLASS = 'novel';
+let TKR_EXCL_CONFICT_CLASS = 'exclconflict';
+let TKR_QUESTION_MARK_CLASS = 'questionmark';
+let TKR_ATTACHPROMPT_ID = 'attachprompt';
+let TKR_ATTACHAFILE_ID = 'attachafile';
+let TKR_ATTACHMAXSIZE_ID = 'attachmaxsize';
+let TKR_CURRENT_TEMPLATE_INDEX_ID = 'current_template_index';
+let TKR_PROMPT_MEMBERS_ONLY_CHECKBOX_ID = 'members_only_checkbox';
+let TKR_PROMPT_SUMMARY_EDITOR_ID = 'summary_editor';
+let TKR_PROMPT_SUMMARY_MUST_BE_EDITED_CHECKBOX_ID =
+    'summary_must_be_edited_checkbox';
+let TKR_PROMPT_CONTENT_EDITOR_ID = 'content_editor';
+let TKR_PROMPT_STATUS_EDITOR_ID = 'status_editor';
+let TKR_PROMPT_OWNER_EDITOR_ID = 'owner_editor';
+let TKR_PROMPT_ADMIN_NAMES_EDITOR_ID = 'admin_names_editor';
+let TKR_OWNER_DEFAULTS_TO_MEMBER_CHECKBOX_ID =
+    'owner_defaults_to_member_checkbox';
+let TKR_OWNER_DEFAULTS_TO_MEMBER_AREA_ID =
+    'owner_defaults_to_member_area';
+let TKR_COMPONENT_REQUIRED_CHECKBOX_ID =
+    'component_required_checkbox';
+let TKR_PROMPT_COMPONENTS_EDITOR_ID = 'components_editor';
+let TKR_FIELD_EDITOR_ID_PREFIX = 'tmpl_custom_';
+let TKR_PROMPT_LABELS_EDITOR_ID_PREFIX = 'label';
+let TKR_CONFIRMAREA_ID = 'confirmarea';
+let TKR_DISCARD_YOUR_CHANGES = 'Discard your changes?';
+// Note, users cannot enter '<'.
+let TKR_DELETED_PROMPT_NAME = '<DELETED>';
+// Display warning if labels contain the following prefixes.
+// The following list is the same as tracker_constants.RESERVED_PREFIXES except
+// for the 'hotlist' prefix. 'hostlist' will be added when it comes a full
+// feature and when projects that use 'Hostlist-*' labels are transitioned off.
+let TKR_LABEL_RESERVED_PREFIXES = [
+  'id', 'project', 'reporter', 'summary', 'status', 'owner', 'cc',
+  'attachments', 'attachment', 'component', 'opened', 'closed',
+  'modified', 'is', 'has', 'blockedon', 'blocking', 'blocked', 'mergedinto',
+  'stars', 'starredby', 'description', 'comment', 'commentby', 'label',
+  'rank', 'explicit_status', 'derived_status', 'explicit_owner',
+  'derived_owner', 'explicit_cc', 'derived_cc', 'explicit_label',
+  'derived_label', 'last_comment_by', 'exact_component',
+  'explicit_component', 'derived_component'];
+
+
+/**
+ * Appends a given child element to the DOM based on parameters.
+ * @param {HTMLElement} parentEl
+ * @param {string} tag
+ * @param {string} optClassName
+ * @param {string} optID
+ * @param {string} optText
+ * @param {string} optStyle
+*/
+function TKR_createChild(parentEl, tag, optClassName, optID, optText, optStyle) {
+  let el = document.createElement(tag);
+  if (optClassName) el.classList.add(optClassName);
+  if (optID) el.id = optID;
+  if (optText) el.textContent = optText;
+  if (optStyle) el.setAttribute('style', optStyle);
+  parentEl.appendChild(el);
+  return el;
+}
+
+/**
+ * Select all the issues on the issue list page.
+ */
+function TKR_selectAllIssues() {
+  TKR_selectIssues(true);
+}
+
+
+/**
+ * Function to deselect all the issues on the issue list page.
+ */
+function TKR_selectNoneIssues() {
+  TKR_selectIssues(false);
+}
+
+
+/**
+ * Function to select or deselect all the issues on the issue list page.
+ * @param {boolean} checked True means select issues, False means deselect.
+ */
+function TKR_selectIssues(checked) {
+  let table = $('resultstable');
+  for (let r = 0; r < table.rows.length; ++r) {
+    let row = table.rows[r];
+    let firstCell = row.cells[0];
+    if (firstCell.tagName == 'TD') {
+      for (let e = 0; e < firstCell.childNodes.length; ++e) {
+        let element = firstCell.childNodes[e];
+        if (element.tagName == 'INPUT' && element.type == 'checkbox') {
+          element.checked = checked ? 'checked' : '';
+          if (checked) {
+            row.classList.add(TKR_SELECTED_CLASS);
+          } else {
+            row.classList.remove(TKR_SELECTED_CLASS);
+          }
+        }
+      }
+    }
+  }
+}
+
+
+/**
+ * The ID number to append to the next dynamically created file upload field.
+ */
+let TKR_nextFileID = 1;
+
+
+/**
+ * Function to dynamically create a new attachment upload field add
+ * insert it into the page DOM.
+ * @param {string} id The id of the parent HTML element.
+ *
+ * TODO(lukasperaza): use different nextFileID for separate forms on same page,
+ *  e.g. issue update form and issue description update form
+ */
+function TKR_addAttachmentFields(id, attachprompt_id,
+    attachafile_id, attachmaxsize_id) {
+  if (TKR_nextFileID >= 16) {
+    return;
+  }
+  if (typeof attachprompt_id === 'undefined') {
+    attachprompt_id = TKR_ATTACHPROMPT_ID;
+  }
+  if (typeof attachafile_id === 'undefined') {
+    attachafile_id = TKR_ATTACHAFILE_ID;
+  }
+  if (typeof attachmaxsize_id === 'undefined') {
+    attachmaxsize_id = TKR_ATTACHMAXSIZE_ID;
+  }
+  let el = $(id);
+  el.style.marginTop = '4px';
+  let div = document.createElement('div');
+  var id = 'file' + TKR_nextFileID;
+  let label = TKR_createChild(div, 'label', null, null, 'Attach file:');
+  label.setAttribute('for', id);
+  let input = TKR_createChild(
+      div, 'input', null, id, null, 'width:auto;margin-left:17px');
+  input.setAttribute('type', 'file');
+  input.name = id;
+  let removeLink = TKR_createChild(
+      div, 'a', null, null, 'Remove', 'font-size:x-small');
+  removeLink.href = '#';
+  removeLink.addEventListener('click', function(event) {
+    let target = event.target;
+    $(attachafile_id).focus();
+    target.parentNode.parentNode.removeChild(target.parentNode);
+    event.preventDefault();
+  });
+  el.appendChild(div);
+  el.querySelector('input').focus();
+  ++TKR_nextFileID;
+  if (TKR_nextFileID < 16) {
+    $(attachafile_id).textContent = 'Attach another file';
+  } else {
+    $(attachprompt_id).style.display = 'none';
+  }
+  $(attachmaxsize_id).style.display = '';
+}
+
+
+/**
+ * Function to display the form so that the user can update an issue.
+ */
+function TKR_openIssueUpdateForm() {
+  TKR_showHidden($('makechangesarea'));
+  TKR_goToAnchor('makechanges');
+  TKR_forceProperTableWidth();
+  window.setTimeout(
+      function() {
+        document.getElementById('addCommentTextArea').focus();
+      },
+      100);
+}
+
+
+/**
+ * The index of the template that is currently selected for editing
+ * on the administration page for issues.
+ */
+let TKR_currentTemplateIndex = 0;
+
+
+/**
+ * Array of field IDs that are defined in the current project, set by call to setFieldIDs().
+ */
+let TKR_fieldIDs = [];
+
+
+function TKR_setFieldIDs(fieldIDs) {
+  TKR_fieldIDs = fieldIDs;
+}
+
+
+/**
+ * This function displays the appropriate template text in a text field.
+ * It is called after the user has selected one template to view/edit.
+ * @param {Element} widget The list widget containing the list of templates.
+ */
+function TKR_selectTemplate(widget) {
+  TKR_showHidden($('edit_panel'));
+  TKR_currentTemplateIndex = widget.value;
+  $(TKR_CURRENT_TEMPLATE_INDEX_ID).value = TKR_currentTemplateIndex;
+
+  let content_editor = $(TKR_PROMPT_CONTENT_EDITOR_ID);
+  TKR_makeDefined(content_editor);
+
+  let can_edit = $('can_edit_' + TKR_currentTemplateIndex).value == 'yes';
+  let disabled = can_edit ? '' : 'disabled';
+
+  $(TKR_PROMPT_MEMBERS_ONLY_CHECKBOX_ID).disabled = disabled;
+  $(TKR_PROMPT_MEMBERS_ONLY_CHECKBOX_ID).checked = $(
+      'members_only_' + TKR_currentTemplateIndex).value == 'yes';
+  $(TKR_PROMPT_SUMMARY_EDITOR_ID).disabled = disabled;
+  $(TKR_PROMPT_SUMMARY_EDITOR_ID).value = $(
+      'summary_' + TKR_currentTemplateIndex).value;
+  $(TKR_PROMPT_SUMMARY_MUST_BE_EDITED_CHECKBOX_ID).disabled = disabled;
+  $(TKR_PROMPT_SUMMARY_MUST_BE_EDITED_CHECKBOX_ID).checked = $(
+      'summary_must_be_edited_' + TKR_currentTemplateIndex).value == 'yes';
+  content_editor.disabled = disabled;
+  content_editor.value = $('content_' + TKR_currentTemplateIndex).value;
+  $(TKR_PROMPT_STATUS_EDITOR_ID).disabled = disabled;
+  $(TKR_PROMPT_STATUS_EDITOR_ID).value = $(
+      'status_' + TKR_currentTemplateIndex).value;
+  $(TKR_PROMPT_OWNER_EDITOR_ID).disabled = disabled;
+  $(TKR_PROMPT_OWNER_EDITOR_ID).value = $(
+      'owner_' + TKR_currentTemplateIndex).value;
+  $(TKR_OWNER_DEFAULTS_TO_MEMBER_CHECKBOX_ID).disabled = disabled;
+  $(TKR_OWNER_DEFAULTS_TO_MEMBER_CHECKBOX_ID).checked = $(
+      'owner_defaults_to_member_' + TKR_currentTemplateIndex).value == 'yes';
+  $(TKR_COMPONENT_REQUIRED_CHECKBOX_ID).disabled = disabled;
+  $(TKR_COMPONENT_REQUIRED_CHECKBOX_ID).checked = $(
+      'component_required_' + TKR_currentTemplateIndex).value == 'yes';
+  $(TKR_OWNER_DEFAULTS_TO_MEMBER_AREA_ID).disabled = disabled;
+  $(TKR_OWNER_DEFAULTS_TO_MEMBER_AREA_ID).style.display =
+      $(TKR_PROMPT_OWNER_EDITOR_ID).value ? 'none' : '';
+  $(TKR_PROMPT_COMPONENTS_EDITOR_ID).disabled = disabled;
+  $(TKR_PROMPT_COMPONENTS_EDITOR_ID).value = $(
+      'components_' + TKR_currentTemplateIndex).value;
+
+  // Blank out all custom field editors first, then fill them in during the next loop.
+  for (var i = 0; i < TKR_fieldIDs.length; i++) {
+    let fieldEditor = $(TKR_FIELD_EDITOR_ID_PREFIX + TKR_fieldIDs[i]);
+    let holder = $('field_value_' + TKR_currentTemplateIndex + '_' + TKR_fieldIDs[i]);
+    if (fieldEditor) {
+      fieldEditor.disabled = disabled;
+      fieldEditor.value = holder ? holder.value : '';
+    }
+  }
+
+  var i = 0;
+  while ($(TKR_PROMPT_LABELS_EDITOR_ID_PREFIX + i)) {
+    $(TKR_PROMPT_LABELS_EDITOR_ID_PREFIX + i).disabled = disabled;
+    $(TKR_PROMPT_LABELS_EDITOR_ID_PREFIX + i).value =
+        $('label_' + TKR_currentTemplateIndex + '_' + i).value;
+    i++;
+  }
+
+  $(TKR_PROMPT_ADMIN_NAMES_EDITOR_ID).disabled = disabled;
+  $(TKR_PROMPT_ADMIN_NAMES_EDITOR_ID).value = $(
+      'admin_names_' + TKR_currentTemplateIndex).value;
+
+  let numNonDeletedTemplates = 0;
+  for (var i = 0; i < TKR_templateNames.length; i++) {
+    if (TKR_templateNames[i] != TKR_DELETED_PROMPT_NAME) {
+      numNonDeletedTemplates++;
+    }
+  }
+  if ($('delbtn')) {
+    if (numNonDeletedTemplates > 1) {
+      $('delbtn').disabled='';
+    } else { // Don't allow the last template to be deleted.
+      $('delbtn').disabled='disabled';
+    }
+  }
+}
+
+
+var TKR_templateNames = []; // Exported in tracker-onload.js
+
+
+/**
+ * Create a new issue template and add the needed form fields to the DOM.
+ */
+function TKR_newTemplate() {
+  let newIndex = TKR_templateNames.length;
+  let templateName = prompt('Name of new template?', '');
+  templateName = templateName.replace(
+      /[&<>"]/g, '', // " help emacs highlighting
+  );
+  if (!templateName) return;
+
+  for (let i = 0; i < TKR_templateNames.length; i++) {
+    if (templateName == TKR_templateNames[i]) {
+      alert('Please choose a unique name.');
+      return;
+    }
+  }
+
+  TKR_addTemplateHiddenFields(newIndex, templateName);
+  TKR_templateNames.push(templateName);
+
+  let templateOption = TKR_createChild(
+      $('template_menu'), 'option', null, null, templateName);
+  templateOption.value = newIndex;
+  templateOption.selected = 'selected';
+
+  let developerOption = TKR_createChild(
+      $('default_template_for_developers'), 'option', null, null, templateName);
+  developerOption.value = templateName;
+
+  let userOption = TKR_createChild(
+      $('default_template_for_users'), 'option', null, null, templateName);
+  userOption.value = templateName;
+
+  TKR_selectTemplate($('template_menu'));
+}
+
+
+/**
+ * Private function to append HTML for new hidden form fields
+ * for a new issue template to the issue admin form.
+ */
+function TKR_addTemplateHiddenFields(templateIndex, templateName) {
+  let parentEl = $('adminTemplates');
+  TKR_appendHiddenField(
+      parentEl, 'template_id_' + templateIndex, 'template_id_' + templateIndex, '0');
+  TKR_appendHiddenField(parentEl, 'name_' + templateIndex,
+      'name_' + templateIndex, templateName);
+  TKR_appendHiddenField(parentEl, 'members_only_' + templateIndex);
+  TKR_appendHiddenField(parentEl, 'summary_' + templateIndex);
+  TKR_appendHiddenField(parentEl, 'summary_must_be_edited_' + templateIndex);
+  TKR_appendHiddenField(parentEl, 'content_' + templateIndex);
+  TKR_appendHiddenField(parentEl, 'status_' + templateIndex);
+  TKR_appendHiddenField(parentEl, 'owner_' + templateIndex);
+  TKR_appendHiddenField(
+      parentEl, 'owner_defaults_to_member_' + templateIndex,
+      'owner_defaults_to_member_' + templateIndex, 'yes');
+  TKR_appendHiddenField(parentEl, 'component_required_' + templateIndex);
+  TKR_appendHiddenField(parentEl, 'components_' + templateIndex);
+
+  var i = 0;
+  while ($('label_0_' + i)) {
+    TKR_appendHiddenField(parentEl, 'label_' + templateIndex,
+        'label_' + templateIndex + '_' + i);
+    i++;
+  }
+
+  for (var i = 0; i < TKR_fieldIDs.length; i++) {
+    let fieldId = 'field_value_' + templateIndex + '_' + TKR_fieldIDs[i];
+    TKR_appendHiddenField(parentEl, fieldId, fieldId);
+  }
+
+  TKR_appendHiddenField(parentEl, 'admin_names_' + templateIndex);
+  TKR_appendHiddenField(
+      parentEl, 'can_edit_' + templateIndex, 'can_edit_' + templateIndex,
+      'yes');
+}
+
+
+/**
+ * Utility function to append string parts for one hidden field
+ * to the given array.
+ */
+function TKR_appendHiddenField(parentEl, name, opt_id, opt_value) {
+  let input = TKR_createChild(parentEl, 'input', null, opt_id || name);
+  input.setAttribute('type', 'hidden');
+  input.name = name;
+  input.value = opt_value || '';
+}
+
+
+/**
+ * Delete the currently selected issue template, and mark its hidden
+ * form field as deleted so that they will be ignored when submitted.
+ */
+function TKR_deleteTemplate() {
+  // Mark the current template name as deleted.
+  TKR_templateNames.splice(
+      TKR_currentTemplateIndex, 1, TKR_DELETED_PROMPT_NAME);
+  $('name_' + TKR_currentTemplateIndex).value = TKR_DELETED_PROMPT_NAME;
+  _toggleHidden($('edit_panel'));
+  $('delbtn').disabled = 'disabled';
+  TKR_rebuildTemplateMenu();
+  TKR_rebuildDefaultTemplateMenu('default_template_for_developers');
+  TKR_rebuildDefaultTemplateMenu('default_template_for_users');
+}
+
+/**
+ * Utility function to rebuild the template menu on the issue admin page.
+ */
+function TKR_rebuildTemplateMenu() {
+  let parentEl = $('template_menu');
+  while (parentEl.childNodes.length) {
+    parentEl.removeChild(parentEl.childNodes[0]);
+  }
+  for (let i = 0; i < TKR_templateNames.length; i++) {
+    if (TKR_templateNames[i] != TKR_DELETED_PROMPT_NAME) {
+      let option = TKR_createChild(
+          parentEl, 'option', null, null, TKR_templateNames[i]);
+      option.value = i;
+    }
+  }
+}
+
+
+/**
+ * Utility function to rebuild a default template drop-down.
+ */
+function TKR_rebuildDefaultTemplateMenu(menuID) {
+  let defaultTemplateName = $(menuID).value;
+  let parentEl = $(menuID);
+  while (parentEl.childNodes.length) {
+    parentEl.removeChild(parentEl.childNodes[0]);
+  }
+  for (let i = 0; i < TKR_templateNames.length; i++) {
+    if (TKR_templateNames[i] != TKR_DELETED_PROMPT_NAME) {
+      let option = TKR_createChild(
+          parentEl, 'option', null, null, TKR_templateNames[i]);
+      option.values = TKR_templateNames[i];
+      if (defaultTemplateName == TKR_templateNames[i]) {
+        option.setAttribute('selected', 'selected');
+      }
+    }
+  }
+}
+
+
+/**
+ * Change the issue template to the specified one.
+ * TODO(jrobbins): move to an AJAX implementation that would not reload page.
+ *
+ * @param {string} projectName The name of the current project.
+ * @param {string} templateName The name of the template to switch to.
+ */
+function TKR_switchTemplate(projectName, templateName) {
+  let ok = true;
+  if (TKR_isDirty()) {
+    ok = confirm('Switching to a different template will lose the text you entered.');
+  }
+  if (ok) {
+    TKR_initialFormValues = TKR_currentFormValues();
+    window.location = '/p/' + projectName +
+      '/issues/entry?template=' + templateName;
+  }
+}
+
+/**
+ * Function to remove a CSS class and initial tip from a text widget.
+ * Some text fields or text areas display gray textual tips to help the user
+ * make use of those widgets.  When the user focuses on the field, the tip
+ * disappears and is made ready for user input (in the normal text color).
+ * @param {Element} el The form field that had the gray text tip.
+ */
+function TKR_makeDefined(el) {
+  if (el.classList.contains(TKR_UNDEF_CLASS)) {
+    el.classList.remove(TKR_UNDEF_CLASS);
+    el.value = '';
+  }
+}
+
+
+/**
+ * Save the contents of the visible issue template text area into a hidden
+ * text field for later submission.
+ * Called when the user has edited the text of a issue template.
+ */
+function TKR_saveTemplate() {
+  if (TKR_currentTemplateIndex) {
+    $('members_only_' + TKR_currentTemplateIndex).value =
+        $(TKR_PROMPT_MEMBERS_ONLY_CHECKBOX_ID).checked ? 'yes' : '';
+    $('summary_' + TKR_currentTemplateIndex).value =
+        $(TKR_PROMPT_SUMMARY_EDITOR_ID).value;
+    $('summary_must_be_edited_' + TKR_currentTemplateIndex).value =
+        $(TKR_PROMPT_SUMMARY_MUST_BE_EDITED_CHECKBOX_ID).checked ? 'yes' : '';
+    $('content_' + TKR_currentTemplateIndex).value =
+        $(TKR_PROMPT_CONTENT_EDITOR_ID).value;
+    $('status_' + TKR_currentTemplateIndex).value =
+        $(TKR_PROMPT_STATUS_EDITOR_ID).value;
+    $('owner_' + TKR_currentTemplateIndex).value =
+        $(TKR_PROMPT_OWNER_EDITOR_ID).value;
+    $('owner_defaults_to_member_' + TKR_currentTemplateIndex).value =
+        $(TKR_OWNER_DEFAULTS_TO_MEMBER_CHECKBOX_ID).checked ? 'yes' : '';
+    $('component_required_' + TKR_currentTemplateIndex).value =
+        $(TKR_COMPONENT_REQUIRED_CHECKBOX_ID).checked ? 'yes' : '';
+    $('components_' + TKR_currentTemplateIndex).value =
+        $(TKR_PROMPT_COMPONENTS_EDITOR_ID).value;
+    $(TKR_OWNER_DEFAULTS_TO_MEMBER_AREA_ID).style.display =
+        $(TKR_PROMPT_OWNER_EDITOR_ID).value ? 'none' : '';
+
+    for (var i = 0; i < TKR_fieldIDs.length; i++) {
+      let fieldID = TKR_fieldIDs[i];
+      let fieldEditor = $(TKR_FIELD_EDITOR_ID_PREFIX + fieldID);
+      if (fieldEditor) {
+        _saveFieldValue(fieldID, fieldEditor.value);
+      }
+    }
+
+    var i = 0;
+    while ($('label_' + TKR_currentTemplateIndex + '_' + i)) {
+      $('label_' + TKR_currentTemplateIndex + '_' + i).value =
+         $(TKR_PROMPT_LABELS_EDITOR_ID_PREFIX + i).value;
+      i++;
+    }
+
+    $('admin_names_' + TKR_currentTemplateIndex).value =
+        $(TKR_PROMPT_ADMIN_NAMES_EDITOR_ID).value;
+  }
+}
+
+
+function _saveFieldValue(fieldID, val) {
+  let fieldValId = 'field_value_' + TKR_currentTemplateIndex + '_' + fieldID;
+  $(fieldValId).value = val;
+}
+
+
+/**
+ * This is a json string encoding of an array of form values after the initial
+ * page load. It is used for comparison on page unload to prompt the user
+ * before abandoning changes. It is initialized in TKR_onload().
+*/
+let TKR_initialFormValues;
+
+
+/**
+ * Returns a json string encoding of an array of all the values from user
+ * input fields of interest (omits search box, e.g.)
+ */
+function TKR_currentFormValues() {
+  let inputs = document.querySelectorAll('input, textarea, select, checkbox');
+  let values = [];
+
+  for (i = 0; i < inputs.length; i++) {
+    // Don't include blank inputs. This prevents a popup if the user
+    // clicks "add a row" for new labels but doesn't actually enter any
+    // text into them. Also ignore search box contents.
+    if (inputs[i].value && !inputs[i].hasAttribute('ignore-dirty') &&
+        inputs[i].name != 'token') {
+      values.push(inputs[i].value);
+    }
+  }
+
+  return JSON.stringify(values);
+}
+
+
+/**
+ * This function returns true if the user has made any edits to fields of
+ * interest.
+ */
+function TKR_isDirty() {
+  return TKR_initialFormValues != TKR_currentFormValues();
+}
+
+
+/**
+ * The user has clicked the 'Discard' button on the issue update form.
+ * If the form has been edited, ask if they are sure about discarding
+ * before then navigating to the given URL.  This can go up to some
+ * other page, or reload the current page with a fresh form.
+ * @param {string} nextUrl The page to show after discarding.
+ */
+function TKR_confirmDiscardUpdate(nextUrl) {
+  if (!TKR_isDirty() || confirm(TKR_DISCARD_YOUR_CHANGES)) {
+    document.location = nextUrl;
+  }
+}
+
+
+/**
+ * The user has clicked the 'Discard' button on the issue entry form.
+ * If the form has been edited, this function asks if they are sure about
+ * discarding before doing it.
+ * @param {Element} discardButton The 'Discard' button.
+ */
+function TKR_confirmDiscardEntry(discardButton) {
+  if (!TKR_isDirty() || confirm(TKR_DISCARD_YOUR_CHANGES)) {
+    TKR_go('list');
+  }
+}
+
+
+/**
+ * Normally, we show 2 rows of label editing fields when updating an issue.
+ * However, if the issue has more than that many labels already, we make sure to
+ * show them all.
+ */
+function TKR_exposeExistingLabelFields() {
+  if ($('label3').value ||
+      $('label4').value ||
+      $('label5').value) {
+    if ($('addrow1')) {
+      _showID('LF_row2');
+      _hideID('addrow1');
+    }
+  }
+  if ($('label6').value ||
+      $('label7').value ||
+      $('label8').value) {
+    _showID('LF_row3');
+    _hideID('addrow2');
+  }
+  if ($('label9').value ||
+      $('label10').value ||
+      $('label11').value) {
+    _showID('LF_row4');
+    _hideID('addrow3');
+  }
+  if ($('label12').value ||
+      $('label13').value ||
+      $('label14').value) {
+    _showID('LF_row5');
+    _hideID('addrow4');
+  }
+  if ($('label15').value ||
+      $('label16').value ||
+      $('label17').value) {
+    _showID('LF_row6');
+    _hideID('addrow5');
+  }
+  if ($('label18').value ||
+      $('label19').value ||
+      $('label20').value) {
+    _showID('LF_row7');
+    _hideID('addrow6');
+  }
+  if ($('label21').value ||
+      $('label22').value ||
+      $('label23').value) {
+    _showID('LF_row8');
+    _hideID('addrow7');
+  }
+}
+
+
+/**
+ * Flag to indicate when the user has not yet caused any input events.
+ * We use this to clear the placeholder in the new issue summary field
+ * exactly once.
+ */
+let TKR_firstEvent = true;
+
+
+/**
+ * This is called in response to almost any user input event on the
+ * issue entry page.  If the placeholder in the new issue sumary field has
+ * not yet been cleared, then this function clears it.
+ */
+function TKR_clearOnFirstEvent(initialSummary) {
+  if (TKR_firstEvent && $('summary').value == initialSummary) {
+    TKR_firstEvent = false;
+    $('summary').value = TKR_keepJustSummaryPrefixes($('summary').value);
+  }
+}
+
+/**
+ * Clear the summary, except for any prefixes of the form "[bracketed text]"
+ * or "keyword:".  If there were any, add a trailing space.  This is useful
+ * to people who like to encode issue classification info in the summary line.
+ */
+function TKR_keepJustSummaryPrefixes(s) {
+  let matches = s.match(/^(\[[^\]]+\])+|^(\S+:\s*)+/);
+  if (matches == null) {
+    return '';
+  }
+
+  let prefix = matches[0];
+  if (prefix.substr(prefix.length - 1) != ' ') {
+    prefix += ' ';
+  }
+  return prefix;
+}
+
+/**
+ * An array of label <input>s that start with reserved prefixes.
+ */
+let TKR_labelsWithReservedPrefixes = [];
+
+/**
+ * An array of label <input>s that are equal to reserved words.
+ */
+let TKR_labelsConflictingWithReserved = [];
+
+/**
+ * An array of novel issue status values entered by the user on the
+ * current page. 'Novel' means that they are not well known and are
+ * likely to be typos.  Note that this list will always have zero or
+ * one element, but a list is used for consistency with the list of
+ * novel labels.
+ */
+let TKR_novelStatuses = [];
+
+/**
+ * An array of novel issue label values entered by the user on the
+ * current page. 'Novel' means that they are not well known and are
+ * likely to be typos.
+ */
+let TKR_novelLabels = [];
+
+/**
+ * A boolean that indicates whether the entered owner value is valid or not.
+ */
+let TKR_invalidOwner = false;
+
+/**
+ * The user has changed the issue status text field.  This function
+ * checks whether it is a well-known status value.  If not, highlight it
+ * as a potential typo.
+ * @param {Element} textField The issue status text field.
+ * @return Always returns true to indicate that the browser should
+ * continue to process the user input event normally.
+ */
+function TKR_confirmNovelStatus(textField) {
+  let v = textField.value.trim().toLowerCase();
+  let isNovel = (v !== '');
+  let wellKnown = TKR_statusWords;
+  for (let i = 0; i < wellKnown.length && isNovel; ++i) {
+    let wk = wellKnown[i];
+    if (v == wk.toLowerCase()) {
+      isNovel = false;
+    }
+  }
+  if (isNovel) {
+    if (TKR_novelStatuses.indexOf(textField) == -1) {
+      TKR_novelStatuses.push(textField);
+    }
+    textField.classList.add(TKR_NOVEL_CLASS);
+  } else {
+    if (TKR_novelStatuses.indexOf(textField) != -1) {
+      TKR_novelStatuses.splice(TKR_novelStatuses.indexOf(textField), 1);
+    }
+    textField.classList.remove(TKR_NOVEL_CLASS);
+  }
+  TKR_updateConfirmBeforeSubmit();
+  return true;
+}
+
+
+/**
+ * The user has changed a issue label text field.  This function checks
+ * whether it is a well-known label value.  If not, highlight it as a
+ * potential typo.
+ * @param {Element} textField An issue label text field.
+ * @return Always returns true to indicate that the browser should
+ * continue to process the user input event normally.
+ *
+ * TODO(jrobbins): code duplication with function above.
+ */
+function TKR_confirmNovelLabel(textField) {
+  let v = textField.value.trim().toLowerCase();
+  if (v.search('-') == 0) {
+    v = v.substr(1);
+  }
+  let isNovel = (v !== '');
+  if (v.indexOf('?') > -1) {
+    isNovel = false; // We don't count labels that the user must edit anyway.
+  }
+  let wellKnown = TKR_labelWords;
+  for (var i = 0; i < wellKnown.length && isNovel; ++i) {
+    let wk = wellKnown[i];
+    if (v == wk.toLowerCase()) {
+      isNovel = false;
+    }
+  }
+
+  let containsReservedPrefix = false;
+  var textFieldWarningDisplayed = TKR_labelsWithReservedPrefixes.indexOf(textField) != -1;
+  for (var i = 0; i < TKR_LABEL_RESERVED_PREFIXES.length; ++i) {
+    if (v.startsWith(TKR_LABEL_RESERVED_PREFIXES[i] + '-')) {
+      if (!textFieldWarningDisplayed) {
+        TKR_labelsWithReservedPrefixes.push(textField);
+      }
+      containsReservedPrefix = true;
+      break;
+    }
+  }
+  if (!containsReservedPrefix && textFieldWarningDisplayed) {
+    TKR_labelsWithReservedPrefixes.splice(
+        TKR_labelsWithReservedPrefixes.indexOf(textField), 1);
+  }
+
+  let conflictsWithReserved = false;
+  var textFieldWarningDisplayed =
+      TKR_labelsConflictingWithReserved.indexOf(textField) != -1;
+  for (var i = 0; i < TKR_LABEL_RESERVED_PREFIXES.length; ++i) {
+    if (v == TKR_LABEL_RESERVED_PREFIXES[i]) {
+      if (!textFieldWarningDisplayed) {
+        TKR_labelsConflictingWithReserved.push(textField);
+      }
+      conflictsWithReserved = true;
+      break;
+    }
+  }
+  if (!conflictsWithReserved && textFieldWarningDisplayed) {
+    TKR_labelsConflictingWithReserved.splice(
+        TKR_labelsConflictingWithReserved.indexOf(textField), 1);
+  }
+
+  if (isNovel) {
+    if (TKR_novelLabels.indexOf(textField) == -1) {
+      TKR_novelLabels.push(textField);
+    }
+    textField.classList.add(TKR_NOVEL_CLASS);
+  } else {
+    if (TKR_novelLabels.indexOf(textField) != -1) {
+      TKR_novelLabels.splice(TKR_novelLabels.indexOf(textField), 1);
+    }
+    textField.classList.remove(TKR_NOVEL_CLASS);
+  }
+  TKR_updateConfirmBeforeSubmit();
+  return true;
+}
+
+/**
+ * Dictionary { prefix:[textField,...], ...} for all the prefixes of any
+ * text that has been entered into any label field.  This is used to find
+ * duplicate labels and multiple labels that share an single exclusive
+ * prefix (e.g., Priority).
+ */
+let TKR_usedPrefixes = {};
+
+/**
+ * This is a prefix to the HTML ids of each label editing field.
+ * It varied by page, so it is set in the HTML page.  Needed to initialize
+ * our validation across label input text fields.
+ */
+let TKR_labelFieldIDPrefix = '';
+
+/**
+ * Initialize the set of all used labels on forms that allow users to
+ * enter issue labels.  Some labels are supplied in the HTML page
+ * itself, and we do not want to offer duplicates of those.
+ */
+function TKR_prepLabelAC() {
+  let i = 0;
+  while ($('label'+i)) {
+    TKR_validateLabel($('label'+i));
+    i++;
+  }
+}
+
+/**
+ * Reads the owner field and determines if the current value is a valid member.
+ */
+function TKR_prepOwnerField(validOwners) {
+  if ($('owneredit')) {
+    currentOwner = $('owneredit').value;
+    if (currentOwner == '') {
+      // Empty owner field is not an invalid owner.
+      invalidOwner = false;
+      return;
+    }
+    invalidOwner = true;
+    for (let i = 0; i < validOwners.length; i++) {
+      let owner = validOwners[i].name;
+      if (currentOwner == owner) {
+        invalidOwner = false;
+        break;
+      }
+    }
+    TKR_invalidOwner = invalidOwner;
+  }
+}
+
+/**
+ * Keep track of which label prefixes have been used so that
+ * we can not offer the same label twice and so that we can highlight
+ * multiple labels that share an exclusive prefix.
+ */
+function TKR_updateUsedPrefixes(textField) {
+  if (textField.oldPrefix != undefined) {
+    DeleteArrayElement(TKR_usedPrefixes[textField.oldPrefix], textField);
+  }
+
+  let prefix = textField.value.split('-')[0].toLowerCase();
+  if (TKR_usedPrefixes[prefix] == undefined) {
+    TKR_usedPrefixes[prefix] = [textField];
+  } else {
+    TKR_usedPrefixes[prefix].push(textField);
+  }
+  textField.oldPrefix = prefix;
+}
+
+/**
+ * Go through all the label entry fields in our prefix-oriented
+ * data structure and highlight any that are part of a conflict
+ * (multiple labels with the same exclusive prefix).  Unhighlight
+ * any label text entry fields that are not in conflict.  And, display
+ * a warning message to encourage the user to correct the conflict.
+ */
+function TKR_highlightExclusiveLabelPrefixConflicts() {
+  let conflicts = [];
+  for (let prefix in TKR_usedPrefixes) {
+    let textFields = TKR_usedPrefixes[prefix];
+    if (textFields == undefined || textFields.length == 0) {
+      delete TKR_usedPrefixes[prefix];
+    } else if (textFields.length > 1 &&
+        FindInArray(TKR_exclPrefixes, prefix) != -1) {
+      conflicts.push(prefix);
+      for (var i = 0; i < textFields.length; i++) {
+        var tf = textFields[i];
+        tf.classList.add(TKR_EXCL_CONFICT_CLASS);
+      }
+    } else {
+      for (var i = 0; i < textFields.length; i++) {
+        var tf = textFields[i];
+        tf.classList.remove(TKR_EXCL_CONFICT_CLASS);
+      }
+    }
+  }
+  if (conflicts.length > 0) {
+    let severity = TKR_restrict_to_known ? 'Error' : 'Warning';
+    let confirm_area = $(TKR_CONFIRMAREA_ID);
+    if (confirm_area) {
+      $('confirmmsg').textContent = (severity +
+          ': Multiple values for: ' + conflicts.join(', '));
+      confirm_area.className = TKR_EXCL_CONFICT_CLASS;
+      confirm_area.style.display = '';
+    }
+  }
+}
+
+/**
+ * Keeps track of any label text fields that have a value that
+ * is bad enough to prevent submission of the form.  When this
+ * list is non-empty, the submit button gets disabled.
+ */
+let TKR_labelsBlockingSubmit = [];
+
+/**
+ * Look for any "?" characters in the label and, if found,
+ * make the label text red, prevent form submission, and
+ * display on-page help to tell the user to edit those labels.
+ * @param {Element} textField An issue label text field.
+ */
+function TKR_highlightQuestionMarks(textField) {
+  let tfIndex = TKR_labelsBlockingSubmit.indexOf(textField);
+  if (textField.value.indexOf('?') > -1 && tfIndex == -1) {
+    TKR_labelsBlockingSubmit.push(textField);
+    textField.classList.add(TKR_QUESTION_MARK_CLASS);
+  } else if (textField.value.indexOf('?') == -1 && tfIndex > -1) {
+    TKR_labelsBlockingSubmit.splice(tfIndex, 1);
+    textField.classList.remove(TKR_QUESTION_MARK_CLASS);
+  }
+
+  let block_submit_msg = $('blocksubmitmsg');
+  if (block_submit_msg) {
+    if (TKR_labelsBlockingSubmit.length > 0) {
+      block_submit_msg.textContent = 'You must edit labels that contain "?".';
+    } else {
+      block_submit_msg.textContent = '';
+    }
+  }
+}
+
+/**
+ * The user has edited a label.  Display a warning if the label is
+ * not a well known label, or if there are multiple labels that
+ * share an exclusive prefix.
+ * @param {Element} textField An issue label text field.
+ */
+function TKR_validateLabel(textField) {
+  if (textField == undefined) return;
+  TKR_confirmNovelLabel(textField);
+  TKR_updateUsedPrefixes(textField);
+  TKR_highlightExclusiveLabelPrefixConflicts();
+  TKR_highlightQuestionMarks(textField);
+}
+
+// TODO(jrobbins): what about typos in owner and cc list?
+
+/**
+ * If there are any novel status or label values, we display a message
+ * that explains that to the user so that they can catch any typos before
+ * submitting them.  If the project is restricting input to only the
+ * well-known statuses and labels, then show these as an error instead.
+ * In that case, on-page JS will prevent submission.
+ */
+function TKR_updateConfirmBeforeSubmit() {
+  let severity = TKR_restrict_to_known ? 'Error' : 'Note';
+  let novelWord = TKR_restrict_to_known ? 'undefined' : 'uncommon';
+  let msg = '';
+  let labels = TKR_novelLabels.map(function(item) {
+    return item.value;
+  });
+  if (TKR_novelStatuses.length > 0 && TKR_novelLabels.length > 0) {
+    msg = severity + ': You are using an ' + novelWord + ' status and ' + novelWord + ' label(s): ' + labels.join(', ') + '.'; // TODO: i18n
+  } else if (TKR_novelStatuses.length > 0) {
+    msg = severity + ': You are using an ' + novelWord + ' status value.';
+  } else if (TKR_novelLabels.length > 0) {
+    msg = severity + ': You are using ' + novelWord + ' label(s): ' + labels.join(', ') + '.';
+  }
+
+  for (var i = 0; i < TKR_labelsWithReservedPrefixes.length; ++i) {
+    msg += '\nNote: The label ' + TKR_labelsWithReservedPrefixes[i].value +
+           ' starts with a reserved word. This is not recommended.';
+  }
+  for (var i = 0; i < TKR_labelsConflictingWithReserved.length; ++i) {
+    msg += '\nNote: The label ' + TKR_labelsConflictingWithReserved[i].value +
+           ' conflicts with a reserved word. This is not recommended.';
+  }
+  // Display the owner is no longer a member note only if an owner error is not
+  // already shown on the page.
+  if (TKR_invalidOwner && !$('ownererror')) {
+    msg += '\nNote: Current owner is no longer a project member.';
+  }
+
+  let confirm_area = $(TKR_CONFIRMAREA_ID);
+  if (confirm_area) {
+    $('confirmmsg').textContent = msg;
+    if (msg != '') {
+      confirm_area.className = TKR_NOVEL_CLASS;
+      confirm_area.style.display = '';
+    } else {
+      confirm_area.style.display = 'none';
+    }
+  }
+}
+
+
+/**
+ * The user has selected a command from the 'Actions...' menu
+ * on the issue list.  This function checks the selected value and carry
+ * out the requested action.
+ * @param {Element} actionsMenu The 'Actions...' <select> form element.
+ */
+function TKR_handleListActions(actionsMenu) {
+  switch (actionsMenu.value) {
+    case 'bulk':
+      TKR_HandleBulkEdit();
+      break;
+    case 'colspec':
+      TKR_closeAllPopups(actionsMenu);
+      _showID('columnspec');
+      _hideID('addissuesspec');
+      break;
+    case 'flagspam':
+      TKR_flagSpam(true);
+      break;
+    case 'unflagspam':
+      TKR_flagSpam(false);
+      break;
+    case 'addtohotlist':
+      TKR_addToHotlist();
+      break;
+    case 'addissues':
+      _showID('addissuesspec');
+      _hideID('columnspec');
+      setCurrentColSpec();
+      break;
+    case 'removeissues':
+      HTL_removeIssues();
+      break;
+    case 'issuesperpage':
+      break;
+  }
+  actionsMenu.value = 'moreactions';
+}
+
+
+async function TKR_handleDetailActions(localId) {
+  let moreActions = $('more_actions');
+
+  if (moreActions.value == 'delete') {
+    $('copy_issue_form_fragment').style.display = 'none';
+    $('move_issue_form_fragment').style.display = 'none';
+    let ok = confirm(
+        'Normally, you should just close issues by setting their status ' +
+      'to a closed value.\n' +
+      'Are you sure you want to delete this issue?');
+    if (ok) {
+      await window.prpcClient.call('monorail.Issues', 'DeleteIssue', {
+        issueRef: {
+          projectName: window.CS_env.projectName,
+          localId: localId,
+        },
+        delete: true,
+      });
+      location.reload(true);
+      return;
+    }
+  }
+
+  if (moreActions.value == 'move') {
+    $('move_issue_form_fragment').style.display = '';
+    $('copy_issue_form_fragment').style.display = 'none';
+    return;
+  }
+  if (moreActions.value == 'copy') {
+    $('copy_issue_form_fragment').style.display = '';
+    $('move_issue_form_fragment').style.display = 'none';
+    return;
+  }
+
+  // If no action was taken, reset the dropdown to the 'More actions...' item.
+  moreActions.value = '0';
+}
+
+/**
+ * The user has selected the "Flag as spam..." menu item.
+ */
+async function TKR_flagSpam(isSpam) {
+  const selectedIssueRefs = [];
+  issueRefs.forEach((issueRef) => {
+    const checkbox = $('cb_' + issueRef.id);
+    if (checkbox && checkbox.checked) {
+      selectedIssueRefs.push({
+        projectName: issueRef.project_name,
+        localId: issueRef.id,
+      });
+    }
+  });
+  if (selectedIssueRefs.length > 0) {
+    if (!confirm((isSpam ? 'Flag' : 'Un-flag') +
+        ' all selected issues as spam?')) {
+      return;
+    }
+    await window.prpcClient.call('monorail.Issues', 'FlagIssues', {
+      issueRefs: selectedIssueRefs,
+      flag: isSpam,
+    });
+    location.reload(true);
+  } else {
+    alert('Please select some issues to flag as spam');
+  }
+}
+
+function TKR_addToHotlist() {
+  const selectedIssueRefs = GetSelectedIssuesRefs();
+  if (selectedIssueRefs.length > 0) {
+    window.__hotlists_dialog.ShowUpdateHotlistDialog();
+  } else {
+    alert('Please select some issues to add to a hotlist');
+  }
+}
+
+
+function GetSelectedIssuesRefs() {
+  let selectedIssueRefs = [];
+  for (let i = 0; i < issueRefs.length; i++) {
+    let checkbox = document.getElementById('cb_' + issueRefs[i]['id']);
+    if (checkbox == null) {
+      checkbox = document.getElementById(
+          'cb_' + issueRefs[i]['project_name'] + ':' + issueRefs[i]['id']);
+    }
+    if (checkbox && checkbox.checked) {
+      selectedIssueRefs.push(issueRefs[i]);
+    }
+  }
+  return selectedIssueRefs;
+}
+
+function onResponseUpdateUI(modifiedHotlists, remainingHotlists) {
+  const list = $('user-hotlists-list');
+  while (list.firstChild) {
+    list.removeChild(list.firstChild);
+  }
+  remainingHotlists.forEach((hotlist) => {
+    const name = hotlist[0];
+    const userId = hotlist[1];
+    const url = `/u/${userId}/hotlists/${name}`;
+    const hotlistLink = document.createElement('a');
+    hotlistLink.setAttribute('href', url);
+    hotlistLink.textContent = name;
+    list.appendChild(hotlistLink);
+    list.appendChild(document.createElement('br'));
+  });
+  $('user-hotlists').style.display = 'block';
+  onAddIssuesResponse(modifiedHotlists);
+}
+
+function onAddIssuesResponse(modifiedHotlists) {
+  const hotlistNames = modifiedHotlists.map((hotlist) => hotlist[0]).join(', ');
+  $('notice').textContent = 'Successfully updated ' + hotlistNames;
+  $('update-issues-hotlists').style.display = 'none';
+  $('alert-table').style.display = 'table';
+}
+
+function onAddIssuesFailure(reason) {
+  $('notice').textContent =
+      'Some hotlists were not updated: ' + reason.description;
+  $('update-issues-hotlists').style.display = 'none';
+  $('alert-table').style.display = 'table';
+}
+
+/**
+ * The user has selected the "Bulk Edit..." menu item.  Go to a page that
+ * offers the ability to edit all selected issues.
+ */
+// TODO(jrobbins): cross-project bulk edit
+function TKR_HandleBulkEdit() {
+  let selectedIssueRefs = GetSelectedIssuesRefs();
+  let selectedLocalIDs = [];
+  for (let i = 0; i < selectedIssueRefs.length; i++) {
+    selectedLocalIDs.push(selectedIssueRefs[i]['id']);
+  }
+  if (selectedLocalIDs.length > 0) {
+    let selectedLocalIDString = selectedLocalIDs.join(',');
+    let url = 'bulkedit?ids=' + selectedLocalIDString;
+    TKR_go(url + _ctxArgs);
+  } else {
+    alert('Please select some issues to edit');
+  }
+}
+
+/**
+ * Clears the selected status value when the 'clear' operator is chosen.
+ */
+function TKR_ignoreWidgetIfOpIsClear(selectEl, inputID) {
+  if (selectEl.value == 'clear') {
+    document.getElementById(inputID).value = '';
+  }
+}
+
+/**
+ * Array of original labels on the served page, so that we can notice
+ * when the used submits a form that has any Restrict-* labels removed.
+ */
+let TKR_allOrigLabels = [];
+
+
+/**
+ * Prevent users from easily entering "+1" comments.
+ */
+function TKR_checkPlusOne() {
+  let c = $('addCommentTextArea').value;
+  let instructions = (
+    '\nPlease use the star icon instead.\n' +
+      'Stars show your interest without annoying other users.');
+  if (new RegExp('^\\s*[-+]+[0-9]+\\s*.{0,30}$', 'm').test(c) &&
+      c.length < 150) {
+    alert('This looks like a "+1" comment.' + instructions);
+    return false;
+  }
+  if (new RegExp('^\\s*me too.{0,30}$', 'i').test(c)) {
+    alert('This looks like a "me too" comment.' + instructions);
+    return false;
+  }
+  return true;
+}
+
+
+/**
+ * If the user removes Restrict-* labels, ask them if they are sure.
+ */
+function TKR_checkUnrestrict(prevent_restriction_removal) {
+  let removedRestrictions = [];
+
+  for (let i = 0; i < TKR_allOrigLabels.length; ++i) {
+    let origLabel = TKR_allOrigLabels[i];
+    if (origLabel.indexOf('Restrict-') == 0) {
+      let found = false;
+      let j = 0;
+      while ($('label' + j)) {
+        let newLabel = $('label' + j).value;
+        if (newLabel == origLabel) {
+          found = true;
+          break;
+        }
+        j++;
+      }
+      if (!found) {
+        removedRestrictions.push(origLabel);
+      }
+    }
+  }
+
+  if (removedRestrictions.length == 0) {
+    return true;
+  }
+
+  if (prevent_restriction_removal) {
+    let msg = 'You may not remove restriction labels.';
+    alert(msg);
+    return false;
+  }
+
+  let instructions = (
+    'You are removing these restrictions:\n   ' +
+      removedRestrictions.join('\n   ') +
+      '\nThis may allow more people to access this issue.' +
+      '\nAre you sure?');
+  return confirm(instructions);
+}
+
+
+/**
+ * Add a column to a list view by updating the colspec form element and
+ * submiting an invisible <form> to load a new page that includes the column.
+ * @param {string} colname The name of the column to start showing.
+ */
+function TKR_addColumn(colname) {
+  let colspec = TKR_getColspecElement();
+  colspec.value = colspec.value + ' ' + colname;
+  $('colspecform').submit();
+}
+
+
+/**
+ * Allow members to shift-click to select multiple issues.  This keeps
+ * track of the last row that the user clicked a checkbox on.
+ */
+let TKR_lastSelectedRow = undefined;
+
+
+/**
+ * Return true if an event had the shift-key pressed.
+ * @param {Event} evt The mouse click event.
+ */
+function TKR_hasShiftKey(evt) {
+  evt = (evt) ? evt : (window.event) ? window.event : '';
+  if (evt) {
+    if (evt.modifiers) {
+      return evt.modifiers & Event.SHIFT_MASK;
+    } else {
+      return evt.shiftKey;
+    }
+  }
+  return false;
+}
+
+
+/**
+ * Select one row: check the checkbox and use highlight color.
+ * @param {Element} row the row containing the checkbox that the user clicked.
+ * @param {boolean} checked True if the user checked the box.
+ */
+function TKR_rangeSelectRow(row, checked) {
+  if (!row) {
+    return;
+  }
+  if (checked) {
+    row.classList.add('selected');
+  } else {
+    row.classList.remove('selected');
+  }
+
+  let td = row.firstChild;
+  while (td && td.tagName != 'TD') {
+    td = td.nextSibling;
+  }
+  if (!td) {
+    return;
+  }
+
+  let checkbox = td.firstChild;
+  while (checkbox && checkbox.tagName != 'INPUT') {
+    checkbox = checkbox.nextSibling;
+  }
+  if (!checkbox) {
+    return;
+  }
+
+  checkbox.checked = checked;
+}
+
+
+/**
+ * If the user shift-clicked a checkbox, (un)select a range.
+ * @param {Event} evt The mouse click event.
+ * @param {Element} el The checkbox that was clicked.
+ */
+function TKR_checkRangeSelect(evt, el) {
+  let clicked_row = el.parentNode.parentNode.rowIndex;
+  if (clicked_row == TKR_lastSelectedRow) {
+    return;
+  }
+  if (TKR_hasShiftKey(evt) && TKR_lastSelectedRow != undefined) {
+    let results_table = $('resultstable');
+    let delta = (clicked_row > TKR_lastSelectedRow) ? 1 : -1;
+    for (let i = TKR_lastSelectedRow; i != clicked_row; i += delta) {
+      TKR_rangeSelectRow(results_table.rows[i], el.checked);
+    }
+  }
+  TKR_lastSelectedRow = clicked_row;
+}
+
+
+/**
+ * Make a link to a given issue that includes context parameters that allow
+ * the user to see the same list columns, sorting, query, and pagination state
+ * if they ever navigate up to the list again.
+ * @param {{issue_url: string}} issueRef The dict with info about an issue,
+ *     including a url to the issue detail page.
+ */
+function TKR_makeIssueLink(issueRef) {
+  return '/p/' + issueRef['project_name'] + '/issues/detail?id=' + issueRef['id'] + _ctxArgs;
+}
+
+
+/**
+ * Hide or show a list column in the case where we already have the
+ * data for that column on the page.
+ * @param {number} colIndex index of the column that is being shown or hidden.
+ */
+function TKR_toggleColumnUpdate(colIndex) {
+  let shownCols = TKR_getColspecElement().value.split(' ');
+  let filteredCols = [];
+  for (let i=0; i< shownCols.length; i++) {
+    if (_allColumnNames[colIndex] != shownCols[i].toLowerCase()) {
+      filteredCols.push(shownCols[i]);
+    }
+  }
+
+  TKR_getColspecElement().value = filteredCols.join(' ');
+  TKR_toggleColumn('hide_col_' + colIndex);
+  _ctxArgs = _formatContextQueryArgs();
+  window.history.replaceState({}, '', '?' + _ctxArgs);
+}
+
+
+/**
+ * Convert a column into a groupby clause by removing it from the column spec
+ * and adding it to the groupby spec, then reloading the page.
+ * @param {number} colIndex index of the column that is being shown or hidden.
+ */
+function TKR_addGroupBy(colIndex) {
+  let colName = _allColumnNames[colIndex];
+  let shownCols = TKR_getColspecElement().value.split(' ');
+  let filteredCols = [];
+  for (var i=0; i < shownCols.length; i++) {
+    if (shownCols[i] && colName != shownCols[i].toLowerCase()) {
+      filteredCols.push(shownCols[i]);
+    }
+  }
+
+  TKR_getColspecElement().value = filteredCols.join(' ');
+
+  let groupSpec = $('groupbyspec');
+  let shownGroupings = groupSpec.value.split(' ');
+  let filteredGroupings = [];
+  for (i=0; i < shownGroupings.length; i++) {
+    if (shownGroupings[i] && colName != shownGroupings[i].toLowerCase()) {
+      filteredGroupings.push(shownGroupings[i]);
+    }
+  }
+  filteredGroupings.push(colName);
+  groupSpec.value = filteredGroupings.join(' ');
+  $('colspecform').submit();
+}
+
+
+/**
+ * Add a multi-valued custom field editing widget.
+ */
+function TKR_addMultiFieldValueWidget(
+    el, field_id, field_type, opt_validate_1, opt_validate_2, field_phase_name) {
+  let widget = document.createElement('INPUT');
+  widget.name = (field_phase_name && (
+    field_phase_name != '')) ? `custom_${field_id}_${field_phase_name}` :
+    `custom_${field_id}`;
+  if (field_type == 'str' || field_type =='url') {
+    widget.size = 90;
+  }
+  if (field_type == 'user') {
+    widget.style = 'width:12em';
+    widget.classList.add('userautocomplete');
+    widget.classList.add('customfield');
+    widget.classList.add('multivalued');
+    widget.addEventListener('focus', function(event) {
+      _acrob(null);
+      _acof(event);
+    });
+  }
+  if (field_type == 'int' || field_type == 'date') {
+    widget.style.textAlign = 'right';
+    widget.style.width = '12em';
+    widget.min = opt_validate_1;
+    widget.max = opt_validate_2;
+  }
+  if (field_type == 'int') {
+    widget.type = 'number';
+  } else if (field_type == 'date') {
+    widget.type = 'date';
+  }
+
+  el.parentNode.insertBefore(widget, el);
+
+  let del_button = document.createElement('U');
+  del_button.onclick = function(event) {
+    _removeMultiFieldValueWidget(event.target);
+  };
+  del_button.textContent = 'X';
+  el.parentNode.insertBefore(del_button, el);
+}
+
+
+function TKR_removeMultiFieldValueWidget(el) {
+  let target = el.previousSibling;
+  while (target && target.tagName != 'INPUT') {
+    target = target.previousSibling;
+  }
+  if (target) {
+    el.parentNode.removeChild(target);
+  }
+  el.parentNode.removeChild(el); // the X itself
+}
+
+
+/**
+ * Trim trailing commas and spaces off <INPUT type="email" multiple> fields
+ * before submitting the form.
+ */
+function TKR_trimCommas() {
+  let ccField = $('memberccedit');
+  if (ccField) {
+    ccField.value = ccField.value.replace(/,\s*$/, '');
+  }
+  ccField = $('memberenter');
+  if (ccField) {
+    ccField.value = ccField.value.replace(/,\s*$/, '');
+  }
+}
+
+
+/**
+ * Identify which issues have been checkedboxed for removal from hotlist.
+ */
+function HTL_removeIssues() {
+  let selectedLocalIDs = [];
+  for (let i = 0; i < issueRefs.length; i++) {
+    issueRef = issueRefs[i]['project_name']+':'+issueRefs[i]['id'];
+    let checkbox = document.getElementById('cb_' + issueRef);
+    if (checkbox && checkbox.checked) {
+      selectedLocalIDs.push(issueRef);
+    }
+  }
+
+  if (selectedLocalIDs.length > 0) {
+    if (!confirm('Remove all selected issues?')) {
+      return;
+    }
+    let selectedLocalIDString = selectedLocalIDs.join(',');
+    $('bulk_remove_local_ids').value = selectedLocalIDString;
+    $('bulk_remove_value').value = 'true';
+    setCurrentColSpec();
+
+    let form = $('bulkremoveissues');
+    form.submit();
+  } else {
+    alert('Please select some issues to remove');
+  }
+}
+
+function setCurrentColSpec() {
+  $('current_col_spec').value = TKR_getColspecElement().value;
+}
+
+
+async function saveNote(textBox, hotlistID) {
+  const projectName = textBox.getAttribute('projectname');
+  const localId = textBox.getAttribute('localid');
+  await window.prpcClient.call(
+      'monorail.Features', 'UpdateHotlistIssueNote', {
+        hotlistRef: {
+          hotlistId: hotlistID,
+        },
+        issueRef: {
+          projectName: textBox.getAttribute('projectname'),
+          localId: textBox.getAttribute('localid'),
+        },
+        note: textBox.value,
+      });
+  $(`itemnote_${projectName}_${localId}`).value = textBox.value;
+}
+
+// TODO(jojwang): monorail:4291, integrate this into autocomplete process
+// to prevent calling ListStatuses twice.
+/**
+ * Load the status select element with possible project statuses.
+ */
+function TKR_loadStatusSelect(projectName, selectId, selected, isBulkEdit=false) {
+  const projectRequestMessage = {
+    project_name: projectName};
+  const statusesPromise = window.prpcClient.call(
+      'monorail.Projects', 'ListStatuses', projectRequestMessage);
+  statusesPromise.then((statusesResponse) => {
+    const jsonData = TKR_convertStatuses(statusesResponse);
+    const statusSelect = document.getElementById(selectId);
+    // An initial option with value='selected' had to be added in HTML
+    // to prevent TKR_isDirty() from registering a change in the select input
+    // even when the user has not selected a different value.
+    // That option needs to be removed otherwise, screenreaders will announce
+    // its existence.
+    while (statusSelect.firstChild) {
+      statusSelect.removeChild(statusSelect.firstChild);
+    }
+    // Add unrecognized status (can be empty status) to open statuses.
+    let selectedFound = false;
+    jsonData.open.concat(jsonData.closed).forEach((status) => {
+      if (status.name === selected) {
+        selectedFound = true;
+      }
+    });
+    if (!selectedFound) {
+      jsonData.open.unshift({name: selected});
+    }
+    // Add open statuses.
+    if (jsonData.open.length > 0) {
+      const openGroup =
+          statusSelect.appendChild(createStatusGroup('Open', jsonData.open, selected, isBulkEdit));
+    }
+    if (jsonData.closed.length > 0) {
+      statusSelect.appendChild(createStatusGroup('Closed', jsonData.closed, selected));
+    }
+  });
+}
+
+function createStatusGroup(groupName, options, selected, isBulkEdit=false) {
+  const groupElement = document.createElement('optgroup');
+  groupElement.label = groupName;
+  options.forEach((option) => {
+    const opt = document.createElement('option');
+    opt.value = option.name;
+    opt.selected = (selected === option.name) ? true : false;
+    // Special case for when opt represents an empty status.
+    if (opt.value === '') {
+      if (isBulkEdit) {
+        opt.textContent = '--- (no change)';
+        opt.setAttribute('aria-label', 'no change');
+      } else {
+        opt.textContent = '--- (empty status)';
+        opt.setAttribute('aria-label', 'empty status');
+      }
+    } else {
+      opt.textContent = option.doc ? `${option.name} = ${option.doc}` : option.name;
+    }
+    groupElement.appendChild(opt);
+  });
+  return groupElement;
+}
+
+/**
+ * Generate DOM for a filter rules preview section.
+ */
+function renderFilterRulesSection(section_id, heading, value_why_list) {
+  let section = $(section_id);
+  while (section.firstChild) {
+    section.removeChild(section.firstChild);
+  }
+  if (value_why_list.length == 0) return false;
+
+  section.appendChild(document.createTextNode(heading + ': '));
+  for (let i = 0; i < value_why_list.length; ++i) {
+    if (i > 0) {
+      section.appendChild(document.createTextNode(', '));
+    }
+    let value = value_why_list[i].value;
+    let why = value_why_list[i].why;
+    let span = section.appendChild(
+        document.createElement('span'));
+    span.textContent = value;
+    if (why) span.setAttribute('title', why);
+  }
+  return true;
+}
+
+
+/**
+ * Generate DOM for a filter rules preview section bullet list.
+ */
+function renderFilterRulesListSection(section_id, heading, value_why_list) {
+  let section = $(section_id);
+  while (section.firstChild) {
+    section.removeChild(section.firstChild);
+  }
+  if (value_why_list.length == 0) return false;
+
+  section.appendChild(document.createTextNode(heading + ': '));
+  let bulletList = document.createElement('ul');
+  section.appendChild(bulletList);
+  for (let i = 0; i < value_why_list.length; ++i) {
+    let listItem = document.createElement('li');
+    bulletList.appendChild(listItem);
+    let value = value_why_list[i].value;
+    let why = value_why_list[i].why;
+    let span = listItem.appendChild(
+        document.createElement('span'));
+    span.textContent = value;
+    if (why) span.setAttribute('title', why);
+  }
+  return true;
+}
+
+
+/**
+ * Ask server to do a presubmit check and then display and warnings
+ * as the user edits an issue.
+ */
+function TKR_presubmit() {
+  const issue_form = (
+    document.forms.create_issue_form || document.forms.issue_update_form);
+  if (!issue_form) {
+    return;
+  }
+
+  const inputs = issue_form.querySelectorAll(
+      'input:not([type="file"]), textarea, select');
+  if (!inputs) {
+    return;
+  }
+
+  const valuesByName = new Map();
+  for (const key in inputs) {
+    if (!inputs.hasOwnProperty(key)) {
+      continue;
+    }
+    const input = inputs[key];
+    if (input.type === 'checkbox' && !input.checked) {
+      continue;
+    }
+    if (!valuesByName.has(input.name)) {
+      valuesByName.set(input.name, []);
+    }
+    valuesByName.get(input.name).push(input.value);
+  }
+
+  const issueDelta = TKR_buildIssueDelta(valuesByName);
+  const issueRef = {project_name: window.CS_env.projectName};
+  if (valuesByName.has('id')) {
+    issueRef.local_id = valuesByName.get('id')[0];
+  }
+
+  const presubmitMessage = {
+    issue_ref: issueRef,
+    issue_delta: issueDelta,
+  };
+  const presubmitPromise = window.prpcClient.call(
+      'monorail.Issues', 'PresubmitIssue', presubmitMessage);
+
+  presubmitPromise.then((response) => {
+    $('owner_avail_state').style.display = (
+      response.ownerAvailabilityState ? '' : 'none');
+    $('owner_avail_state').className = (
+      'availability_' + response.ownerAvailabilityState);
+    $('owner_availability').textContent = response.ownerAvailability;
+
+    let derived_labels;
+    if (response.derivedLabels) {
+      derived_labels = renderFilterRulesSection(
+          'preview_filterrules_labels', 'Labels', response.derivedLabels);
+    }
+    let derived_owner_email;
+    if (response.derivedOwners) {
+      derived_owner_email = renderFilterRulesSection(
+          'preview_filterrules_owner', 'Owner', response.derivedOwners[0]);
+    }
+    let derived_cc_emails;
+    if (response.derivedCcs) {
+      derived_cc_emails = renderFilterRulesSection(
+          'preview_filterrules_ccs', 'Cc', response.derivedCcs);
+    }
+    let warnings;
+    if (response.warnings) {
+      warnings = renderFilterRulesListSection(
+          'preview_filterrules_warnings', 'Warnings', response.warnings);
+    }
+    let errors;
+    if (response.errors) {
+      errors = renderFilterRulesListSection(
+          'preview_filterrules_errors', 'Errors', response.errors);
+    }
+
+    if (derived_labels || derived_owner_email || derived_cc_emails ||
+        warnings || errors) {
+      $('preview_filterrules_area').style.display = '';
+    } else {
+      $('preview_filterrules_area').style.display = 'none';
+    }
+  });
+}
+
+function HTL_deleteHotlist(form) {
+  if (confirm('Are you sure you want to delete this hotlist? This cannot be undone.')) {
+    $('delete').value = 'true';
+    form.submit();
+  }
+}
+
+function HTL_toggleIssuesShown(toggleIssuesButton) {
+  const can = toggleIssuesButton.value;
+  const hotlist_name = $('hotlist_name').value;
+  let url = `${hotlist_name}?can=${can}`;
+  const hidden_cols = $('colcontrol').classList.value;
+  if (window.location.href.includes('&colspec') || hidden_cols) {
+    const colSpecElement =
+        TKR_getColspecElement(); // eslint-disable-line new-cap
+    let sort = '';
+    if ($('sort')) {
+      sort = $('sort').value.split(' ').join('+');
+      url += `&sort=${sort}`;
+    }
+    url += colSpecElement ? `&colspec=${colSpecElement.value}` : '';
+  }
+  TKR_go(url);
+}
diff --git a/static/js/tracker/tracker-fields.js b/static/js/tracker/tracker-fields.js
new file mode 100644
index 0000000..d84f11d
--- /dev/null
+++ b/static/js/tracker/tracker-fields.js
@@ -0,0 +1,75 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+/**
+ * This file contains JS code for editing fields and field definitions.
+ */
+
+var TKR_fieldNameXmlHttp;
+
+
+/**
+ * Function that communicates with the server.
+ * @param {string} projectName Current project name.
+ * @param {string} fieldName The proposed field name.
+ */
+async function TKR_checkFieldNameOnServer(projectName, fieldName) {
+  fieldName = fieldName.toLowerCase();
+
+  const fieldNameMessage = {
+    project_name: projectName,
+    field_name: fieldName,
+  };
+  const labelOptionsMessage = {
+    project_name: projectName,
+  };
+  const responses = await Promise.all([
+      window.prpcClient.call(
+          'monorail.Projects', 'CheckFieldName', fieldNameMessage),
+      window.prpcClient.call(
+          'monorail.Projects', 'GetLabelOptions', labelOptionsMessage),
+  ]);
+
+  const fieldNameResponse = responses[0];
+  const labelsResponse = responses[1];
+
+  $('fieldnamefeedback').textContent = fieldNameResponse.error || '';
+  $('submit_btn').disabled = fieldNameResponse.error ? 'disabled' : '';
+
+  const maskedLabels = (labelsResponse.labelOptions || []).filter(
+      label_def => label_def.label.toLowerCase().startsWith(fieldName + '-'));
+
+  if (maskedLabels.length === 0) {
+    enableOtherTypeOptions(false);
+  } else {
+    const prefixLength = fieldName.length + 1;
+    const padLength = Math.max.apply(null, maskedLabels.map(
+        label_def => label_def.label.length - prefixLength));
+    const choicesLines = maskedLabels.map(label_def => {
+      // Strip the field name from the label.
+      const choice = label_def.label.substr(prefixLength);
+      return choice.padEnd(padLength) + ' = ' + label_def.docstring;
+    });
+    $('choices').textContent = choicesLines.join('\n');
+    $('field_type').value = 'enum_type';
+    $('choices_row').style.display = '';
+    enableOtherTypeOptions(true);
+  }
+}
+
+
+function enableOtherTypeOptions(disabled) {
+  let type_option_el = $('field_type').firstChild;
+  while (type_option_el) {
+    if (type_option_el.tagName == 'OPTION') {
+      if (type_option_el.value != 'enum_type') {
+        type_option_el.disabled = disabled ? 'disabled' : '';
+      }
+    }
+    type_option_el = type_option_el.nextSibling;
+  }
+}
diff --git a/static/js/tracker/tracker-install-ac.js b/static/js/tracker/tracker-install-ac.js
new file mode 100644
index 0000000..2fe1dcd
--- /dev/null
+++ b/static/js/tracker/tracker-install-ac.js
@@ -0,0 +1,53 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+/* eslint-disable camelcase */
+/* eslint-disable no-unused-vars */
+
+/**
+  * Sets up the legacy autocomplete editing widget on DOM elements that are
+  * set to use it.
+  */
+function TKR_install_ac() {
+  _ac_install();
+
+  _ac_register(function(input, event) {
+    if (input.id.startsWith('hotlists')) return TKR_hotlistsStore;
+    if (input.id.startsWith('search')) return TKR_searchStore;
+    if (input.id.startsWith('query_') || input.id.startsWith('predicate_')) {
+      return TKR_projectQueryStore;
+    }
+    if (input.id.startsWith('cmd')) return TKR_quickEditStore;
+    if (input.id.startsWith('labelPrefix')) return TKR_labelPrefixStore;
+    if (input.id.startsWith('label') && input.id != 'labelsInput') return TKR_labelStore;
+    if (input.dataset.acType === 'label' && input.id != 'labelsInput') return TKR_labelMultiStore;
+    if ((input.id.startsWith('component') || input.dataset.acType === 'component')
+      && input.id != 'componentsInput') return TKR_componentListStore;
+    if (input.id.startsWith('status')) return TKR_statusStore;
+    if (input.id.startsWith('member') || input.dataset.acType === 'member') return TKR_memberListStore;
+
+    if (input.id == 'admin_names_editor') return TKR_memberListStore;
+    if (input.id.startsWith('owner') && input.id != 'ownerInput') return TKR_ownerStore;
+    if (input.name == 'needs_perm' || input.name == 'grants_perm') {
+      return TKR_customPermissionsStore;
+    }
+    if (input.id == 'owner_editor' || input.dataset.acType === 'owner') return TKR_ownerStore;
+    if (input.className.indexOf('userautocomplete') != -1) {
+      const customFieldIDStr = input.name;
+      const uac = TKR_userAutocompleteStores[customFieldIDStr];
+      if (uac) return uac;
+      return TKR_ownerStore;
+    }
+    if (input.className.indexOf('autocomplete') != -1) {
+      return TKR_autoCompleteStore;
+    }
+    if (input.id.startsWith('copy_to') || input.id.startsWith('move_to') ||
+       input.id.startsWith('new_savedquery_projects') ||
+       input.id.startsWith('savedquery_projects')) {
+      return TKR_projectStore;
+    }
+  });
+};
diff --git a/static/js/tracker/tracker-keystrokes.js b/static/js/tracker/tracker-keystrokes.js
new file mode 100644
index 0000000..9a75971
--- /dev/null
+++ b/static/js/tracker/tracker-keystrokes.js
@@ -0,0 +1,232 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+/**
+ * This file contains JS functions that implement keystroke accelerators
+ * for Monorail.
+ */
+
+/**
+ * Array of HTML elements where the kibbles cursor can be.  E.g.,
+ * the TR elements of an issue list, or the TR's for comments on an issue.
+ */
+let TKR_cursorStops;
+
+/**
+ * Integer index into TKR_cursorStops of the currently selected cursor
+ * stop, or undefined if nothing has been selected yet.
+ */
+let TKR_selected = undefined;
+
+/**
+ * Register keystrokes that apply to all pages in the current component.
+ * E.g., keystrokes that should work on every page under the "Issues" tab.
+ * @param {string} listUrl Rooted URL of the artifact list.
+ * @param {string} entryUrl Rooted URL of the artifact entry page.
+ * @param {string} currentPageType One of 'list', 'entry', or 'detail'.
+ */
+function TKR_setupKibblesComponentKeys(listUrl, entryUrl, currentPageType) {
+  if (currentPageType != 'list') {
+    kibbles.keys.addKeyPressListener(
+        'u', function() {
+          TKR_go(listUrl);
+        });
+  }
+}
+
+
+/**
+ * On the artifact list page, go to the artifact at the kibbles cursor.
+ * @param {number} linkCellIndex row child that is expected to hold a link.
+ */
+function TKR_openArtifactAtCursor(linkCellIndex, newWindow) {
+  if (TKR_selected >= 0 && TKR_selected < TKR_cursorStops.length) {
+    window._goIssue(TKR_selected, newWindow);
+  }
+}
+
+
+/**
+ * On the artifact list page, toggle the checkbox for the artifact at
+ * the kibbles cursor.
+ * @param {number} cbCellIndex row child that is expected to hold a checkbox.
+ */
+function TKR_selectArtifactAtCursor(cbCellIndex) {
+  if (TKR_selected >= 0 && TKR_selected < TKR_cursorStops.length) {
+    const cell = TKR_cursorStops[TKR_selected].children[cbCellIndex];
+    let cb = cell.firstChild;
+    while (cb && cb.tagName != 'INPUT') {
+      cb = cb.nextSibling;
+    }
+    if (cb) {
+      cb.checked = cb.checked ? '' : 'checked';
+      TKR_highlightRow(cb);
+    }
+  }
+}
+
+/**
+ * On the artifact list page, toggle the star for the artifact at
+ * the kibbles cursor.
+ * @param {number} cbCellIndex row child that is expected to hold a checkbox
+ *     and star widget.
+ */
+function TKR_toggleStarArtifactAtCursor(cbCellIndex) {
+  if (TKR_selected >= 0 && TKR_selected < TKR_cursorStops.length) {
+    const cell = TKR_cursorStops[TKR_selected].children[cbCellIndex];
+    let starIcon = cell.firstChild;
+    while (starIcon && starIcon.tagName != 'A') {
+      starIcon = starIcon.nextSibling;
+    }
+    if (starIcon) {
+      _TKR_toggleStar(
+          starIcon, issueRefs[TKR_selected]['project_name'],
+          issueRefs[TKR_selected]['id'], null, null);
+    }
+  }
+}
+
+/**
+ * Updates the style on new stop and clears the style on the former stop.
+ * @param {Object} newStop the cursor stop that the user is selecting now.
+ * @param {Object} formerStop the old cursor stop, if any.
+ */
+function TKR_updateCursor(newStop, formerStop) {
+  TKR_selected = undefined;
+  if (formerStop) {
+    formerStop.element.classList.remove('cursor_on');
+    formerStop.element.classList.add('cursor_off');
+  }
+  if (newStop && newStop.element) {
+    newStop.element.classList.remove('cursor_off');
+    newStop.element.classList.add('cursor_on');
+    TKR_selected = newStop.index;
+  }
+}
+
+
+/**
+ * Walk part of the page DOM to find elements that should be kibbles
+ * cursor stops.  E.g., the rows of the issue list results table.
+ * @return {Array} an array of html elements.
+ */
+function TKR_findCursorRows() {
+  const rows = [];
+  const cursorarea = document.getElementById('cursorarea');
+  TKR_accumulateCursorRows(cursorarea, rows);
+  return rows;
+}
+
+
+/**
+ * Recusrively walk part of the page DOM to find elements that should
+ * be kibbles cursor stops.  E.g., the rows of the issue list results
+ * table.  The cursor stops are appended to the given rows array.
+ * @param {Element} parent html element to start on.
+ * @param {Array} rows  array of html TR or DIV elements, each cursor stop will
+ *    be added to this array.
+ */
+function TKR_accumulateCursorRows(parent, rows) {
+  for (let i = 0; i < parent.childNodes.length; i++) {
+    const elem = parent.childNodes[i];
+    const name = elem.tagName;
+    if (name && (name == 'TR' || name == 'DIV')) {
+      if (elem.className.indexOf('cursor') >= 0) {
+        elem.cursorIndex = rows.length;
+        rows.push(elem);
+      }
+    }
+    TKR_accumulateCursorRows(elem, rows);
+  }
+}
+
+
+/**
+ * Initialize kibbles cursors stops for the current page.
+ * @param {boolean} selectFirstStop True if the first stop should be
+ *   selected before the user presses any keys.
+ */
+function TKR_setupKibblesCursorStops(selectFirstStop) {
+  kibbles.skipper.addStopListener(
+      kibbles.skipper.LISTENER_TYPE.PRE, TKR_updateCursor);
+
+  // Set the 'offset' option to return the middle of the client area
+  // an option can be a static value, or a callback
+  kibbles.skipper.setOption('padding_top', 50);
+
+  // Set the 'offset' option to return the middle of the client area
+  // an option can be a static value, or a callback
+  kibbles.skipper.setOption('padding_bottom', 50);
+
+  // register our stops with skipper
+  TKR_cursorStops = TKR_findCursorRows();
+  for (let i = 0; i < TKR_cursorStops.length; i++) {
+    const element = TKR_cursorStops[i];
+    kibbles.skipper.append(element);
+
+    if (element.className.indexOf('cursor_on') >= 0) {
+      kibbles.skipper.setCurrentStop(i);
+    }
+  }
+}
+
+
+/**
+ * Initialize kibbles keystrokes for an artifact entry page.
+ * @param {string} listUrl Rooted URL of the artifact list.
+ * @param {string} entryUrl Rooted URL of the artifact entry page.
+ */
+function TKR_setupKibblesOnEntryPage(listUrl, entryUrl) {
+  TKR_setupKibblesComponentKeys(listUrl, entryUrl, 'entry');
+}
+
+
+/**
+ * Initialize kibbles keystrokes for an artifact list page.
+ * @param {string} listUrl Rooted URL of the artifact list.
+ * @param {string} entryUrl Rooted URL of the artifact entry page.
+ * @param {string} projectName Name of the current project.
+ * @param {number} linkCellIndex table column that is expected to
+ *   link to individual artifacts.
+ * @param {number} opt_checkboxCellIndex table column that is expected
+ *   to contain a selection checkbox.
+ */
+function TKR_setupKibblesOnListPage(
+    listUrl, entryUrl, projectName, linkCellIndex,
+    opt_checkboxCellIndex) {
+  TKR_setupKibblesCursorStops(true);
+
+  kibbles.skipper.addFwdKey('j');
+  kibbles.skipper.addRevKey('k');
+
+  if (opt_checkboxCellIndex != undefined) {
+    const cbCellIndex = opt_checkboxCellIndex;
+    kibbles.keys.addKeyPressListener(
+        'x', function() {
+          TKR_selectArtifactAtCursor(cbCellIndex);
+        });
+    kibbles.keys.addKeyPressListener(
+        's',
+        function() {
+          TKR_toggleStarArtifactAtCursor(cbCellIndex);
+        });
+  }
+  kibbles.keys.addKeyPressListener(
+      'o', function() {
+        TKR_openArtifactAtCursor(linkCellIndex, false);
+      });
+  kibbles.keys.addKeyPressListener(
+      'O', function() {
+        TKR_openArtifactAtCursor(linkCellIndex, true);
+      });
+  kibbles.keys.addKeyPressListener(
+      'enter', function() {
+        TKR_openArtifactAtCursor(linkCellIndex);
+      });
+
+  TKR_setupKibblesComponentKeys(listUrl, entryUrl, 'list');
+}
diff --git a/static/js/tracker/tracker-nav.js b/static/js/tracker/tracker-nav.js
new file mode 100644
index 0000000..4458a51
--- /dev/null
+++ b/static/js/tracker/tracker-nav.js
@@ -0,0 +1,182 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+/* eslint-disable no-var */
+
+/**
+ * This file contains JS functions that implement various navigation
+ * features of Monorail.
+ */
+
+
+/**
+ * Navigate the browser to the given URL.
+ * @param {string} url The URL of the page to browse.
+ * @param {boolean} newWindow Open a new tab or window.
+ */
+function TKR_go(url, newWindow) {
+  if (newWindow) {
+    window.open(url, '_blank');
+  } else {
+    document.location = url;
+  }
+}
+
+
+/**
+ * Tell the browser to scroll to the given anchor on the current page.
+ * @param {string} anchor Name of the <a name="xxx"> anchor on the page.
+ */
+function TKR_goToAnchor(anchor) {
+  document.location.hash = anchor;
+}
+
+
+/**
+ * Get the user-editable colspec form field.  This text field is normally
+ * display:none, but it is shown when the user chooses "Edit columns...".
+ * We need a function to get this element because there are multiple form
+ * fields on the page with name="colspec", and an IE misfeature sets their
+ * id attributes as well, which makes document.getElementById() fail.
+ * @return {Element} user editable colspec form field.
+ */
+function TKR_getColspecElement() {
+  const elem = document.getElementById('colspec_field');
+  return elem && elem.firstChild;
+}
+
+
+/**
+ * Get the artifact search form field.  This is a visible text field where
+ * the user enters a query for issues. This function
+ * is needed because there is also the project search field on the each page,
+ * and it has name="q".  An IE misfeature confuses name="..." with id="...".
+ * @return {Element} artifact query form field, or undefined.
+ */
+function TKR_getArtifactSearchField() {
+  const element = _getSearchBarComponent();
+  if (!element) return $('searchq');
+
+  return element.shadowRoot.querySelector('#searchq');
+}
+
+
+/**
+ * Get the can selector. This function
+ * @return {Element} can input element.
+ */
+function TKR_getArtifactCanField() {
+  const element = _getSearchBarComponent();
+  if (!element) return $('can');
+
+  return element.shadowRoot.querySelector('#can');
+}
+
+
+function _getSearchBarComponent() {
+  const element = document.querySelector('mr-header');
+  if (!element) return;
+
+  return element.shadowRoot.querySelector('mr-search-bar');
+}
+
+
+/**
+ * Build a query string for all the common contextual values that we use.
+ */
+function TKR_formatContextQueryArgs() {
+  let args = '';
+  let colspec = _ctxDefaultColspec;
+  const colSpecElem = TKR_getColspecElement();
+  if (colSpecElem) {
+    colspec = colSpecElem.value;
+  }
+
+  if (_ctxHotlistID != '') args += '&hotlist_id=' + _ctxHotlistID;
+  if (_ctxCan != 2) args += '&can=' + _ctxCan;
+  args += '&q=' + encodeURIComponent(_ctxQuery);
+  if (_ctxSortspec != '') args += '&sort=' + _ctxSortspec;
+  if (_ctxGroupBy != '') args += '&groupby=' + _ctxGroupBy;
+  if (colspec != _ctxDefaultColspec) args += '&colspec=' + colspec;
+  if (_ctxStart != 0) args += '&start=' + _ctxStart;
+  if (_ctxNum != _ctxResultsPerPage) args += '&num=' + _ctxNum;
+  if (!colSpecElem) args += '&mode=grid';
+  return args;
+}
+
+// Fields that should use ":" when filtering.
+const _PRETOKENIZED_FIELDS = [
+  'owner', 'reporter', 'cc', 'commentby', 'component'];
+
+/**
+ * The user wants to narrow their search results by adding a search term
+ * for the given prefix and value. Reload the issue list page with that
+ * additional search term.
+ * @param {string} prefix Field or label prefix, e.g., "Priority".
+ * @param {string} suffix Field or label value, e.g., "High".
+ */
+function TKR_filterTo(prefix, suffix) {
+  let newQuery = TKR_getArtifactSearchField().value;
+  if (newQuery != '') newQuery += ' ';
+
+  let op = '=';
+  for (let i = 0; i < _PRETOKENIZED_FIELDS.length; i++) {
+    if (prefix == _PRETOKENIZED_FIELDS[i]) {
+      op = ':';
+      break;
+    }
+  }
+
+  newQuery += prefix + op + suffix;
+  let url = 'list?can=' + TKR_getArtifactCanField().value + '&q=' + newQuery;
+  if ($('sort') && $('sort').value) url += '&sort=' + $('sort').value;
+  url += '&colspec=' + TKR_getColspecElement().value;
+  TKR_go(url);
+}
+
+
+/**
+ * The user wants to sort their search results by adding a sort spec
+ * for the given column. Reload the issue list page with that
+ * additional sort spec.
+ * @param {string} colname Field or label prefix, e.g., "Priority".
+ * @param {boolean} descending True if the values should be reversed.
+ */
+function TKR_addSort(colname, descending) {
+  let existingSortSpec = '';
+  if ($('sort')) {
+    existingSortSpec = $('sort').value;
+  }
+  const oldSpecs = existingSortSpec.split(/ +/);
+  let sortDirective = colname;
+  if (descending) sortDirective = '-' + colname;
+  const specs = [sortDirective];
+  for (let i = 0; i < oldSpecs.length; i++) {
+    if (oldSpecs[i] != '' && oldSpecs[i] != colname &&
+        oldSpecs[i] != '-' + colname) {
+      specs.push(oldSpecs[i]);
+    }
+  }
+
+  const isHotlist = window.location.href.includes('/hotlists/');
+  let url = isHotlist ? ($('hotlist_name').value + '?') : ('list?');
+  url += ('can='+ TKR_getArtifactCanField().value + '&q=' +
+      TKR_getArtifactSearchField().value);
+  url += '&sort=' + specs.join('+');
+  url += '&colspec=' + TKR_getColspecElement().value;
+  TKR_go(url);
+}
+
+/** Convenience function for sorting in ascending order. */
+function TKR_sortUp(colname) {
+  TKR_addSort(colname, false);
+}
+
+/** Convenience function for sorting in descending order. */
+function TKR_sortDown(colname) {
+  TKR_addSort(colname, true);
+}
+
diff --git a/static/js/tracker/tracker-onload.js b/static/js/tracker/tracker-onload.js
new file mode 100644
index 0000000..051c86d
--- /dev/null
+++ b/static/js/tracker/tracker-onload.js
@@ -0,0 +1,136 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+/* eslint-disable camelcase */
+/* eslint-disable no-unused-vars */
+
+
+/**
+ * This file contains the Monorail onload() function that is called
+ * when each EZT page loads.
+ */
+
+
+/**
+ * This code is run on every DIT page load.  It registers a handler
+ * for autocomplete on four different types of text fields based on the
+ * name of that text field.
+ */
+function TKR_onload() {
+  TKR_install_ac();
+  _PC_Install();
+  TKR_allColumnNames = _allColumnNames;
+  TKR_labelFieldIDPrefix = _lfidprefix;
+  TKR_allOrigLabels = _allOrigLabels;
+  TKR_initialFormValues = TKR_currentFormValues();
+}
+
+// External names for functions that are called directly from HTML.
+// JSCompiler does not rename functions that begin with an underscore.
+// They are not defined with "var" because we want them to be global.
+
+// TODO(jrobbins): the underscore names could be shortened by a
+// cross-file search-and-replace script in our build process.
+
+_selectAllIssues = TKR_selectAllIssues;
+_selectNoneIssues = TKR_selectNoneIssues;
+
+_toggleRows = TKR_toggleRows;
+_toggleColumn = TKR_toggleColumn;
+_toggleColumnUpdate = TKR_toggleColumnUpdate;
+_addGroupBy = TKR_addGroupBy;
+_addcol = TKR_addColumn;
+_checkRangeSelect = TKR_checkRangeSelect;
+_makeIssueLink = TKR_makeIssueLink;
+
+_onload = TKR_onload;
+
+_handleListActions = TKR_handleListActions;
+_handleDetailActions = TKR_handleDetailActions;
+
+_loadStatusSelect = TKR_loadStatusSelect;
+_fetchUserProjects = TKR_fetchUserProjects;
+_setACOptions = TKR_setUpAutoCompleteStore;
+_openIssueUpdateForm = TKR_openIssueUpdateForm;
+_addAttachmentFields = TKR_addAttachmentFields;
+_ignoreWidgetIfOpIsClear = TKR_ignoreWidgetIfOpIsClear;
+
+_acstore = _AC_SimpleStore;
+_accomp = _AC_Completion;
+_acreg = _ac_register;
+
+_formatContextQueryArgs = TKR_formatContextQueryArgs;
+_ctxArgs = '';
+_ctxCan = undefined;
+_ctxQuery = undefined;
+_ctxSortspec = undefined;
+_ctxGroupBy = undefined;
+_ctxDefaultColspec = undefined;
+_ctxStart = undefined;
+_ctxNum = undefined;
+_ctxResultsPerPage = undefined;
+
+_filterTo = TKR_filterTo;
+_sortUp = TKR_sortUp;
+_sortDown = TKR_sortDown;
+
+_closeAllPopups = TKR_closeAllPopups;
+_closeSubmenus = TKR_closeSubmenus;
+_showRight = TKR_showRight;
+_showBelow = TKR_showBelow;
+_highlightRow = TKR_highlightRow;
+
+_setFieldIDs = TKR_setFieldIDs;
+_selectTemplate = TKR_selectTemplate;
+_saveTemplate = TKR_saveTemplate;
+_newTemplate = TKR_newTemplate;
+_deleteTemplate = TKR_deleteTemplate;
+_switchTemplate = TKR_switchTemplate;
+_templateNames = TKR_templateNames;
+
+_confirmNovelStatus = TKR_confirmNovelStatus;
+_confirmNovelLabel = TKR_confirmNovelLabel;
+_vallab = TKR_validateLabel;
+_exposeExistingLabelFields = TKR_exposeExistingLabelFields;
+_confirmDiscardEntry = TKR_confirmDiscardEntry;
+_confirmDiscardUpdate = TKR_confirmDiscardUpdate;
+_lfidprefix = undefined;
+_allOrigLabels = undefined;
+_checkPlusOne = TKR_checkPlusOne;
+_checkUnrestrict = TKR_checkUnrestrict;
+
+_clearOnFirstEvent = TKR_clearOnFirstEvent;
+_forceProperTableWidth = TKR_forceProperTableWidth;
+
+_initialFormValues = TKR_initialFormValues;
+_currentFormValues = TKR_currentFormValues;
+
+_acof = _ac_onfocus;
+_acmo = _ac_mouseover;
+_acse = _ac_select;
+_acrob = _ac_ob;
+
+// Variables that are given values in the HTML file.
+_allColumnNames = [];
+
+_go = TKR_go;
+_getColspec = TKR_getColspecElement;
+
+// Make the document actually listen for click events, otherwise the
+// event handlers above would never get called.
+if (document.captureEvents) document.captureEvents(Event.CLICK);
+
+_setupKibblesOnEntryPage = TKR_setupKibblesOnEntryPage;
+_setupKibblesOnListPage = TKR_setupKibblesOnListPage;
+
+_checkFieldNameOnServer = TKR_checkFieldNameOnServer;
+_checkLeafName = TKR_checkLeafName;
+
+_addMultiFieldValueWidget = TKR_addMultiFieldValueWidget;
+_removeMultiFieldValueWidget = TKR_removeMultiFieldValueWidget;
+_trimCommas = TKR_trimCommas;
+
+_initDragAndDrop = TKR_initDragAndDrop;
diff --git a/static/js/tracker/tracker-update-issues-hotlists.js b/static/js/tracker/tracker-update-issues-hotlists.js
new file mode 100644
index 0000000..04a85bf
--- /dev/null
+++ b/static/js/tracker/tracker-update-issues-hotlists.js
@@ -0,0 +1,320 @@
+/* Copyright 2018 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+/**
+ * This file contains JS functions that support a dialog for adding and removing
+ * issues from hotlists in Monorail.
+ */
+
+(function() {
+  window.__hotlists_dialog = window.__hotlists_dialog || {};
+
+  // An optional IssueRef.
+  // If set, we will not check for selected issues, and only add/remove issueRef
+  // instead.
+  window.__hotlists_dialog.issueRef = null;
+  // A function to be called with the modified hotlists. If issueRef is set, the
+  // hotlists for which the user is owner and the issue is part of will be
+  // passed as well.
+  window.__hotlists_dialog.onResponse = () => {};
+  // A function to be called if there was an error updating the hotlists.
+  window.__hotlists_dialog.onFailure = () => {};
+
+  /**
+   * A function to show the hotlist dialog.
+   * It is the only function exported by this module.
+   */
+  function ShowUpdateHotlistDialog() {
+    _FetchHotlists().then(_BuildDialog);
+  }
+
+  async function _CreateNewHotlistWithIssues() {
+    let selectedIssueRefs;
+    if (window.__hotlists_dialog.issueRef) {
+      selectedIssueRefs = [window.__hotlists_dialog.issueRef];
+    } else {
+      selectedIssueRefs = _GetSelectedIssueRefs();
+    }
+
+    const name = await _CheckNewHotlistName();
+    if (!name) {
+      return;
+    }
+
+    const message = {
+      name: name,
+      summary: 'Hotlist of bulk added issues',
+      issueRefs: selectedIssueRefs,
+    };
+    try {
+      await window.prpcClient.call(
+          'monorail.Features', 'CreateHotlist', message);
+    } catch (error) {
+      window.__hotlists_dialog.onFailure(error);
+      return;
+    }
+
+    const newHotlist = [name, window.CS_env.loggedInUserEmail];
+    const newIssueHotlists = [];
+    window.__hotlists_dialog._issueHotlists.forEach(
+        hotlist => newIssueHotlists.push(hotlist.split('_')));
+    newIssueHotlists.push(newHotlist);
+    window.__hotlists_dialog.onResponse([newHotlist], newIssueHotlists);
+  }
+
+  async function _UpdateIssuesInHotlists() {
+    const hotlistRefsAdd = _GetSelectedHotlists(
+        window.__hotlists_dialog._userHotlists);
+    const hotlistRefsRemove = _GetSelectedHotlists(
+        window.__hotlists_dialog._issueHotlists);
+    if (hotlistRefsAdd.length === 0 && hotlistRefsRemove.length === 0) {
+      alert('Please select/un-select some hotlists');
+      return;
+    }
+
+    let selectedIssueRefs;
+    if (window.__hotlists_dialog.issueRef) {
+      selectedIssueRefs = [window.__hotlists_dialog.issueRef];
+    } else {
+      selectedIssueRefs = _GetSelectedIssueRefs();
+    }
+
+    if (hotlistRefsAdd.length > 0) {
+      const message = {
+        hotlistRefs: hotlistRefsAdd,
+        issueRefs: selectedIssueRefs,
+      };
+      try {
+        await window.prpcClient.call(
+            'monorail.Features', 'AddIssuesToHotlists', message);
+      } catch (error) {
+        window.__hotlists_dialog.onFailure(error);
+        return;
+      }
+      hotlistRefsAdd.forEach(hotlist => {
+        window.__hotlists_dialog._issueHotlists.add(
+            hotlist.name + '_' + hotlist.owner.user_id);
+      });
+    }
+
+    if (hotlistRefsRemove.length > 0) {
+      const message = {
+        hotlistRefs: hotlistRefsRemove,
+        issueRefs: selectedIssueRefs,
+      };
+      try {
+        await window.prpcClient.call(
+            'monorail.Features', 'RemoveIssuesFromHotlists', message);
+      } catch (error) {
+        window.__hotlists_dialog.onFailure(error);
+        return;
+      }
+      hotlistRefsRemove.forEach(hotlist => {
+        window.__hotlists_dialog._issueHotlists.delete(
+            hotlist.name + '_' + hotlist.owner.user_id);
+      });
+    }
+
+    const modifiedHotlists = hotlistRefsAdd.concat(hotlistRefsRemove).map(
+        hotlist => [hotlist.name, hotlist.owner.user_id]);
+    const newIssueHotlists = [];
+    window.__hotlists_dialog._issueHotlists.forEach(
+        hotlist => newIssueHotlists.push(hotlist.split('_')));
+
+    window.__hotlists_dialog.onResponse(modifiedHotlists, newIssueHotlists);
+  }
+
+  async function _FetchHotlists() {
+    const userHotlistsMessage = {
+      user: {
+        display_name: window.CS_env.loggedInUserEmail,
+      }
+    };
+    const userHotlistsResponse = await window.prpcClient.call(
+        'monorail.Features', 'ListHotlistsByUser', userHotlistsMessage);
+
+    // Here we have the list of all hotlists owned by the user. We filter out
+    // the hotlists that already contain issueRef in the next paragraph of code.
+    window.__hotlists_dialog._userHotlists = new Set();
+    (userHotlistsResponse.hotlists || []).forEach(hotlist => {
+      window.__hotlists_dialog._userHotlists.add(
+          hotlist.name + '_' + hotlist.ownerRef.userId);
+    });
+
+    // Here we filter out the hotlists that are owned by the user, and that
+    // contain issueRef from _userHotlists and save them into _issueHotlists.
+    window.__hotlists_dialog._issueHotlists = new Set();
+    if (window.__hotlists_dialog.issueRef) {
+      const issueHotlistsMessage = {
+        issue: window.__hotlists_dialog.issueRef,
+      };
+      const issueHotlistsResponse = await window.prpcClient.call(
+          'monorail.Features', 'ListHotlistsByIssue', issueHotlistsMessage);
+      (issueHotlistsResponse.hotlists || []).forEach(hotlist => {
+        const hotlistRef = hotlist.name + '_' + hotlist.ownerRef.userId;
+        if (window.__hotlists_dialog._userHotlists.has(hotlistRef)) {
+          window.__hotlists_dialog._userHotlists.delete(hotlistRef);
+          window.__hotlists_dialog._issueHotlists.add(hotlistRef);
+        }
+      });
+    }
+  }
+
+  function _BuildDialog() {
+    const table = $('js-hotlists-table');
+
+    while (table.firstChild) {
+      table.removeChild(table.firstChild);
+    }
+
+    if (window.__hotlists_dialog._issueHotlists.size > 0) {
+      _UpdateRows(
+          table, 'Remove issues from:',
+          window.__hotlists_dialog._issueHotlists);
+    }
+    _UpdateRows(table, 'Add issues to:',
+        window.__hotlists_dialog._userHotlists);
+    _BuildCreateNewHotlist(table);
+
+    $('update-issues-hotlists').style.display = 'block';
+    $('save-issues-hotlists').addEventListener(
+        'click', _UpdateIssuesInHotlists);
+    $('cancel-update-hotlists').addEventListener('click', function() {
+      $('update-issues-hotlists').style.display = 'none';
+    });
+
+  }
+
+  function _BuildCreateNewHotlist(table) {
+    const inputTr = document.createElement('tr');
+    inputTr.classList.add('hotlist_rows');
+
+    const inputCell = document.createElement('td');
+    const input = document.createElement('input');
+    input.setAttribute('id', 'text_new_hotlist_name');
+    input.setAttribute('placeholder', 'New hotlist name');
+    // Hotlist changes are automatic and should be ignored by
+    // TKR_currentFormValues() and TKR_isDirty()
+    input.setAttribute('ignore-dirty', true);
+    input.addEventListener('input', _CheckNewHotlistName);
+    inputCell.appendChild(input);
+    inputTr.appendChild(inputCell);
+
+    const buttonCell = document.createElement('td');
+    const button = document.createElement('button');
+    button.setAttribute('id', 'create-new-hotlist');
+    button.addEventListener('click', _CreateNewHotlistWithIssues);
+    button.textContent = 'Create New Hotlist';
+    button.disabled = true;
+    buttonCell.appendChild(button);
+    inputTr.appendChild(buttonCell);
+
+    table.appendChild(inputTr);
+
+    const feedbackTr = document.createElement('tr');
+    feedbackTr.classList.add('hotlist_rows');
+
+    const feedbackCell = document.createElement('td');
+    feedbackCell.setAttribute('colspan', '2');
+    const feedback = document.createElement('span');
+    feedback.classList.add('fielderror');
+    feedback.setAttribute('id', 'hotlistnamefeedback');
+    feedbackCell.appendChild(feedback);
+    feedbackTr.appendChild(feedbackCell);
+
+    table.appendChild(feedbackTr);
+  }
+
+  function _UpdateRows(table, title, hotlists) {
+    const tr = document.createElement('tr');
+    tr.classList.add('hotlist_rows');
+    const addCell = document.createElement('td');
+    const add = document.createElement('b');
+    add.textContent = title;
+    addCell.appendChild(add);
+    tr.appendChild(addCell);
+    table.appendChild(tr);
+
+    hotlists.forEach(hotlist => {
+      const hotlistParts = hotlist.split('_');
+      const name = hotlistParts[0];
+
+      const tr = document.createElement('tr');
+      tr.classList.add('hotlist_rows');
+
+      const cbCell = document.createElement('td');
+      const cb = document.createElement('input');
+      cb.classList.add('checkRangeSelect');
+      cb.setAttribute('id', 'cb_hotlist_' + hotlist);
+      cb.setAttribute('type', 'checkbox');
+      // Hotlist changes are automatic and should be ignored by
+      // TKR_currentFormValues() and TKR_isDirty()
+      cb.setAttribute('ignore-dirty', true);
+      cbCell.appendChild(cb);
+
+      const nameCell = document.createElement('td');
+      const label = document.createElement('label');
+      label.htmlFor = cb.id;
+      label.textContent = name;
+      nameCell.appendChild(label);
+
+      tr.appendChild(cbCell);
+      tr.appendChild(nameCell);
+      table.appendChild(tr);
+    });
+  }
+
+  async function _CheckNewHotlistName() {
+    const name = $('text_new_hotlist_name').value;
+    const checkNameResponse = await window.prpcClient.call(
+        'monorail.Features', 'CheckHotlistName', {name});
+
+    if (checkNameResponse.error) {
+      $('hotlistnamefeedback').textContent = checkNameResponse.error;
+      $('create-new-hotlist').disabled = true;
+      return null;
+    }
+
+    $('hotlistnamefeedback').textContent = '';
+    $('create-new-hotlist').disabled = false;
+    return name;
+  }
+
+  /**
+  * Call GetSelectedIssuesRefs from tracker-editing.js and convert to an Array
+  * of IssueRef PBs.
+  */
+  function _GetSelectedIssueRefs() {
+    return GetSelectedIssuesRefs().map(issueRef => ({
+      project_name: issueRef['project_name'],
+      local_id: issueRef['id'],
+    }));
+  }
+
+  /**
+   * Get HotlistRef PBs for the hotlists that the user wants to add/remove the
+   * selected issues to.
+   */
+  function _GetSelectedHotlists(hotlists) {
+    const selectedHotlistRefs = [];
+    hotlists.forEach(hotlist => {
+      const checkbox = $('cb_hotlist_' + hotlist);
+      const hotlistParts = hotlist.split('_');
+      if (checkbox && checkbox.checked) {
+        selectedHotlistRefs.push({
+          name: hotlistParts[0],
+          owner: {
+            user_id: hotlistParts[1],
+          }
+        });
+      }
+    });
+    return selectedHotlistRefs;
+  }
+
+  Object.assign(window.__hotlists_dialog, {ShowUpdateHotlistDialog});
+})();
diff --git a/static/js/tracker/tracker-util.js b/static/js/tracker/tracker-util.js
new file mode 100644
index 0000000..040f8c1
--- /dev/null
+++ b/static/js/tracker/tracker-util.js
@@ -0,0 +1,166 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+/**
+ * This file contains JS utilities used by other JS files in Monorail.
+ */
+
+
+/**
+ * Add an indexOf method to all arrays, if this brower's JS implementation
+ * does not already have it.
+ * @param {Object} item The item to find
+ * @return {number} The index of the given item, or -1 if not found.
+ */
+if (Array.prototype.indexOf == undefined) {
+  Array.prototype.indexOf = function(item) {
+    for (let i = 0; i < this.length; ++i) {
+      if (this[i] == item) return i;
+    }
+    return -1;
+  };
+}
+
+
+/**
+ * This function works around a FF HTML layout problem.  The table
+ * width is somehow rendered at 100% when the table contains a
+ * display:none element, later, when that element is displayed, the
+ * table renders at the correct width.  The work-around is to have the
+ * element initiallye displayed so that the table renders properly,
+ * but then immediately hide the element until it is needed.
+ *
+ * TODO(jrobbins): Find HTML markup that FF can render more
+ * consistently.  After that, I can remove this hack.
+ */
+function TKR_forceProperTableWidth() {
+  let e = $('confirmarea');
+  if (e) e.style.display='none';
+}
+
+
+function TKR_parseIssueRef(issueRef) {
+  issueRef = issueRef.trim();
+  if (!issueRef) {
+    return null;
+  }
+
+  let projectName = window.CS_env.projectName;
+  let localId = issueRef;
+  if (issueRef.includes(':')) {
+    const parts = issueRef.split(':', 2);
+    projectName = parts[0];
+    localId = parts[1];
+  }
+
+  return {
+    project_name: projectName,
+    local_id: localId};
+}
+
+
+function _buildFieldsForIssueDelta(issueDelta, valuesByName) {
+  issueDelta.field_vals_add = [];
+  issueDelta.field_vals_remove = [];
+  issueDelta.fields_clear = [];
+
+  valuesByName.forEach((values, key, map) => {
+    if (key.startsWith('op_custom_') && values == 'clear') {
+      const field_id = key.substring('op_custom_'.length);
+      issueDelta.fields_clear.push({field_id: field_id});
+    } else if (key.startsWith('custom_')) {
+      const field_id = key.substring('custom_'.length);
+      values = values.filter(Boolean);
+      if (valuesByName.get('op_' + key) === 'remove') {
+        values.forEach((value) => {
+          issueDelta.field_vals_remove.push({
+            field_ref: {field_id: field_id},
+            value: value});
+        });
+      } else {
+        values.forEach((value) => {
+          issueDelta.field_vals_add.push({
+            field_ref: {field_id: field_id},
+            value: value});
+        });
+      }
+    }
+  });
+}
+
+
+function _classifyPlusMinusItems(values) {
+  let result = {
+    add: [],
+    remove: []};
+  values = new Set(values);
+  values.forEach((value) => {
+    if (!value.startsWith('-') && value) {
+      result.add.push(value);
+    } else if (value.startsWith('-') && value.substring(1)) {
+      result.remove.push(value);
+    }
+  });
+  return result;
+}
+
+
+function TKR_buildIssueDelta(valuesByName) {
+  let issueDelta = {};
+
+  if (valuesByName.has('status')) {
+    issueDelta.status = valuesByName.get('status')[0];
+  }
+  if (valuesByName.has('owner')) {
+    issueDelta.owner_ref = {
+      display_name: valuesByName.get('owner')[0].trim().toLowerCase()};
+  }
+  if (valuesByName.has('cc')) {
+    const cc_usernames = _classifyPlusMinusItems(
+      valuesByName.get('cc')[0].toLowerCase().split(/[,;\s]+/));
+    issueDelta.cc_refs_add = cc_usernames.add.map(
+      (email) => ({display_name: email}));
+    issueDelta.cc_refs_remove = cc_usernames.remove.map(
+      (email) => ({display_name: email}));
+  }
+  if (valuesByName.has('components')) {
+    const components = _classifyPlusMinusItems(
+      valuesByName.get('components')[0].split(/[,;\s]/));
+    issueDelta.comp_refs_add = components.add.map(
+      (path) => ({path: path}));
+    issueDelta.comp_refs_remove = components.remove.map(
+      (path) => ({path: path}));
+  }
+  if (valuesByName.has('label')) {
+    const labels = _classifyPlusMinusItems(valuesByName.get('label'));
+    issueDelta.label_refs_add = labels.add.map(
+      (label) => ({label: label}));
+    issueDelta.label_refs_remove = labels.remove.map(
+      (label) => ({label: label}));
+  }
+  if (valuesByName.has('blocked_on')) {
+    const blockedOn = _classifyPlusMinusItems(valuesByName.get('blocked_on'));
+    issueDelta.blocked_on_refs_add = blockedOn.add.map(TKR_parseIssueRef);
+    issueDelta.blocked_on_refs_add = blockedOn.remove.map(TKR_parseIssueRef);
+  }
+  if (valuesByName.has('blocking')) {
+    const blocking = _classifyPlusMinusItems(valuesByName.get('blocking'));
+    issueDelta.blocking_refs_add = blocking.add.map(TKR_parseIssueRef);
+    issueDelta.blocking_refs_add = blocking.remove.map(TKR_parseIssueRef);
+  }
+  if (valuesByName.has('merge_into')) {
+    issueDelta.merged_into_ref = TKR_parseIssueRef(
+      valuesByName.get('merge_into')[0]);
+  }
+  if (valuesByName.has('summary')) {
+    issueDelta.summary = valuesByName.get('summary')[0];
+  }
+
+  _buildFieldsForIssueDelta(issueDelta, valuesByName);
+
+  return issueDelta;
+}
diff --git a/static/js/tracker/trackerac_test.js b/static/js/tracker/trackerac_test.js
new file mode 100644
index 0000000..583fb01
--- /dev/null
+++ b/static/js/tracker/trackerac_test.js
@@ -0,0 +1,132 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+const feedData = {
+  'open': [{name: 'New', doc: 'Newly reported'},
+    {name: 'Started', doc: 'Work has begun'}],
+  'closed': [{name: 'Fixed', doc: 'Problem was fixed'},
+    {name: 'Invalid', doc: 'Bad issue report'}],
+  'labels': [{name: 'Type-Defect', doc: 'Something is broken'},
+    {name: 'Type-Enhancement', doc: 'It could be better'},
+    {name: 'Priority-High', doc: 'Urgent'},
+    {name: 'Priority-Low', doc: 'Not so urgent'},
+    {name: 'Hot', doc: ''},
+    {name: 'Cold', doc: ''}],
+  'members': [{name: 'jrobbins', doc: ''},
+    {name: 'jrobbins@chromium.org', doc: ''}],
+  'excl_prefixes': [],
+  'strict': false,
+};
+
+function setUp() {
+  TKR_autoCompleteFeedName = 'issueOptions';
+}
+
+/**
+ * The assertEquals method cannot do element-by-element comparisons.
+ * A search of how other teams write JS unit tests turned up this
+ * way to compare arrays.
+ */
+function assertElementsEqual(arrayA, arrayB) {
+  assertEquals(arrayA.join(' ;; '), arrayB.join(' ;; '));
+}
+
+function completionsEqual(strings, completions) {
+  if (strings.length != completions.length) {
+    return false;
+  }
+  for (let i = 0; i < strings.length; i++) {
+    if (strings[i] != completions[i].value) {
+      return false;
+    }
+  }
+  return true;
+}
+
+function assertHasCompletion(s, acStore) {
+  const ch = s.charAt(0).toLowerCase();
+  const firstCharMapArray = acStore.firstCharMap_[ch];
+  assertNotNull(!firstCharMapArray);
+  for (let i = 0; i < firstCharMapArray.length; i++) {
+    if (s == firstCharMapArray[i].value) return;
+  }
+  fail('completion ' + s + ' not found in acStore[' +
+       acStoreToString(acStore) + ']');
+}
+
+function assertHasAllCompletions(stringArray, acStore) {
+  for (let i = 0; i < stringArray.length; i++) {
+    assertHasCompletion(stringArray[i], acStore);
+  }
+}
+
+function acStoreToString(acStore) {
+  const allCompletions = [];
+  for (const ch in acStore.firstCharMap_) {
+    if (acStore.firstCharMap_.hasOwnProperty(ch)) {
+      const firstCharArray = acStore.firstCharMap_[ch];
+      for (let i = 0; i < firstCharArray.length; i++) {
+        allCompletions[firstCharArray[i].value] = true;
+      }
+    }
+  }
+  const parts = [];
+  for (const comp in allCompletions) {
+    if (allCompletions.hasOwnProperty(comp)) {
+      parts.push(comp);
+    }
+  }
+  return parts.join(', ');
+}
+
+function testSetUpStatusStore() {
+  TKR_setUpStatusStore(feedData.open, feedData.closed);
+  assertElementsEqual(
+      ['New', 'Started', 'Fixed', 'Invalid'],
+      TKR_statusWords);
+  assertHasAllCompletions(
+      ['New', 'Started', 'Fixed', 'Invalid'],
+      TKR_statusStore);
+}
+
+function testSetUpSearchStore() {
+  TKR_setUpSearchStore(
+      feedData.labels, feedData.members, feedData.open, feedData.closed);
+  assertHasAllCompletions(
+      ['status:New', 'status:Started', 'status:Fixed', 'status:Invalid',
+        '-status:New', '-status:Started', '-status:Fixed', '-status:Invalid',
+        'Type=Defect', '-Type=Defect', 'Type=Enhancement', '-Type=Enhancement',
+        'label:Hot', 'label:Cold', '-label:Hot', '-label:Cold',
+        'owner:jrobbins', 'cc:jrobbins', '-owner:jrobbins', '-cc:jrobbins',
+        'summary:', 'opened-after:today-1', 'commentby:me', 'reporter:me'],
+      TKR_searchStore);
+}
+
+function testSetUpQuickEditStore() {
+  TKR_setUpQuickEditStore(
+      feedData.labels, feedData.members, feedData.open, feedData.closed);
+  assertHasAllCompletions(
+      ['status=New', 'status=Started', 'status=Fixed', 'status=Invalid',
+        'Type=Defect', 'Type=Enhancement', 'Hot', 'Cold', '-Hot', '-Cold',
+        'owner=jrobbins', 'owner=me', 'cc=jrobbins', 'cc=me', 'cc=-jrobbins',
+        'cc=-me', 'summary=""', 'owner=----'],
+      TKR_quickEditStore);
+}
+
+function testSetUpLabelStore() {
+  TKR_setUpLabelStore(feedData.labels);
+  assertHasAllCompletions(
+      ['Type-Defect', 'Type-Enhancement', 'Hot', 'Cold'],
+      TKR_labelStore);
+}
+
+function testSetUpMembersStore() {
+  TKR_setUpMemberStore(feedData.members);
+  assertHasAllCompletions(
+      ['jrobbins', 'jrobbins@chromium.org'],
+      TKR_memberListStore);
+}
diff --git a/static/js/tracker/trackerediting_test.js b/static/js/tracker/trackerediting_test.js
new file mode 100644
index 0000000..27d45bf
--- /dev/null
+++ b/static/js/tracker/trackerediting_test.js
@@ -0,0 +1,69 @@
+/* Copyright 2016 The Chromium Authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the LICENSE file or at
+ * https://developers.google.com/open-source/licenses/bsd
+ */
+
+
+function testKeepJustSummaryPrefixes_NoPrefixes() {
+  assertEquals(
+      '',
+      TKR_keepJustSummaryPrefixes(''));
+
+  assertEquals(
+      '',
+      TKR_keepJustSummaryPrefixes('Enter one line summary'));
+
+  assertEquals(
+      '',
+      TKR_keepJustSummaryPrefixes('Translation problem [en]'));
+
+  assertEquals(
+      '',
+      TKR_keepJustSummaryPrefixes('Crash at HH:MM'));
+}
+
+function testKeepJustSummaryPrefixes_WithColons() {
+  assertEquals(
+      'Security: ',
+      TKR_keepJustSummaryPrefixes('Security:'));
+
+  assertEquals(
+      'Exploit: ',
+      TKR_keepJustSummaryPrefixes('Exploit: remote exploit'));
+
+  assertEquals(
+      'XSS:Security: ',
+      TKR_keepJustSummaryPrefixes('XSS:Security: rest of summary'));
+
+  assertEquals(
+      'XSS: Security: ',
+      TKR_keepJustSummaryPrefixes('XSS: Security: rest of summary'));
+
+  assertEquals(
+      'XSS-Security: ',
+      TKR_keepJustSummaryPrefixes('XSS-Security: rest of summary'));
+
+  assertEquals(
+      'XSS: Security: ',
+      TKR_keepJustSummaryPrefixes('XSS: Security: rest [of] su:mmary'));
+
+  assertEquals(
+      'XSS-Security: ',
+      TKR_keepJustSummaryPrefixes('XSS-Security: rest [of] su:mmary'));
+}
+
+function testKeepJustSummaryPrefixes_WithBrackets() {
+  assertEquals(
+      '[Printing] ',
+      TKR_keepJustSummaryPrefixes('[Printing] problem with page'));
+
+  assertEquals(
+      '[Printing] ',
+      TKR_keepJustSummaryPrefixes('[Printing]   problem with page'));
+
+  assertEquals(
+      '[l10n][en] ',
+      TKR_keepJustSummaryPrefixes('[l10n][en]Translation problem'));
+}
