Index: mojo/tools/mopy/background_app_group.py |
diff --git a/mojo/tools/mopy/background_app_group.py b/mojo/tools/mopy/background_app_group.py |
deleted file mode 100755 |
index 2e3eae006aed13881d48a707f6b07fa6c35ee317..0000000000000000000000000000000000000000 |
--- a/mojo/tools/mopy/background_app_group.py |
+++ /dev/null |
@@ -1,157 +0,0 @@ |
-#!/usr/bin/env python |
-# Copyright 2014 The Chromium Authors. All rights reserved. |
-# Use of this source code is governed by a BSD-style license that can be |
-# found in the LICENSE file. |
- |
-import logging |
-import os |
-import subprocess |
-import time |
-import sys |
- |
-import mopy.paths |
- |
-from shutil import copyfileobj, rmtree |
-from signal import SIGTERM |
-from tempfile import mkdtemp, TemporaryFile |
- |
- |
-class TimeoutError(Exception): |
- """Allows distinction between timeout failures and generic OSErrors.""" |
- pass |
- |
- |
-def _poll_for_condition( |
- condition, max_seconds=10, sleep_interval=0.1, desc='[unnamed condition]'): |
- """Poll until a condition becomes true. |
- |
- Arguments: |
- condition: callable taking no args and returning bool. |
- max_seconds: maximum number of seconds to wait. |
- Might bail up to sleep_interval seconds early. |
- sleep_interval: number of seconds to sleep between polls. |
- desc: description put in TimeoutError. |
- |
- Returns: |
- The true value that caused the poll loop to terminate. |
- |
- Raises: |
- TimeoutError if condition doesn't become true before max_seconds is reached. |
- """ |
- start_time = time.time() |
- while time.time() + sleep_interval - start_time <= max_seconds: |
- value = condition() |
- if value: |
- return value |
- time.sleep(sleep_interval) |
- |
- raise TimeoutError('Timed out waiting for condition: %s' % desc) |
- |
- |
-class _BackgroundShell(object): |
- """Manages a mojo_shell instance that listens for external applications.""" |
- |
- def __init__(self, mojo_shell_path, shell_args=None): |
- """In a background process, run a shell at mojo_shell_path listening |
- for external apps on an instance-specific socket. |
- |
- Arguments: |
- mojo_shell_path: path to the mojo_shell binary to run. |
- shell_args: a list of arguments to pass to mojo_shell. |
- |
- Raises: |
- a TimeoutError if the shell takes too long to create the socket. |
- """ |
- self._tempdir = mkdtemp(prefix='background_shell_') |
- self._socket_path = os.path.join(self._tempdir, 'socket') |
- self._output_file = TemporaryFile() |
- |
- shell_command = [mojo_shell_path, |
- '--enable-external-applications=' + self._socket_path] |
- if shell_args: |
- shell_command += shell_args |
- logging.getLogger().debug(shell_command) |
- |
- self._shell = subprocess.Popen(shell_command, stdout=self._output_file, |
- stderr=subprocess.STDOUT) |
- _poll_for_condition(lambda: os.path.exists(self._socket_path), |
- desc="External app socket creation.") |
- |
- |
- def __del__(self): |
- if self._shell: |
- self._shell.terminate() |
- self._shell.wait() |
- if self._shell.returncode != -SIGTERM: |
- copyfileobj(self._output_file, sys.stdout) |
- rmtree(self._tempdir) |
- |
- |
- @property |
- def socket_path(self): |
- """The path of the socket where the shell is listening for external apps.""" |
- return self._socket_path |
- |
- |
-class BackgroundAppGroup(object): |
- """Manages a group of mojo apps running in the background.""" |
- |
- def __init__(self, paths, app_urls, shell_args=None): |
- """In a background process, spins up mojo_shell with external |
- applications enabled, passing an optional list of extra arguments. |
- Then, launches apps indicated by app_urls in the background. |
- The apps and shell are automatically torn down upon destruction. |
- |
- Arguments: |
- paths: a mopy.paths.Paths object. |
- app_urls: a list of URLs for apps to run via mojo_launcher. |
- shell_args: a list of arguments to pass to mojo_shell. |
- |
- Raises: |
- a TimeoutError if the shell takes too long to begin running. |
- """ |
- self._shell = _BackgroundShell(paths.mojo_shell_path, shell_args) |
- |
- # Run apps defined by app_urls in the background. |
- self._apps = [] |
- for app_url in app_urls: |
- launch_command = [ |
- paths.mojo_launcher_path, |
- '--shell-path=' + self._shell.socket_path, |
- '--app-url=' + app_url, |
- '--app-path=' + paths.FileFromUrl(app_url), |
- '--vmodule=*/mojo/shell/*=2'] |
- logging.getLogger().debug(launch_command) |
- app_output_file = TemporaryFile() |
- self._apps.append((app_output_file, |
- subprocess.Popen(launch_command, |
- stdout=app_output_file, |
- stderr=subprocess.STDOUT))) |
- |
- |
- def __del__(self): |
- self._StopApps() |
- |
- |
- def __enter__(self): |
- return self |
- |
- |
- def __exit__(self, ex_type, ex_value, traceback): |
- self._StopApps() |
- |
- |
- def _StopApps(self): |
- """Terminate all background apps.""" |
- for output_file, app in self._apps: |
- app.terminate() |
- app.wait() |
- if app.returncode != -SIGTERM: |
- copyfileobj(output_file, sys.stdout) |
- self._apps = [] |
- |
- |
- @property |
- def socket_path(self): |
- """The path of the socket where the shell is listening for external apps.""" |
- return self._shell._socket_path |