Bug 1497682 - Part 3. Add junit test. r=droeh
authorMakoto Kato <m_kato@ga2.so-net.ne.jp>
Tue, 18 Dec 2018 18:05:36 +0900
changeset 451125 b68c8690cc9e3fc1b7092d0939af17290479975d
parent 451124 78488dedd35ed0adcd9841f5f6a0db7eb365e58f
child 451126 5e4074b128f944119f2f224391453db85e2406cb
push id35227
push usercbrindusan@mozilla.com
push dateTue, 18 Dec 2018 17:34:45 +0000
treeherdermozilla-central@1a7fb4c17553 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersdroeh
bugs1497682
milestone66.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1497682 - Part 3. Add junit test. r=droeh Summary: Add autofill hint test if using Android 8+. Depends on D12881 Reviewers: droeh Reviewed By: droeh Bug #: 1497682 Differential Revision: https://phabricator.services.mozilla.com/D12882
mobile/android/geckoview/src/androidTest/assets/www/forms2.html
mobile/android/geckoview/src/androidTest/java/org/mozilla/geckoview/test/BaseSessionTest.kt
mobile/android/geckoview/src/androidTest/java/org/mozilla/geckoview/test/ContentDelegateTest.kt
new file mode 100644
--- /dev/null
+++ b/mobile/android/geckoview/src/androidTest/assets/www/forms2.html
@@ -0,0 +1,19 @@
+<html>
+    <head><title>Forms2</title></head>
+    <body>
+        <form>
+            <input type="text" id="firstname">
+            <input type="text" id="lastname">
+            <input type="text" id="user1" value="foo">
+            <input type="password" id="pass1" value="foo">
+        </form>
+        <iframe id="iframe"></iframe>
+    <script>
+        addEventListener("load", function(e) {
+            if (window.parent === window) {
+                document.getElementById("iframe").contentWindow.location.href = window.location.href;
+            }
+        });
+    </script>
+    </body>
+</html>
--- a/mobile/android/geckoview/src/androidTest/java/org/mozilla/geckoview/test/BaseSessionTest.kt
+++ b/mobile/android/geckoview/src/androidTest/java/org/mozilla/geckoview/test/BaseSessionTest.kt
@@ -24,16 +24,17 @@ import kotlin.reflect.KClass
  * providing the test rule and other utilities.
  */
 open class BaseSessionTest(noErrorCollector: Boolean = false) {
     companion object {
         const val CLICK_TO_RELOAD_HTML_PATH = "/assets/www/clickToReload.html"
         const val CONTENT_CRASH_URL = "about:crashcontent"
         const val DOWNLOAD_HTML_PATH = "/assets/www/download.html"
         const val FORMS_HTML_PATH = "/assets/www/forms.html"
+        const val FORMS2_HTML_PATH = "/assets/www/forms2.html"
         const val HELLO_HTML_PATH = "/assets/www/hello.html"
         const val HELLO2_HTML_PATH = "/assets/www/hello2.html"
         const val INPUTS_PATH = "/assets/www/inputs.html"
         const val INVALID_URI = "not a valid uri"
         const val LINKS_HTML_PATH = "/assets/www/links.html"
         const val LOREM_IPSUM_HTML_PATH = "/assets/www/loremIpsum.html"
         const val NEW_SESSION_CHILD_HTML_PATH = "/assets/www/newSession_child.html"
         const val NEW_SESSION_HTML_PATH = "/assets/www/newSession.html"
--- a/mobile/android/geckoview/src/androidTest/java/org/mozilla/geckoview/test/ContentDelegateTest.kt
+++ b/mobile/android/geckoview/src/androidTest/java/org/mozilla/geckoview/test/ContentDelegateTest.kt
@@ -330,16 +330,19 @@ class ContentDelegateTest : BaseSessionT
                         when (child.inputType) {
                             InputType.TYPE_CLASS_TEXT or
                                     InputType.TYPE_TEXT_VARIATION_WEB_PASSWORD ->
                                 arrayOf(View.AUTOFILL_HINT_PASSWORD)
                             InputType.TYPE_CLASS_TEXT or
                                     InputType.TYPE_TEXT_VARIATION_WEB_EMAIL_ADDRESS ->
                                 arrayOf(View.AUTOFILL_HINT_EMAIL_ADDRESS)
                             InputType.TYPE_CLASS_PHONE -> arrayOf(View.AUTOFILL_HINT_PHONE)
+                            InputType.TYPE_CLASS_TEXT or
+                                    InputType.TYPE_TEXT_VARIATION_WEB_EDIT_TEXT ->
+                                arrayOf(View.AUTOFILL_HINT_USERNAME)
                             else -> null
                         }))
 
                 autoFillValues.append(child.id, when (child.inputType) {
                     InputType.TYPE_CLASS_TEXT or InputType.TYPE_TEXT_VARIATION_WEB_PASSWORD -> "baz"
                     InputType.TYPE_CLASS_TEXT or InputType.TYPE_TEXT_VARIATION_WEB_EMAIL_ADDRESS -> "a@b.c"
                     InputType.TYPE_CLASS_NUMBER -> "24"
                     InputType.TYPE_CLASS_PHONE -> "42"
@@ -450,16 +453,81 @@ class ContentDelegateTest : BaseSessionT
                            equalTo(GeckoSession.TextInputDelegate.AUTO_FILL_NOTIFY_VIEW_EXITED))
                 assertThat("ID should be valid", virtualId, not(equalTo(View.NO_ID)))
             }
         })
         assertThat("Should not have focused field",
                    countAutoFillNodes({ it.isFocused }), equalTo(0))
     }
 
+    @WithDevToolsAPI
+    @Test fun autofill_userpass() {
+        if (Build.VERSION.SDK_INT < 26) {
+            return
+        }
+
+        mainSession.loadTestPath(FORMS2_HTML_PATH)
+        // Wait for the auto-fill nodes to populate.
+        sessionRule.waitUntilCalled(object : Callbacks.TextInputDelegate {
+            @AssertCalled(count = 2)
+            override fun notifyAutoFill(session: GeckoSession, notification: Int, virtualId: Int) {
+            }
+        })
+
+        mainSession.evaluateJS("$('#pass1').focus()")
+        sessionRule.waitUntilCalled(object : Callbacks.TextInputDelegate {
+            @AssertCalled(count = 1)
+            override fun notifyAutoFill(session: GeckoSession, notification: Int, virtualId: Int) {
+            }
+        })
+
+        val rootNode = ViewNode.newInstance()
+        val rootStructure = ViewNodeBuilder.newInstance(AssistStructure(), rootNode,
+                /* async */ false) as ViewStructure
+
+        // Perform auto-fill and return number of auto-fills performed.
+        fun checkAutoFillChild(child: AssistStructure.ViewNode): Int {
+            var sum = 0
+            // Seal the node info instance so we can perform actions on it.
+            if (child.childCount > 0) {
+                for (i in 0 until child.childCount) {
+                    sum += checkAutoFillChild(child.getChildAt(i))
+                }
+            }
+
+            if (child === rootNode) {
+                return sum
+            }
+
+            assertThat("ID should be valid", child.id, not(equalTo(View.NO_ID)))
+
+            if (EditText::class.java.name == child.className) {
+                val htmlInfo = child.htmlInfo
+                assertThat("Should have HTML tag", htmlInfo.tag, equalTo("input"))
+
+                if (child.autofillHints == null) {
+                    return sum
+                }
+                child.autofillHints.forEach {
+                    when (it) {
+                        View.AUTOFILL_HINT_USERNAME, View.AUTOFILL_HINT_PASSWORD -> {
+                            sum++
+                        }
+                    }
+                }
+            }
+            return sum
+        }
+
+        mainSession.textInput.onProvideAutofillVirtualStructure(rootStructure, 0)
+        // form and iframe have each 2 hints.
+        assertThat("autofill hint count",
+                   checkAutoFillChild(rootNode), equalTo(4))
+    }
+
     private fun goFullscreen() {
         sessionRule.setPrefsUntilTestEnd(mapOf("full-screen-api.allow-trusted-requests-only" to false))
         mainSession.loadTestPath(FULLSCREEN_PATH)
         mainSession.waitForPageStop()
         mainSession.evaluateJS("$('#fullscreen').requestFullscreen()")
         sessionRule.waitUntilCalled(object : Callbacks.ContentDelegate {
             override  fun onFullScreen(session: GeckoSession, fullScreen: Boolean) {
                 assertThat("Div went fullscreen", fullScreen, equalTo(true))