Skip to content
Open
Show file tree
Hide file tree
Changes from all 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
5 changes: 5 additions & 0 deletions .changeset/backgrounding-support.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"appwright": patch
---

Add `device.backgroundApp()` to delegate to Appium's `mobile: backgroundApp` command.
25 changes: 25 additions & 0 deletions src/device/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -274,6 +274,31 @@ export class Device {
]);
}

/**
* Sends the currently running app to the background.
*
* @param seconds - Number of seconds to keep app in background.
* Use -1 to background indefinitely (until manually reactivated).
* If positive number, app returns to foreground after specified seconds.
*
* @example
* ```js
* // Background for 10 seconds then auto-return
* await device.backgroundApp(10);
*
* // Background indefinitely (for battery tests)
* await device.backgroundApp(-1);
* await device.pause(30 * 60 * 1000); // Wait 30 minutes
* await device.activateApp(); // Manually bring back
* ```
*/
@boxedStep
async backgroundApp(seconds: number = -1): Promise<void> {
await this.webDriverClient.executeScript("mobile: backgroundApp", [
seconds,
]);
}

/**
* Retrieves text content from the clipboard of the mobile device. This is useful
* after a "copy to clipboard" action has been performed. This returns base64 encoded string.
Expand Down
42 changes: 42 additions & 0 deletions src/tests/device.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
import { describe, test, expect, vi } from "vitest";
//@ts-ignore
import { Client as WebDriverClient } from "webdriver";
import playwrightTest from "@playwright/test";
import { Device } from "../device";

// Override Playwright's test.step/info to work in Vitest environment
// so boxedStep decorator can execute without throwing.
(playwrightTest as unknown as { step: Function }).step = vi.fn(
async (_name: string, body: () => Promise<unknown>) => await body(),
);
(playwrightTest as unknown as { info: () => undefined }).info = () => undefined;

const createDevice = (executeScript = vi.fn()) => {
//@ts-ignore - providing partial WebDriver client for testing
const webDriverClient: WebDriverClient = {
executeScript,
};
const device = new Device(
webDriverClient,
"com.example.app",
{ expectTimeout: 1_000 },
"emulator",
);
return { device, executeScript };
};

describe("Device", () => {
describe("backgroundApp", () => {
test("backgrounds indefinitely by default", async () => {
const { device, executeScript } = createDevice();
await device.backgroundApp();
expect(executeScript).toHaveBeenCalledWith("mobile: backgroundApp", [-1]);
});

test("backgrounds for given duration", async () => {
const { device, executeScript } = createDevice();
await device.backgroundApp(30);
expect(executeScript).toHaveBeenCalledWith("mobile: backgroundApp", [30]);
});
});
});