Espresso-Web היא נקודת כניסה לעבודה עם רכיבי ממשק משתמש של Android WebView. Espresso-Web משתמש מחדש ב-Atoms מ-WebDriver API הפופולרי כדי לבדוק את ההתנהגות של WebView ולשלוט בה.
מתי כדאי להשתמש ב-Espresso-Web
כדאי להשתמש ב-Espresso-Web כדי לבדוק את האפליקציות ההיברידיות, במיוחד את השילוב של רכיבי ממשק המשתמש המקוריים של האפליקציה עם רכיבי ממשק המשתמש שלה.WebView
אפשר להשתמש ב-Espresso-Web API בשילוב עם ממשקי API אחרים של Espresso כדי ליצור אינטראקציה מלאה עם רכיבי אינטרנט בתוך אובייקטים של WebView
.
אם אתם צריכים לבדוק רק את WebView
עצמו, ולא את האינטראקציות בין WebView
לבין רכיבים מקוריים באפליקציה, כדאי לכתוב בדיקת אינטרנט כללית באמצעות מסגרת כמו WebDriver. אם משתמשים במסגרת לבדיקת אתרים, לא צריך להשתמש במכשיר Android או במכונה וירטואלית של Java, ולכן הבדיקות יפעלו מהר יותר ובאופן מהימן יותר. עם זאת, Espresso-Web מאפשר לכם לעשות שימוש חוזר באטומי WebDriver מותאמים אישית, מה שמעניק לכם גמישות רבה, במיוחד כשכותבים בדיקות שמתכננים להריץ גם באפליקציות אינטרנט עצמאיות וגם באפליקציות שכוללות ממשק משתמש של Android.
איך זה עובד
בדומה לשיטה onData()
של Espresso, אינטראקציה מסוג WebView
מורכבת מכמה אטומים.
אינטראקציות WebView
משתמשות בשילוב של שפת התכנות Java וגשר JavaScript כדי לבצע את העבודה. מכיוון שאין סיכוי להיווצרות מצבי מירוץ בחשיפת נתונים מסביבת JavaScript – כל מה ש-Espresso רואה בצד שמבוסס על Java הוא עותק מבודד – יש תמיכה מלאה בהחזרת נתונים מאובייקטים של Web.WebInteraction
, כך שאפשר לאמת את כל הנתונים שמוחזרים מבקשה.
מה זה WebDriver Atom?
מסגרת WebDriver משתמשת ב-Atoms כדי למצוא ולשנות רכיבי אינטרנט באופן פרוגרמטי. WebDriver משתמש ב-Atoms כדי לאפשר שינוי בדפדפן. מבחינה רעיונית, Atom דומה ל-ViewAction
, יחידה עצמאית שמבצעת פעולה בממשק המשתמש. אתם חושפים את ה-Atoms באמצעות רשימה של שיטות מוגדרות, כמו findElement()
ו-getElement()
, כדי להפעיל את הדפדפן מנקודת המבט של המשתמש. עם זאת, אם משתמשים ישירות ב-framework של WebDriver, צריך לתזמן את ה-Atoms בצורה נכונה, וזה דורש לוגיקה מפורטת למדי.
ב-Espresso, המחלקות Web
ו-Web.WebInteraction
עוטפות את הקוד הסטנדרטי הזה ויוצרות אינטראקציה עם אובייקטים של WebView שדומה ל-Espresso. לכן, בהקשר של WebView
, נעשה שימוש ב-Atoms כתחליף ל-Espresso ViewMatchers
וViewActions
.
ה-API נראה פשוט למדי:
Kotlin
onWebView() .withElement(Atom) .perform(Atom) .check(WebAssertion)
Java
onWebView() .withElement(Atom) .perform(Atom) .check(WebAssertion);
מידע נוסף זמין במסמכי התיעוד של Selenium בנושא Atoms.
הטמעה של WebView
כדי להשתמש ב-WebView
בבדיקות של האפליקציה, צריך לפעול לפי ההנחיות שמפורטות בקטעים הבאים.
חבילות
כדי לכלול את Espresso-Web בפרויקט, מבצעים את השלבים הבאים:
- פותחים את קובץ
build.gradle
של האפליקציה. בדרך כלל זה לא קובץbuild.gradle
ברמה העליונה, אלא קובץapp/build.gradle
. מוסיפים את השורה הבאה בתוך dependencies:
גרוב
androidTestImplementation 'androidx.test.espresso:espresso-web:3.6.1'
Kotlin
androidTestImplementation('androidx.test.espresso:espresso-web:3.6.1')
Espresso-Web תואם רק ל-Espresso 2.2 ואילך ולגרסה 0.3 ואילך של ספריית הבדיקות, לכן חשוב לעדכן גם את השורות האלה:
גרוב
androidTestImplementation 'androidx.test:runner:1.6.1' androidTestImplementation 'androidx.test:rules:1.6.1' androidTestImplementation 'androidx.test.espresso:espresso-core:3.6.1'
Kotlin
androidTestImplementation('androidx.test:runner:1.6.1') androidTestImplementation('androidx.test:rules:1.6.1') androidTestImplementation('androidx.test.espresso:espresso-core:3.6.1')
שימוש נפוץ ב-API
השיטה onWebView()
היא נקודת הכניסה העיקרית כשעובדים עם WebView ב-Android באמצעות
Espresso. משתמשים בשיטה הזו כדי לבצע בדיקות Espresso-Web, כמו הבדיקות הבאות:
Kotlin
onWebView() .withElement(findElement(Locator.ID, "link_2")) // similar to onView(withId(...)) .perform(webClick()) // Similar to perform(click()) // Similar to check(matches(...)) .check(webMatches(getCurrentUrl(), containsString("navigation_2.html")))
Java
onWebView() .withElement(findElement(Locator.ID, "link_2")) // similar to onView(withId(...)) .perform(webClick()) // Similar to perform(click()) // Similar to check(matches(...)) .check(webMatches(getCurrentUrl(), containsString("navigation_2.html")));
בדוגמה הזו, Espresso-Web מאתר רכיב DOM שהמזהה שלו הוא "link_2"
ולוחץ עליו. הכלי מאמת שה-WebView שולח בקשת GET שמכילה את המחרוזת "navigation_2.html"
.
תמיכה ב-JavaScript
כשמריצים את הבדיקות, המערכת מבצעת את כל האינטראקציות עם WebView באמצעות JavaScript. לכן, כדי לתמוך בהערכת JavaScript, צריך להפעיל JavaScript ב-WebView שנבדק.
אפשר להפעיל את JavaScript בכוח על ידי קריאה ל-forceJavascriptEnabled()
כפעולה בפעילות שנבדקת, כמו בקטע הקוד הבא.
@RunWith(AndroidJUnit4::class) class MyTestSuite { @get:Rule val activityScenarioRule = activityScenarioRule<MyWebViewActivity>() @Test fun testWebViewInteraction() { onWebView().forceJavascriptEnabled() } }
אינטראקציות נפוצות באתר
אלה הפעולות הנפוצות עם אובייקטים של Web.WebInteraction
:
-
withElement()
מפנה לרכיב DOM ב-WebView.דוגמה:
Kotlin
onWebView().withElement(findElement(Locator.ID, "teacher"))
Java
onWebView().withElement(findElement(Locator.ID, "teacher"));
-
withContextualElement()
מפנה לרכיב DOM בהיקף מסוים בתוך WebView, ביחס לרכיב DOM אחר. קודם צריך לקרוא ל-withElement()
כדי ליצור את אובייקט ההפניהWeb.WebInteraction
(רכיב DOM).דוגמה:
Kotlin
.withElement(findElement(Locator.ID, "teacher")) .withContextualElement(findElement(Locator.ID, "person_name"))
Java
.withElement(findElement(Locator.ID, "teacher")) .withContextualElement(findElement(Locator.ID, "person_name"));
-
check()
בודקת תנאי ומוודאת שהוא שווה ל-true
.דוגמה:
Kotlin
onWebView() .withElement(findElement(Locator.ID, "teacher")) .withContextualElement(findElement(Locator.ID, "person_name")) .check(webMatches(getText(), containsString("Socrates")))
Java
onWebView() .withElement(findElement(Locator.ID, "teacher")) .withContextualElement(findElement(Locator.ID, "person_name")) .check(webMatches(getText(), containsString("Socrates")));
-
perform()
מבצע פעולה ב-WebView, כמו לחיצה על רכיב.דוגמה:
Kotlin
onWebView() .withElement(findElement(Locator.ID, "teacher")) .perform(webClick())
Java
onWebView() .withElement(findElement(Locator.ID, "teacher")) .perform(webClick());
-
reset()
מחזירה את WebView למצב ההתחלתי שלה. המאפיין הזה נחוץ כשפעולה קודמת, כמו לחיצה, גורמת לשינוי בניווט שמונע גישה לאובייקטים ElementReference ו-WindowReference.הערה: השימוש בפונקציה
reset()
מועיל כשמבצעים בדיקות של תהליכי עבודה בכמה דפים, כמו שליחת טפסים, אבל בדרך כלל מומלץ להגביל את היקף הבדיקות ולהתמקד בדף אחד.דוגמה:
Kotlin
onWebView() .withElement(...) .perform(...) .reset()
Java
onWebView() .withElement(...) .perform(...) .reset();
דוגמה
בדוגמה הבאה נבדק אם אחרי שמזינים טקסט ב-WebView ולוחצים על הלחצן Submit (שליחה), אותו טקסט מופיע ברכיב אחר באותו WebView:
Kotlin
const val MACCHIATO = "Macchiato" @RunWith(AndroidJUnit4::class) class MyEspressoWebTestSuite { @Test fun typeTextInInput_clickButton_SubmitsForm() { // Create an intent that displays a web form. val webFormIntent = Intent() // ... // Lazily launch the Activity with a custom start Intent per test. ActivityScenario.launchActivity(webFormIntent) // Selects the WebView in your layout. If you have multiple WebView // objects, you can also use a matcher to select a given WebView, // onWebView(withId(R.id.web_view)). onWebView() // Find the input element by ID. .withElement(findElement(Locator.ID, "text_input")) // Clear previous input and enter new text into the input element. .perform(clearElement()) .perform(DriverAtoms.webKeys(MACCHIATO)) // Find the "Submit" button and simulate a click using JavaScript. .withElement(findElement(Locator.ID, "submitBtn")) .perform(webClick()) // Find the response element by ID, and verify that it contains the // entered text. .withElement(findElement(Locator.ID, "response")) .check(webMatches(getText(), containsString(MACCHIATO))) } }
Java
public static final String MACCHIATO = "Macchiato"; @Test public void typeTextInInput_clickButton_SubmitsForm() { // Create an intent that displays a web form. Intent webFormIntent = new Intent(); // ... // Lazily launch the Activity with a custom start Intent per test. ActivityScenario.launchActivity(webFormIntent); // Selects the WebView in your layout. If you have multiple WebView objects, // you can also use a matcher to select a given WebView, // onWebView(withId(R.id.web_view)). onWebView() // Find the input element by ID. .withElement(findElement(Locator.ID, "text_input")) // Clear previous input and enter new text into the input element. .perform(clearElement()) .perform(DriverAtoms.webKeys(MACCHIATO)) // Find the "Submit" button and simulate a click using JavaScript. .withElement(findElement(Locator.ID, "submitBtn")) .perform(webClick()) // Find the response element by ID, and verify that it contains the // entered text. .withElement(findElement(Locator.ID, "response")) .check(webMatches(getText(), containsString(MACCHIATO))); }
מקורות מידע נוספים
מידע נוסף על שימוש ב-Espresso-Web בבדיקות של Android זמין במקורות המידע הבאים.
טעימות
- WebBasicSample:
Use Espresso-Web to interact with
WebView
objects.