Skip to content
Open
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -7,3 +7,5 @@
/build
/captures
.externalNativeBuild
*.log
.idea
8 changes: 8 additions & 0 deletions README.md

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Small cosmetic change for both statements, please modify as given below:

  • To integrate BrowserStack Test Reporting & Analytics with Espresso, refer to our documentation
  • To integrate BrowserStack Accessibility to functional tests and generate comprehensive reports of accessibility issues, refer to our documentation

Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,14 @@
* Build the test application: `./gradlew assembleAndroidTest` (apk will be generated in the `app/build/outputs/apk/androidTest/debug/` directory)
* Upload both the apk files to BrowserStack and start a session. Refer our documentation for details: [Using Espresso with BrowserStack](https://www.browserstack.com/app-automate/espresso/get-started)

### Test Reporting & Analytics

* to integrate BrowserStack Test Reporting & Analytics with Espresso refer our documentation: [Test Reporting & Analytics on Espresso](https://www.browserstack.com/docs/test-reporting-and-analytics/quick-start/espresso)

### App Accessibility Testing

* To add accessibility checks to functional tests and generate comprehensive reports of accessibility issues refer our documentation: [Integrate Espresso test suite with app accessibility testing](https://www.browserstack.com/docs/app-accessibility/automated-tests/get-started/espresso/integrate-with-app-automate)

## Notes
* You can view your test results on the [BrowserStack app-automate dashboard](https://www.browserstack.com/app-automate)

Expand Down
69 changes: 43 additions & 26 deletions app/build.gradle
Original file line number Diff line number Diff line change
@@ -1,47 +1,64 @@
apply plugin: 'com.android.application'
apply plugin: 'jacoco'
jacoco {
toolVersion='0.7.5.201505241946'
}
buildscript {
repositories {
mavenCentral()
}
plugins {
alias(libs.plugins.android.application)
id 'com.browserstack.gradle-tool'
id 'jacoco'
}

android {
compileSdkVersion 30
dataBinding.enabled = true
namespace 'com.sample.browserstack.samplecalculator'
compileSdk 34

defaultConfig {
applicationId "com.sample.browserstack.samplecalculator"
minSdkVersion 15
targetSdkVersion 30
minSdk 26
targetSdk 34
versionCode 1
versionName "1.0"
testInstrumentationRunner 'androidx.test.runner.AndroidJUnitRunner'

testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}

buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
debug {
testCoverageEnabled true
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}

compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}

dataBinding {
enabled = true
}
}

dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation 'androidx.appcompat:appcompat:1.0.0'
implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.1.0'
androidTestImplementation 'androidx.test:rules:1.1.1'
androidTestImplementation 'androidx.test.ext:junit:1.1.1'
testImplementation 'junit:junit:4.12'
}
implementation libs.appcompat
implementation libs.material
implementation libs.activity
implementation libs.constraintlayout
testImplementation libs.junit
androidTestImplementation libs.ext.junit
androidTestImplementation libs.espresso.core

androidTestImplementation(group: 'com.browserstack', name: 'browserstack-java-sdk', version: 'latest.release') {
exclude group: 'com.google.code.findbugs', module: 'jsr305'
}

configurations.androidTestImplementation {
exclude group: 'com.google.code.findbugs', module: 'jsr305'
}
}

jacoco {
toolVersion = '0.8.8'
}

task printSdkVersion {
doLast {
println android.compileSdkVersion
}
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package com.sample.browserstack.samplecalculator;

import androidx.test.filters.SmallTest;
import androidx.test.rule.ActivityTestRule;
import androidx.test.ext.junit.rules.ActivityScenarioRule;
import androidx.test.ext.junit.runners.AndroidJUnit4;

import org.junit.Before;
Expand All @@ -25,14 +25,13 @@
public class EnsureInputTests {

@Rule
public ActivityTestRule<MainActivity> activityRule =
new ActivityTestRule<MainActivity>(MainActivity.class);

private MainActivity mainActivity;
public ActivityScenarioRule<MainActivity> activityScenarioRule =
new ActivityScenarioRule<>(MainActivity.class);

@Before
public void setUp() {
mainActivity = activityRule.getActivity();
// ActivityScenarioRule handles activity initialization automatically
// No need to manually get activity reference in modern testing
}

@Test
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package com.sample.browserstack.samplecalculator;

import androidx.test.filters.MediumTest;
import androidx.test.rule.ActivityTestRule;
import androidx.test.ext.junit.rules.ActivityScenarioRule;
import androidx.test.ext.junit.runners.AndroidJUnit4;

import org.junit.Before;
Expand All @@ -25,14 +25,13 @@
public class EnsureOperationTests {

@Rule
public ActivityTestRule<MainActivity> activityRule =
new ActivityTestRule<MainActivity>(MainActivity.class);

private MainActivity mainActivity;
public ActivityScenarioRule<MainActivity> activityScenarioRule =
new ActivityScenarioRule<>(MainActivity.class);

@Before
public void setUp() {
mainActivity = activityRule.getActivity();
// ActivityScenarioRule handles activity initialization automatically
// No need to manually get activity reference in modern testing
}

@Test
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package com.sample.browserstack.samplecalculator;

import androidx.test.filters.MediumTest;
import androidx.test.rule.ActivityTestRule;
import androidx.test.ext.junit.rules.ActivityScenarioRule;
import androidx.test.ext.junit.runners.AndroidJUnit4;

import org.junit.Rule;
Expand All @@ -26,8 +26,8 @@
public class EnsureRandomTests {

@Rule
public ActivityTestRule<MainActivity> activityRule =
new ActivityTestRule<MainActivity>(MainActivity.class);
public ActivityScenarioRule<MainActivity> activityScenarioRule =
new ActivityScenarioRule<>(MainActivity.class);

@Test
public void testZeroMultiplication() {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,13 +1,25 @@
package com.sample.browserstack.samplecalculator;

import android.content.Context;
import androidx.test.platform.app.InstrumentationRegistry;
import static androidx.test.espresso.action.ViewActions.click;
import static androidx.test.espresso.action.ViewActions.replaceText;
import static androidx.test.espresso.matcher.ViewMatchers.withId;

import android.util.Log;

import androidx.test.espresso.Espresso;
import androidx.test.ext.junit.rules.ActivityScenarioRule;
import androidx.test.ext.junit.runners.AndroidJUnit4;

import org.junit.Assert;
import org.junit.Assume;
import org.junit.Before;
import org.junit.Ignore;
import org.junit.Rule;
import org.junit.Test;
import org.junit.experimental.categories.Category;
import org.junit.runner.RunWith;

import static org.junit.Assert.*;
import com.browserstack.accessibility.AccessibilityUtils;

/**
* Instrumented test, which will execute on an Android device.
Expand All @@ -16,10 +28,89 @@
*/
@RunWith(AndroidJUnit4.class)
public class ExampleInstrumentedTest {
@Rule
public ActivityScenarioRule<MainActivity> activityScenarioRule =
new ActivityScenarioRule<>(MainActivity.class);

@Before
public void myBeforeEach() throws Exception{
Log.d("TRANSFORMATION_LOGS", "From @Before");
}

@Test
public void testCalculatorBasicOperation() {
android.util.Log.d("TRANSFORMATION_LOGS", "IN TEST");
Espresso.onView(withId(R.id.buttonTwo)).perform(click());
Espresso.onView(withId(R.id.buttonAdd)).perform(click());
Espresso.onView(withId(R.id.buttonThree)).perform(click());
Espresso.onView(withId(R.id.buttonEqual)).perform(click());
}

@Test
public void exceptionFailedTest() throws Exception {
Espresso.onView(withId(R.id.buttonFive)).perform(click());
Espresso.onView(withId(R.id.buttonMultiply)).perform(click());
Espresso.onView(withId(R.id.buttonTwo)).perform(click());
Espresso.onView(withId(R.id.buttonEqual)).perform(click());
throw new Exception("EXCEPTION FROM TEST");
}

@Test
@Category(ExampleInstrumentedTest.class)
public void assertionFailedTest() throws Exception {
Log.d("TEST_LOGS", "testStarted");

Espresso.onView(withId(R.id.buttonOne)).perform(click());
Espresso.onView(withId(R.id.buttonAdd)).perform(click());
Espresso.onView(withId(R.id.buttonOne)).perform(click());
Espresso.onView(withId(R.id.buttonEqual)).perform(click());

Log.d("PERFORM_SCAN_LOGS", "beforeScan");
AccessibilityUtils.performEspressoAppAccessibilityScan("");
Log.d("PERFORM_SCAN_LOGS", "afterScan");

Thread.sleep(10000);

Log.d("A11Y_RESULTS_SUMMARY", AccessibilityUtils.getResultsSummary().toString());
Log.d("A11Y_RESULTS", AccessibilityUtils.getResults().toString());

Assert.assertTrue(false);
Thread.sleep(2000);

Log.d("TEST_LOGS", "testEnded");
}

@Test
@Category(MainActivity.class)
public void testTags() throws InterruptedException{
Log.d("TEST_LOGS", "testStarted");

Assert.assertTrue(true);
Thread.sleep(10000);

Log.d("A11Y_RESULTS_SUMMARY", AccessibilityUtils.getResultsSummary().toString());
Log.d("A11Y_RESULTS", AccessibilityUtils.getResults().toString());

Log.d("TEST_LOGS", "testEnded");
}

@Test
@Ignore
public void testIgnored() throws InterruptedException {
Log.d("TRANSFORMATION_LOGS", "testIgnored");
Thread.sleep(2000);
}

@Test
@Ignore("IGNORE MESSAGE")
public void testIgnoredWithMessage() throws InterruptedException {
Log.d("TRANSFORMATION_LOGS", "testIgnoredWithMessage");
Thread.sleep(2000);
}

@Test
public void useAppContext() {
// Context of the app under test.
Context appContext = InstrumentationRegistry.getInstrumentation().getTargetContext();
assertEquals("com.sample.browserstack.samplecalculator", appContext.getPackageName());
public void testAssumptionFailure() throws InterruptedException {
Assume.assumeTrue(false);
Thread.sleep(2000);
}
}
15 changes: 11 additions & 4 deletions app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
@@ -1,16 +1,23 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.sample.browserstack.samplecalculator">
xmlns:tools="http://schemas.android.com/tools">

<uses-permission android:name="android.permission.INTERNET"/>

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<application
android:usesCleartextTraffic="true"
android:allowBackup="true"
android:dataExtractionRules="@xml/data_extraction_rules"
android:fullBackupContent="@xml/backup_rules"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity android:name=".MainActivity">
android:theme="@style/AppTheme"
tools:targetApi="31">
<activity
android:name=".MainActivity"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />

Expand Down
12 changes: 12 additions & 0 deletions app/src/main/res/xml/backup_rules.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<?xml version="1.0" encoding="utf-8"?><!--
Sample backup rules file; uncomment and customize as necessary.
See https://developer.android.com/guide/topics/data/autobackup
for details.
Note: This file is ignored for devices older that API 23 even if they contain android:fullBackupContent="true".
-->
<full-backup-content>
<!-- TODO: Use <include> and <exclude> to control what is backed up.
<include domain=["file" | "database" | "sharedpref" | "external" | "root"] path="string" />
<exclude domain=["file" | "database" | "sharedpref" | "external" | "root"] path="string" />
-->
</full-backup-content>
19 changes: 19 additions & 0 deletions app/src/main/res/xml/data_extraction_rules.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<?xml version="1.0" encoding="utf-8"?><!--
Sample data extraction rules file; uncomment and customize as necessary.
See https://developer.android.com/about/versions/12/backup-restore#xml-changes
for details.
-->
<data-extraction-rules>
<cloud-backup>
<!-- TODO: Use <include> and <exclude> to control what is backed up.
<include .../>
<exclude .../>
-->
</cloud-backup>
<!--
<device-transfer>
<include .../>
<exclude .../>
</device-transfer>
-->
</data-extraction-rules>
14 changes: 4 additions & 10 deletions build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -7,19 +7,13 @@ buildscript {
jcenter()
}
dependencies {
classpath 'com.android.tools.build:gradle:3.4.1'
classpath 'com.android.tools.build:gradle:8.5.0'
// NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files
classpath 'com.browserstack:gradle-tool:1.1.0'
}
}

allprojects {
repositories {
google()
jcenter()
}
}

task clean(type: Delete) {
delete rootProject.buildDir
plugins {
alias(libs.plugins.android.application) apply false
}
Loading