Skip to content

dlenroc/appium-roku-driver

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

99 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Appium Roku Driver · NPM Version Node.js Version Node.js CI

Roku Driver is a WebDriver that allows testing channels and screensavers using any WebDriver client.

Prerequisites

Installation

appium driver install --source npm @dlenroc/appium-roku-driver

Documentation

Thanks to the Appium and WebDriver protocols, this driver works just like other WebDriver implementations, but there are a couple of things worth mentioning.

Initialization

Like other drivers, Roku Driver uses the fast reset algorithm by default: registries are cleared before each test, and a full reinstallation occurs only if the channel differs from the one already installed.

Locators

The following locator strategies are supported: tag name, link text, partial link text, css selector, and xpath.

Contexts

  • ECP (default) External Control Protocol is a context that finds elements quickly but does not expose many attributes.

  • ODC (WIP) On-Device Component is a context that finds elements more slowly but exposes all attributes. It can be tuned using the elementResponseAttributes setting.

Deep linking

  • input - Sends a custom event to the launched channel.

    driver.url('roku://input?<key>=<value>');
  • launch - Launches given channel with specific arguments.

    driver.url('roku://launch/:channel_id?<key>=<value>');

Channels

In Roku, appId is dev for a sideloaded channel or a number for channels installed from the store (e.g., 12 for Netflix).

driver.queryAppState('dev');
driver.queryAppState('12');

Note: most commands only work with SceneGraph-based sideloaded channels.

Screensaver / Screensaver Settings

This driver allows testing of screensavers via the appium:entryPoint capability.

  • channel (default) - Opens channel itself.
  • screensaver - Opens your channel screen saver.
  • screensaver-settings - Opens your channel screen saver settings.

Note: Usually screensavers open on their own and close immediately after any user input is sent, but when entryPoint screensaver is used, it runs in the context of the channel, so the input interaction does not close it (BACK and HOME buttons are an exception).

Registries / Arguments

In Roku world:

Knowing this, you can significantly speed up automation by skipping authorization and configuration steps where appropriate.

Note: appium:arguments and appium:registry will contain different values in your case.

const capabilities = {
  ...commonCapabilities,

  // Launch parameters
  'appium:arguments': {
    contentId: 1234,
    mediaType: 'movie',
  },

  // Registry sections Settings
  'appium:registry': {
    account: {
      token: '<user_token>',
    },
  },
};

BrightScript Logging

// Forward logs to the console
driver.on('log.entryAdded', (entry) => console.log(entry.text));

// Subscribe to BrightScript logs
await driver.sessionSubscribe({ events: ['log.entryAdded'] });

// Unsubscribe from BrightScript logs (optional)
await driver.sessionUnsubscribe({ events: ['log.entryAdded'] });

Actions

The following action types are supported:

  • keyDown, keyUp - presses/releases the given key.
  • pointerMove - focuses the element using arrow buttons.
  • pause - waits a given number of milliseconds.

Below are key codes and their equivalents on a Roku remote.

Code Keyboard Key Roku Key
\uE002 Help Info
\ue003 Backspace Backspace
\ue006 Return Enter
\ue007 Enter Select
\ue00b Pause Play
\uE00C Escape Back
\uE00E Page Up ChannelUp
\uE00F Page Down ChannelDown
\ue011 Home Home
\ue012 Arrow Left Left
\ue013 Arrow Up Up
\ue014 Arrow Right Right
\ue015 Arrow Down Down
\uE01A 0 InputAV1
\uE01B 1 InputHDMI1
\uE01C 2 InputHDMI2
\uE01D 3 InputHDMI3
\uE01E 4 InputHDMI4
\uE01F 5 InputTuner
\uE036 F6 InstantReplay
\uE037 F7 Rev
\uE038 F8 Play
\uE039 F9 Fwd
\uE03A F10 VolumeMute
\uE03B F11 VolumeDown
\uE03C F12 VolumeUp

Capabilities

If adding a vendor prefix is a problem, @appium/relaxed-caps-plugin can be used to get rid of them.

Roku Capabilities

Capability Required Type Description
appium:ip + string The IP address of the target device
appium:password + string Password for the development environment
appium:username - string Username for the development environment
appium:context - string Sets the context to be used, default ECP
appium:registry - object Pre-fills the registry with the specified sections/keys
appium:arguments - object Parameters to be passed to the main method
appium:entryPoint - string Specifies the channel entry point, possible values are channel, screensaver, screensaver-settings

Appium Capabilities

Capability Required Type Description
platformName + string Must be roku
appium:automationName + string Must be roku
appium:deviceName +/- string Helps webdriver clients understand that they are dealing with appium
webSocketUrl - boolean Opt in to the use of the Bidi protocol. Defaults to false.
appium:app - string The absolute local path or remote http URL to channel
appium:noReset - boolean Do not stop app, do not clear app data, and do not uninstall app
appium:printPageSourceOnFindFailure - boolean When a find operation fails, print the current page source. Defaults to false
appium:newCommandTimeout - number How long (in seconds) Appium will wait for a new command from the client before assuming the client quit and ending the session
appium:settings[<key>] - any Update driver settings on session creation
appium:shouldTerminateApp - boolean If true, the channel will be closed after the session is finished. Defaults to false

Settings

Name Type Description
elementResponseAttributes string Comma-separated list of element attribute names that will be available in page source and related actions

Supported Commands

The supported commands are listed in the sections below but note that they may have a different name in the client you are using

Example: calling the setContext command

// Java
driver.context('ECP');

// WebdriverIO
driver.switchContext('ECP');

WebDriver Commands

Command Description
createSession Create a new session
deleteSession End the running session
setUrl Open a deep link
active Get the currently focused element
findElement Search for an element
findElements Search for multiple elements
findElementFromElement Search for an element in parent element
findElementsFromElement Search multiple elements in parent element
getAttribute Get the value of an attribute from a given element
getProperty Get the value of a property from a given element
  • isFocused - returns true if the element is focused.
  • isInFocusChain - returns true if the element or any of its descendants are focused
  • isInFocusHierarchy - returns true if the element or any of its ancestors or descendants is focused
getText Get the visible text of a given element
getName Get the tag name of given element
getElementRect Get the position and size of the given element
elementDisplayed Check if the element is displayed
click Presses the Select button on given element
clear Clears the content of the given element
setValue Send a sequence of keystrokes to an element
getPageSource Get the XML representation of the current UI
execute Execute a Roku command
performActions Performs a chain of actions
releaseActions Release pressed key
getScreenshot Take a screenshot

Appium Commands

Command Description
installApp Install the channel if it is not installed
activateApp Launch the given channel
terminateApp Terminate the channel (Available since Roku OS 13.0)
removeApp Remove the given channel from the device
isAppInstalled Checks if a channel is installed
queryAppState Queries the channel state
pushFile Push a file to the device
pullFile Pull a file from the device
pullFolder Pull a folder from the device
updateSettings Updates current test session settings
getCurrentContext Get the name of the current context
setContext Switches to the given context
getContexts Get the names of available contexts

BiDi Commands

Command Description
bidiSubscribe Enables certain events either globally or for a set of contexts
bidiUnsubscribe Disables events either globally or for a set of contexts

Roku Commands

In addition to the standard Appium commands, Roku has several additional features that go beyond the Appium protocol. These are available through a JavaScript executor and a script in the following format: <component>:<command>

The following components are available: ecp, debugServer, developerServer, and odc

Example:

// with args
driver.execute('ecp:launch', [{ appId: 'dev', params: {} }]);

// without args
const playerState = driver.execute('ecp:queryMediaPlayer');
playerState.duration;