Merge "Revert "Debounce autocomplete queries by default""
diff --git a/polygerrit-ui/app/elements/change/gr-confirm-rebase-dialog/gr-confirm-rebase-dialog.html b/polygerrit-ui/app/elements/change/gr-confirm-rebase-dialog/gr-confirm-rebase-dialog.html
index 5d69499..8e179cc 100644
--- a/polygerrit-ui/app/elements/change/gr-confirm-rebase-dialog/gr-confirm-rebase-dialog.html
+++ b/polygerrit-ui/app/elements/change/gr-confirm-rebase-dialog/gr-confirm-rebase-dialog.html
@@ -105,7 +105,6 @@
           <gr-autocomplete
               id="parentInput"
               query="[[_query]]"
-              no-debounce
               text="{{_inputText}}"
               on-tap="_handleEnterChangeNumberTap"
               on-commit="_handleBaseSelected"
diff --git a/polygerrit-ui/app/elements/change/gr-confirm-rebase-dialog/gr-confirm-rebase-dialog_test.html b/polygerrit-ui/app/elements/change/gr-confirm-rebase-dialog/gr-confirm-rebase-dialog_test.html
index c89784f..24815db 100644
--- a/polygerrit-ui/app/elements/change/gr-confirm-rebase-dialog/gr-confirm-rebase-dialog_test.html
+++ b/polygerrit-ui/app/elements/change/gr-confirm-rebase-dialog/gr-confirm-rebase-dialog_test.html
@@ -166,7 +166,6 @@
 
       test('input text change triggers function', () => {
         sandbox.spy(element, '_getRecentChanges');
-        element.$.parentInput.noDebounce = true;
         element._inputText = '1';
         assert.isTrue(element._getRecentChanges.calledOnce);
         element._inputText = '12';
diff --git a/polygerrit-ui/app/elements/core/gr-search-bar/gr-search-bar.html b/polygerrit-ui/app/elements/core/gr-search-bar/gr-search-bar.html
index fdd730d..169fd85 100644
--- a/polygerrit-ui/app/elements/core/gr-search-bar/gr-search-bar.html
+++ b/polygerrit-ui/app/elements/core/gr-search-bar/gr-search-bar.html
@@ -48,6 +48,7 @@
           id="searchInput"
           text="{{_inputVal}}"
           query="[[query]]"
+          debounce-wait="200"
           on-commit="_handleInputCommit"
           allow-non-suggested-values
           multi
diff --git a/polygerrit-ui/app/elements/edit/gr-edit-controls/gr-edit-controls_test.html b/polygerrit-ui/app/elements/edit/gr-edit-controls/gr-edit-controls_test.html
index c67a2af..9d85d37 100644
--- a/polygerrit-ui/app/elements/edit/gr-edit-controls/gr-edit-controls_test.html
+++ b/polygerrit-ui/app/elements/edit/gr-edit-controls/gr-edit-controls_test.html
@@ -61,14 +61,12 @@
 
   suite('edit button CUJ', () => {
     let navStubs;
-    let openAutoCcmplete;
 
     setup(() => {
       navStubs = [
         sandbox.stub(Gerrit.Nav, 'getEditUrlForDiff'),
         sandbox.stub(Gerrit.Nav, 'navigateToRelativeUrl'),
       ];
-      openAutoCcmplete = element.$.openDialog.querySelector('gr-autocomplete');
     });
 
     test('_isValidPath', () => {
@@ -86,8 +84,8 @@
         assert.isTrue(element._hideAllDialogs.called);
         assert.isTrue(element.$.openDialog.disabled);
         assert.isFalse(queryStub.called);
-        openAutoCcmplete.noDebounce = true;
-        openAutoCcmplete.text = 'src/test.cpp';
+        element.$.openDialog.querySelector('gr-autocomplete').text =
+            'src/test.cpp';
         assert.isTrue(queryStub.called);
         assert.isFalse(element.$.openDialog.disabled);
         MockInteractions.tap(element.$.openDialog.$$('gr-button[primary]'));
@@ -102,8 +100,8 @@
       MockInteractions.tap(element.$$('#open'));
       return showDialogSpy.lastCall.returnValue.then(() => {
         assert.isTrue(element.$.openDialog.disabled);
-        openAutoCcmplete.noDebounce = true;
-        openAutoCcmplete.text = 'src/test.cpp';
+        element.$.openDialog.querySelector('gr-autocomplete').text =
+            'src/test.cpp';
         assert.isFalse(element.$.openDialog.disabled);
         MockInteractions.tap(element.$.openDialog.$$('gr-button'));
         for (const stub of navStubs) { assert.isFalse(stub.called); }
@@ -116,13 +114,10 @@
   suite('delete button CUJ', () => {
     let navStub;
     let deleteStub;
-    let deleteAutocomplete;
 
     setup(() => {
       navStub = sandbox.stub(Gerrit.Nav, 'navigateToChange');
       deleteStub = sandbox.stub(element.$.restAPI, 'deleteFileInChangeEdit');
-      deleteAutocomplete =
-          element.$.deleteDialog.querySelector('gr-autocomplete');
     });
 
     test('delete', () => {
@@ -131,8 +126,8 @@
       return showDialogSpy.lastCall.returnValue.then(() => {
         assert.isTrue(element.$.deleteDialog.disabled);
         assert.isFalse(queryStub.called);
-        deleteAutocomplete.noDebounce = true;
-        deleteAutocomplete.text = 'src/test.cpp';
+        element.$.deleteDialog.querySelector('gr-autocomplete').text =
+            'src/test.cpp';
         assert.isTrue(queryStub.called);
         assert.isFalse(element.$.deleteDialog.disabled);
         MockInteractions.tap(element.$.deleteDialog.$$('gr-button[primary]'));
@@ -154,8 +149,8 @@
       return showDialogSpy.lastCall.returnValue.then(() => {
         assert.isTrue(element.$.deleteDialog.disabled);
         assert.isFalse(queryStub.called);
-        deleteAutocomplete.noDebounce = true;
-        deleteAutocomplete.text = 'src/test.cpp';
+        element.$.deleteDialog.querySelector('gr-autocomplete').text =
+            'src/test.cpp';
         assert.isTrue(queryStub.called);
         assert.isFalse(element.$.deleteDialog.disabled);
         MockInteractions.tap(element.$.deleteDialog.$$('gr-button[primary]'));
@@ -188,13 +183,10 @@
   suite('rename button CUJ', () => {
     let navStub;
     let renameStub;
-    let renameAutocomplete;
 
     setup(() => {
       navStub = sandbox.stub(Gerrit.Nav, 'navigateToChange');
       renameStub = sandbox.stub(element.$.restAPI, 'renameFileInChangeEdit');
-      renameAutocomplete =
-          element.$.renameDialog.querySelector('gr-autocomplete');
     });
 
     test('rename', () => {
@@ -203,8 +195,8 @@
       return showDialogSpy.lastCall.returnValue.then(() => {
         assert.isTrue(element.$.renameDialog.disabled);
         assert.isFalse(queryStub.called);
-        renameAutocomplete.noDebounce = true;
-        renameAutocomplete.text = 'src/test.cpp';
+        element.$.renameDialog.querySelector('gr-autocomplete').text =
+            'src/test.cpp';
         assert.isTrue(queryStub.called);
         assert.isTrue(element.$.renameDialog.disabled);
 
@@ -231,8 +223,8 @@
       return showDialogSpy.lastCall.returnValue.then(() => {
         assert.isTrue(element.$.renameDialog.disabled);
         assert.isFalse(queryStub.called);
-        renameAutocomplete.noDebounce = true;
-        renameAutocomplete.text = 'src/test.cpp';
+        element.$.renameDialog.querySelector('gr-autocomplete').text =
+            'src/test.cpp';
         assert.isTrue(queryStub.called);
         assert.isTrue(element.$.renameDialog.disabled);
 
diff --git a/polygerrit-ui/app/elements/settings/gr-watched-projects-editor/gr-watched-projects-editor.html b/polygerrit-ui/app/elements/settings/gr-watched-projects-editor/gr-watched-projects-editor.html
index 558140f..0b8c331 100644
--- a/polygerrit-ui/app/elements/settings/gr-watched-projects-editor/gr-watched-projects-editor.html
+++ b/polygerrit-ui/app/elements/settings/gr-watched-projects-editor/gr-watched-projects-editor.html
@@ -96,6 +96,7 @@
             <th>
               <gr-autocomplete
                   id="newProject"
+                  debounce-wait="200"
                   query="[[_query]]"
                   threshold="1"
                   placeholder="Project"></gr-autocomplete>
diff --git a/polygerrit-ui/app/elements/shared/gr-autocomplete/gr-autocomplete.js b/polygerrit-ui/app/elements/shared/gr-autocomplete/gr-autocomplete.js
index 150be05..287ccdd 100644
--- a/polygerrit-ui/app/elements/shared/gr-autocomplete/gr-autocomplete.js
+++ b/polygerrit-ui/app/elements/shared/gr-autocomplete/gr-autocomplete.js
@@ -18,7 +18,6 @@
   'use strict';
 
   const TOKENIZE_REGEX = /(?:[^\s"]+|"[^"]*")+/g;
-  const DEBOUNCE_WAIT_MS = 200;
 
   Polymer({
     is: 'gr-autocomplete',
@@ -134,11 +133,12 @@
       },
 
       /**
-       * When true, querying for suggestions is not debounced w/r/t keypresses
+       * The number of milliseconds to use as the debounce wait time. If null,
+       * no debouncing is used.
        */
-      noDebounce: {
-        type: Boolean,
-        value: false,
+      debounceWait: {
+        type: Number,
+        value: null,
       },
 
       /** @type {?} */
@@ -176,7 +176,6 @@
 
     detached() {
       this.unlisten(document.body, 'tap', '_handleBodyTap');
-      this.cancelDebouncer('update-suggestions');
     },
 
     get focusStart() {
@@ -259,10 +258,10 @@
         });
       };
 
-      if (this.noDebounce) {
-        update();
+      if (this.debounceWait) {
+        this.debounce('update-suggestions', update, this.debounceWait);
       } else {
-        this.debounce('update-suggestions', update, DEBOUNCE_WAIT_MS);
+        update();
       }
     },
 
diff --git a/polygerrit-ui/app/elements/shared/gr-autocomplete/gr-autocomplete_test.html b/polygerrit-ui/app/elements/shared/gr-autocomplete/gr-autocomplete_test.html
index a216bd4..dfb0a0d 100644
--- a/polygerrit-ui/app/elements/shared/gr-autocomplete/gr-autocomplete_test.html
+++ b/polygerrit-ui/app/elements/shared/gr-autocomplete/gr-autocomplete_test.html
@@ -28,7 +28,7 @@
 
 <test-fixture id="basic">
   <template>
-    <gr-autocomplete no-debounce></gr-autocomplete>
+    <gr-autocomplete></gr-autocomplete>
   </template>
 </test-fixture>
 
@@ -236,7 +236,7 @@
       assert.isTrue(queryStub.called);
     });
 
-    test('noDebounce=false debounces the query', () => {
+    test('debounceWait debounces the query', () => {
       const queryStub = sandbox.spy(() => {
         return Promise.resolve([]);
       });
@@ -244,11 +244,11 @@
       const debounceStub = sandbox.stub(element, 'debounce',
           (name, cb) => { callback = cb; });
       element.query = queryStub;
-      element.noDebounce = false;
+      element.debounceWait = 100;
       element.text = 'a';
       assert.isFalse(queryStub.called);
       assert.isTrue(debounceStub.called);
-      assert.equal(debounceStub.lastCall.args[2], 200);
+      assert.equal(debounceStub.lastCall.args[2], 100);
       assert.isFunction(callback);
       callback();
       assert.isTrue(queryStub.called);