Revert of [android] Stop using isolate.py for data dependency management. (patchset #9 id:160001 of https://codereview.chromium.org/2492123002/ )
Reason for revert: Breaks the blink bot, e.g. https://build.chromium.org/p/chromium.webkit/builders/WebKit%20Android%20%28Nexus4%29/builds/57103 Original issue's description: > [android] Stop using isolate.py for data dependency management. > > BUG=663110 > > Committed: https://crrev.com/634c87cf4af7ac11f2dbe7687a6d7904c2217ee3 > Cr-Commit-Position: refs/heads/master@{#432940} TBR=agrieve@chromium.org,dpranke@chromium.org NOPRESUBMIT=true NOTREECHECKS=true NOTRY=true BUG=663110 Review-Url: https://codereview.chromium.org/2514453003 Cr-Original-Commit-Position: refs/heads/master@{#433020} Cr-Mirrored-From: https://chromium.googlesource.com/chromium/src Cr-Mirrored-Commit: 67002b0fdaa3123f10f96fa2f7965677d531db74
This commit is contained in:
Родитель
d7507a0fce
Коммит
faaecf8a5e
|
@ -121,6 +121,9 @@ group("test_runner_py") {
|
|||
"//third_party/catapult/devil/devil/devil_dependencies.json",
|
||||
"//third_party/proguard/lib/proguard.jar",
|
||||
]
|
||||
data_deps = [
|
||||
"//tools/swarming_client:isolate_py",
|
||||
]
|
||||
}
|
||||
|
||||
# Create wrapper scripts in out/bin that takes care of setting the
|
||||
|
|
|
@ -62,7 +62,6 @@ def CommonChecks(input_api, output_api):
|
|||
J('pylib', 'local', 'device', 'local_device_test_run_test.py'),
|
||||
J('pylib', 'results', 'json_results_test.py'),
|
||||
J('pylib', 'symbols', 'elf_symbolizer_unittest.py'),
|
||||
J('pylib', 'utils', 'device_dependencies_test.py'),
|
||||
],
|
||||
env=pylib_test_env))
|
||||
|
||||
|
|
|
@ -0,0 +1,120 @@
|
|||
#!/usr/bin/env python
|
||||
# Copyright 2016 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.
|
||||
|
||||
"""Creates an .isolate given a list of files.
|
||||
|
||||
"""
|
||||
|
||||
import argparse
|
||||
import os
|
||||
import pprint
|
||||
import re
|
||||
import sys
|
||||
|
||||
|
||||
_UNIVERSAL_BLACKLIST = (
|
||||
r'.*OWNERS', # Should never be included.
|
||||
)
|
||||
|
||||
_ANDROID_BLACKLIST = (
|
||||
r'.*\.crx', # Chrome extension zip files.
|
||||
r'.*external_extensions\.json', # Chrome external extensions config file.
|
||||
r'.*\.so', # Libraries packed into .apk.
|
||||
r'.*\.mojom\.js', # Some test_support targets include python deps.
|
||||
r'.*Mojo.*manifest\.json', # Some source_set()s pull these in.
|
||||
r'.*jni_generator_tests', # Exists just to test the compile, not to be run.
|
||||
)
|
||||
|
||||
_DEVICE_BLACKLIST = (
|
||||
r'.*\.py', # Some test_support targets include python deps.
|
||||
|
||||
# v8's blobs get packaged into APKs.
|
||||
r'.*natives_blob.*\.bin',
|
||||
r'.*snapshot_blob.*\.bin',
|
||||
)
|
||||
|
||||
_ASSERT_WHITELIST = (
|
||||
r'.*\.pak',
|
||||
r'.*/', # Assume directories are always included on purpose.
|
||||
)
|
||||
|
||||
|
||||
def _IsExecutable(path):
|
||||
return os.path.isfile(path) and os.access(path, os.X_OK)
|
||||
|
||||
|
||||
def _MatchesAny(path, patterns):
|
||||
return any(re.match(p, path) for p in patterns)
|
||||
|
||||
|
||||
def main():
|
||||
parser = argparse.ArgumentParser(description=__doc__)
|
||||
parser.add_argument('--command',
|
||||
help='The command to put in the .isolate (optional)')
|
||||
parser.add_argument('--runtime-deps-file', required=True,
|
||||
help='Input .runtime_deps file.')
|
||||
parser.add_argument('--output-directory', required=True,
|
||||
help='Location of the ninja output directory')
|
||||
parser.add_argument('--out-file', help='Write to file rather than stdout.')
|
||||
parser.add_argument('--apply-android-filters', action='store_true',
|
||||
help='Filter files not required for Android.')
|
||||
parser.add_argument('--apply-device-filters', action='store_true',
|
||||
help='Filter files not required in *.device.isolate.')
|
||||
parser.add_argument('--assert-no-odd-data', action='store_true',
|
||||
help='Fail if any data deps exist (after filtering) '
|
||||
'that are not a part of the _ASSERT_WHITELIST. Use '
|
||||
'this to prevent unexpected runtime_deps from '
|
||||
'creeping in')
|
||||
options = parser.parse_args()
|
||||
|
||||
deps = []
|
||||
with open(options.runtime_deps_file) as deps_file:
|
||||
for path in deps_file:
|
||||
if path.startswith('./'):
|
||||
path = path[2:]
|
||||
deps.append(path.rstrip())
|
||||
|
||||
deps = (d for d in deps if not _MatchesAny(d, _UNIVERSAL_BLACKLIST))
|
||||
|
||||
if options.apply_android_filters:
|
||||
deps = (d for d in deps if not _MatchesAny(d, _ANDROID_BLACKLIST))
|
||||
|
||||
if options.apply_device_filters:
|
||||
deps = (d for d in deps if not _MatchesAny(d, _DEVICE_BLACKLIST))
|
||||
# Breakpad tests have a helper exe, which is packaged in the _dist.
|
||||
deps = (d for d in deps if not _IsExecutable(d))
|
||||
|
||||
# Make them relative to out-file.
|
||||
if options.out_file:
|
||||
subdir = os.path.relpath(options.output_directory,
|
||||
os.path.dirname(options.out_file))
|
||||
deps = (os.path.join(subdir, d) for d in deps)
|
||||
|
||||
deps = sorted(deps)
|
||||
|
||||
if options.assert_no_odd_data:
|
||||
odd_files = [d for d in deps if not _MatchesAny(d, _ASSERT_WHITELIST)]
|
||||
assert not odd_files, ('Found possibly undesired file in runtime_deps: %s' %
|
||||
odd_files)
|
||||
|
||||
isolate_dict = {
|
||||
'variables': {
|
||||
'files': deps,
|
||||
}
|
||||
}
|
||||
if options.command:
|
||||
isolate_dict['variables']['command'] = [options.command]
|
||||
|
||||
isolate_data = pprint.pformat(isolate_dict)
|
||||
if options.out_file:
|
||||
with open(options.out_file, 'w') as f:
|
||||
f.write(isolate_data + '\n')
|
||||
else:
|
||||
print isolate_data
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
sys.exit(main())
|
||||
|
|
@ -62,7 +62,6 @@ def main(args):
|
|||
group.add_argument('--executable-dist-dir')
|
||||
group.add_argument('--isolate-file-path')
|
||||
group.add_argument('--output-directory')
|
||||
group.add_argument('--runtime-deps-path')
|
||||
group.add_argument('--test-apk')
|
||||
group.add_argument('--test-apk-incremental-install-script')
|
||||
group.add_argument('--coverage-dir')
|
||||
|
@ -103,9 +102,6 @@ def main(args):
|
|||
if args.output_directory:
|
||||
test_runner_path_args.append(
|
||||
('--output-directory', RelativizePathToScript(args.output_directory)))
|
||||
if args.runtime_deps_path:
|
||||
test_runner_path_args.append(
|
||||
('--runtime-deps-path', RelativizePathToScript(args.runtime_deps_path)))
|
||||
if args.test_apk:
|
||||
test_runner_path_args.append(
|
||||
('--test-apk', RelativizePathToScript(args.test_apk)))
|
||||
|
|
|
@ -7,17 +7,17 @@ from pylib.instrumentation import instrumentation_test_instance
|
|||
from pylib.junit import junit_test_instance
|
||||
from pylib.monkey import monkey_test_instance
|
||||
from pylib.perf import perf_test_instance
|
||||
from pylib.utils import device_dependencies
|
||||
from pylib.utils import isolator
|
||||
|
||||
|
||||
def CreateTestInstance(args, error_func):
|
||||
|
||||
if args.command == 'gtest':
|
||||
return gtest_test_instance.GtestTestInstance(
|
||||
args, device_dependencies.GetDataDependencies, error_func)
|
||||
args, isolator.Isolator(), error_func)
|
||||
elif args.command == 'instrumentation':
|
||||
return instrumentation_test_instance.InstrumentationTestInstance(
|
||||
args, device_dependencies.GetDataDependencies, error_func)
|
||||
args, isolator.Isolator(), error_func)
|
||||
elif args.command == 'junit':
|
||||
return junit_test_instance.JunitTestInstance(args, error_func)
|
||||
elif args.command == 'monkey':
|
||||
|
|
|
@ -14,6 +14,7 @@ from pylib import constants
|
|||
from pylib.constants import host_paths
|
||||
from pylib.base import base_test_result
|
||||
from pylib.base import test_instance
|
||||
from pylib.utils import isolator
|
||||
|
||||
with host_paths.SysPath(host_paths.BUILD_COMMON_PATH):
|
||||
import unittest_util # pylint: disable=import-error
|
||||
|
@ -229,7 +230,7 @@ def ConvertTestFilterFileIntoGTestFilterArgument(input_lines):
|
|||
|
||||
class GtestTestInstance(test_instance.TestInstance):
|
||||
|
||||
def __init__(self, args, data_deps_delegate, error_func):
|
||||
def __init__(self, args, isolate_delegate, error_func):
|
||||
super(GtestTestInstance, self).__init__()
|
||||
# TODO(jbudorick): Support multiple test suites.
|
||||
if len(args.suite_name) > 1:
|
||||
|
@ -286,10 +287,16 @@ class GtestTestInstance(test_instance.TestInstance):
|
|||
else:
|
||||
self._gtest_filter = None
|
||||
|
||||
self._data_deps_delegate = data_deps_delegate
|
||||
self._runtime_deps_path = args.runtime_deps_path
|
||||
if not self._runtime_deps_path:
|
||||
logging.warning('No data dependencies will be pushed.')
|
||||
if (args.isolate_file_path and
|
||||
not isolator.IsIsolateEmpty(args.isolate_file_path)):
|
||||
self._isolate_abs_path = os.path.abspath(args.isolate_file_path)
|
||||
self._isolate_delegate = isolate_delegate
|
||||
self._isolated_abs_path = os.path.join(
|
||||
constants.GetOutDirectory(), '%s.isolated' % self._suite)
|
||||
else:
|
||||
logging.warning('%s isolate file provided. No data deps will be pushed.',
|
||||
'Empty' if args.isolate_file_path else 'No')
|
||||
self._isolate_delegate = None
|
||||
|
||||
if args.app_data_files:
|
||||
self._app_data_files = args.app_data_files
|
||||
|
@ -386,8 +393,15 @@ class GtestTestInstance(test_instance.TestInstance):
|
|||
#override
|
||||
def SetUp(self):
|
||||
"""Map data dependencies via isolate."""
|
||||
self._data_deps.extend(
|
||||
self._data_deps_delegate(self._runtime_deps_path))
|
||||
if self._isolate_delegate:
|
||||
self._isolate_delegate.Remap(
|
||||
self._isolate_abs_path, self._isolated_abs_path)
|
||||
self._isolate_delegate.PurgeExcluded(_DEPS_EXCLUSION_LIST)
|
||||
self._isolate_delegate.MoveOutputDeps()
|
||||
dest_dir = None
|
||||
self._data_deps.extend([
|
||||
(self._isolate_delegate.isolate_deps_dir, dest_dir)])
|
||||
|
||||
|
||||
def GetDataDependencies(self):
|
||||
"""Returns the test suite's data dependencies.
|
||||
|
@ -441,6 +455,7 @@ class GtestTestInstance(test_instance.TestInstance):
|
|||
|
||||
#override
|
||||
def TearDown(self):
|
||||
"""Do nothing."""
|
||||
pass
|
||||
"""Clear the mappings created by SetUp."""
|
||||
if self._isolate_delegate:
|
||||
self._isolate_delegate.Clear()
|
||||
|
||||
|
|
|
@ -18,6 +18,7 @@ from pylib.base import test_instance
|
|||
from pylib.constants import host_paths
|
||||
from pylib.instrumentation import test_result
|
||||
from pylib.instrumentation import instrumentation_parser
|
||||
from pylib.utils import isolator
|
||||
from pylib.utils import proguard
|
||||
|
||||
with host_paths.SysPath(host_paths.BUILD_COMMON_PATH):
|
||||
|
@ -399,7 +400,7 @@ def GetUniqueTestName(test, sep='#'):
|
|||
|
||||
class InstrumentationTestInstance(test_instance.TestInstance):
|
||||
|
||||
def __init__(self, args, data_deps_delegate, error_func):
|
||||
def __init__(self, args, isolate_delegate, error_func):
|
||||
super(InstrumentationTestInstance, self).__init__()
|
||||
|
||||
self._additional_apks = []
|
||||
|
@ -416,9 +417,10 @@ class InstrumentationTestInstance(test_instance.TestInstance):
|
|||
self._initializeApkAttributes(args, error_func)
|
||||
|
||||
self._data_deps = None
|
||||
self._data_deps_delegate = None
|
||||
self._runtime_deps_path = None
|
||||
self._initializeDataDependencyAttributes(args, data_deps_delegate)
|
||||
self._isolate_abs_path = None
|
||||
self._isolate_delegate = None
|
||||
self._isolated_abs_path = None
|
||||
self._initializeDataDependencyAttributes(args, isolate_delegate)
|
||||
|
||||
self._annotations = None
|
||||
self._excluded_annotations = None
|
||||
|
@ -518,12 +520,22 @@ class InstrumentationTestInstance(test_instance.TestInstance):
|
|||
self._additional_apks = (
|
||||
[apk_helper.ToHelper(x) for x in args.additional_apks])
|
||||
|
||||
def _initializeDataDependencyAttributes(self, args, data_deps_delegate):
|
||||
def _initializeDataDependencyAttributes(self, args, isolate_delegate):
|
||||
self._data_deps = []
|
||||
self._data_deps_delegate = data_deps_delegate
|
||||
self._runtime_deps_path = args.runtime_deps_path
|
||||
if (args.isolate_file_path and
|
||||
not isolator.IsIsolateEmpty(args.isolate_file_path)):
|
||||
if os.path.isabs(args.isolate_file_path):
|
||||
self._isolate_abs_path = args.isolate_file_path
|
||||
else:
|
||||
self._isolate_abs_path = os.path.join(
|
||||
constants.DIR_SOURCE_ROOT, args.isolate_file_path)
|
||||
self._isolate_delegate = isolate_delegate
|
||||
self._isolated_abs_path = os.path.join(
|
||||
constants.GetOutDirectory(), '%s.isolated' % self._test_package)
|
||||
else:
|
||||
self._isolate_delegate = None
|
||||
|
||||
if not self._runtime_deps_path:
|
||||
if not self._isolate_delegate:
|
||||
logging.warning('No data dependencies will be pushed.')
|
||||
|
||||
def _initializeTestFilterAttributes(self, args):
|
||||
|
@ -676,8 +688,11 @@ class InstrumentationTestInstance(test_instance.TestInstance):
|
|||
|
||||
#override
|
||||
def SetUp(self):
|
||||
self._data_deps.extend(
|
||||
self._data_deps_delegate(self._runtime_deps_path))
|
||||
if self._isolate_delegate:
|
||||
self._isolate_delegate.Remap(
|
||||
self._isolate_abs_path, self._isolated_abs_path)
|
||||
self._isolate_delegate.MoveOutputDeps()
|
||||
self._data_deps.extend([(self._isolate_delegate.isolate_deps_dir, None)])
|
||||
|
||||
def GetDataDependencies(self):
|
||||
return self._data_deps
|
||||
|
@ -749,4 +764,5 @@ class InstrumentationTestInstance(test_instance.TestInstance):
|
|||
|
||||
#override
|
||||
def TearDown(self):
|
||||
pass
|
||||
if self._isolate_delegate:
|
||||
self._isolate_delegate.Clear()
|
||||
|
|
|
@ -251,7 +251,7 @@ class LocalDeviceGtestRun(local_device_test_run.LocalDeviceTestRun):
|
|||
def SetUp(self):
|
||||
@local_device_environment.handle_shard_failures_with(
|
||||
on_failure=self._env.BlacklistDevice)
|
||||
def individual_device_set_up(dev, host_device_tuples):
|
||||
def individual_device_set_up(dev):
|
||||
def install_apk():
|
||||
# Install test APK.
|
||||
self._delegate.Install(dev)
|
||||
|
@ -259,12 +259,11 @@ class LocalDeviceGtestRun(local_device_test_run.LocalDeviceTestRun):
|
|||
def push_test_data():
|
||||
# Push data dependencies.
|
||||
device_root = self._delegate.GetTestDataRoot(dev)
|
||||
host_device_tuples_substituted = [
|
||||
(h, local_device_test_run.SubstituteDeviceRoot(d, device_root))
|
||||
for h, d in host_device_tuples]
|
||||
dev.PushChangedFiles(
|
||||
host_device_tuples_substituted,
|
||||
delete_device_stale=True)
|
||||
data_deps = self._test_instance.GetDataDependencies()
|
||||
host_device_tuples = [
|
||||
(h, d if d is not None else device_root)
|
||||
for h, d in data_deps]
|
||||
dev.PushChangedFiles(host_device_tuples, delete_device_stale=True)
|
||||
if not host_device_tuples:
|
||||
dev.RunShellCommand(['rm', '-rf', device_root], check_return=True)
|
||||
dev.RunShellCommand(['mkdir', '-p', device_root], check_return=True)
|
||||
|
@ -290,9 +289,7 @@ class LocalDeviceGtestRun(local_device_test_run.LocalDeviceTestRun):
|
|||
for step in steps:
|
||||
step()
|
||||
|
||||
self._env.parallel_devices.pMap(
|
||||
individual_device_set_up,
|
||||
self._test_instance.GetDataDependencies())
|
||||
self._env.parallel_devices.pMap(individual_device_set_up)
|
||||
|
||||
#override
|
||||
def _ShouldShard(self):
|
||||
|
|
|
@ -66,6 +66,14 @@ class LocalDeviceInstrumentationTestRun(
|
|||
|
||||
#override
|
||||
def SetUp(self):
|
||||
def substitute_device_root(d, device_root):
|
||||
if not d:
|
||||
return device_root
|
||||
elif isinstance(d, list):
|
||||
return posixpath.join(*(p if p else device_root for p in d))
|
||||
else:
|
||||
return d
|
||||
|
||||
@local_device_environment.handle_shard_failures_with(
|
||||
self._env.BlacklistDevice)
|
||||
def individual_device_set_up(dev, host_device_tuples):
|
||||
|
@ -109,7 +117,7 @@ class LocalDeviceInstrumentationTestRun(
|
|||
device_root = posixpath.join(dev.GetExternalStoragePath(),
|
||||
'chromium_tests_root')
|
||||
host_device_tuples_substituted = [
|
||||
(h, local_device_test_run.SubstituteDeviceRoot(d, device_root))
|
||||
(h, substitute_device_root(d, device_root))
|
||||
for h, d in host_device_tuples]
|
||||
logging.info('instrumentation data deps:')
|
||||
for h, d in host_device_tuples_substituted:
|
||||
|
|
|
@ -5,7 +5,6 @@
|
|||
import fnmatch
|
||||
import imp
|
||||
import logging
|
||||
import posixpath
|
||||
import signal
|
||||
import thread
|
||||
import threading
|
||||
|
@ -45,15 +44,6 @@ def IncrementalInstall(device, apk_helper, installer_script):
|
|||
permissions=None) # Auto-grant permissions from manifest.
|
||||
|
||||
|
||||
def SubstituteDeviceRoot(device_path, device_root):
|
||||
if not device_path:
|
||||
return device_root
|
||||
elif isinstance(device_path, list):
|
||||
return posixpath.join(*(p if p else device_root for p in device_path))
|
||||
else:
|
||||
return device_path
|
||||
|
||||
|
||||
class LocalDeviceTestRun(test_run.TestRun):
|
||||
|
||||
def __init__(self, env, test_instance):
|
||||
|
|
|
@ -15,34 +15,6 @@ with host_paths.SysPath(host_paths.PYMOCK_PATH):
|
|||
import mock # pylint: disable=import-error
|
||||
|
||||
|
||||
class SubstituteDeviceRootTest(unittest.TestCase):
|
||||
|
||||
def testNoneDevicePath(self):
|
||||
self.assertEquals(
|
||||
'/fake/device/root',
|
||||
local_device_test_run.SubstituteDeviceRoot(
|
||||
None, '/fake/device/root'))
|
||||
|
||||
def testStringDevicePath(self):
|
||||
self.assertEquals(
|
||||
'/another/fake/device/path',
|
||||
local_device_test_run.SubstituteDeviceRoot(
|
||||
'/another/fake/device/path', '/fake/device/root'))
|
||||
|
||||
def testListWithNoneDevicePath(self):
|
||||
self.assertEquals(
|
||||
'/fake/device/root/subpath',
|
||||
local_device_test_run.SubstituteDeviceRoot(
|
||||
[None, 'subpath'], '/fake/device/root'))
|
||||
|
||||
def testListWithoutNoneDevicePath(self):
|
||||
self.assertEquals(
|
||||
'/another/fake/device/path',
|
||||
local_device_test_run.SubstituteDeviceRoot(
|
||||
['/', 'another', 'fake', 'device', 'path'],
|
||||
'/fake/device/root'))
|
||||
|
||||
|
||||
class TestLocalDeviceTestRun(local_device_test_run.LocalDeviceTestRun):
|
||||
|
||||
# pylint: disable=abstract-method
|
||||
|
|
|
@ -1,104 +0,0 @@
|
|||
# Copyright 2016 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 os
|
||||
import re
|
||||
|
||||
from pylib import constants
|
||||
|
||||
|
||||
_BLACKLIST = [
|
||||
re.compile(r'.*OWNERS'), # Should never be included.
|
||||
re.compile(r'.*\.crx'), # Chrome extension zip files.
|
||||
re.compile(r'.*\.so'), # Libraries packed into .apk.
|
||||
re.compile(r'.*Mojo.*manifest\.json'), # Some source_set()s pull these in.
|
||||
re.compile(r'.*\.py'), # Some test_support targets include python deps.
|
||||
|
||||
# Some test_support targets include python deps.
|
||||
re.compile(r'.*\.mojom\.js'),
|
||||
|
||||
# Chrome external extensions config file.
|
||||
re.compile(r'.*external_extensions\.json'),
|
||||
|
||||
# Exists just to test the compile, not to be run.
|
||||
re.compile(r'.*jni_generator_tests'),
|
||||
|
||||
# v8's blobs get packaged into APKs.
|
||||
re.compile(r'.*natives_blob.*\.bin'),
|
||||
re.compile(r'.*snapshot_blob.*\.bin'),
|
||||
]
|
||||
|
||||
|
||||
def DevicePathComponentsFor(host_path, output_directory):
|
||||
"""Returns the device path components for a given host path.
|
||||
|
||||
This returns the device path as a list of joinable path components,
|
||||
with None as the first element to indicate that the path should be
|
||||
rooted at $EXTERNAL_STORAGE.
|
||||
|
||||
e.g., given
|
||||
|
||||
'$CHROMIUM_SRC/foo/bar/baz.txt'
|
||||
|
||||
this would return
|
||||
|
||||
[None, 'foo', 'bar', 'baz.txt']
|
||||
|
||||
This handles a couple classes of paths differently than it otherwise would:
|
||||
- All .pak files get mapped to top-level paks/
|
||||
- Anything in the output directory gets mapped relative to the output
|
||||
directory rather than the source directory.
|
||||
|
||||
e.g. given
|
||||
|
||||
'$CHROMIUM_SRC/out/Release/icu_fake_dir/icudtl.dat'
|
||||
|
||||
this would return
|
||||
|
||||
[None, 'icu_fake_dir', 'icudtl.dat']
|
||||
|
||||
Args:
|
||||
host_path: The absolute path to the host file.
|
||||
Returns:
|
||||
A list of device path components.
|
||||
"""
|
||||
if host_path.startswith(output_directory):
|
||||
if os.path.splitext(host_path)[1] == '.pak':
|
||||
return [None, 'paks', os.path.basename(host_path)]
|
||||
rel_host_path = os.path.relpath(host_path, output_directory)
|
||||
else:
|
||||
rel_host_path = os.path.relpath(host_path, constants.DIR_SOURCE_ROOT)
|
||||
|
||||
device_path_components = [None]
|
||||
p = rel_host_path
|
||||
while p:
|
||||
p, d = os.path.split(p)
|
||||
if d:
|
||||
device_path_components.insert(1, d)
|
||||
return device_path_components
|
||||
|
||||
|
||||
def GetDataDependencies(runtime_deps_path):
|
||||
"""Returns a list of device data dependencies.
|
||||
|
||||
Args:
|
||||
runtime_deps_path: A str path to the .runtime_deps file.
|
||||
Returns:
|
||||
A list of (host_path, device_path) tuples.
|
||||
"""
|
||||
if not runtime_deps_path:
|
||||
return []
|
||||
|
||||
with open(runtime_deps_path, 'r') as runtime_deps_file:
|
||||
rel_host_files = [l.strip() for l in runtime_deps_file if l]
|
||||
|
||||
output_directory = constants.GetOutDirectory()
|
||||
abs_host_files = [
|
||||
os.path.abspath(os.path.join(output_directory, r))
|
||||
for r in rel_host_files]
|
||||
filtered_abs_host_files = [
|
||||
host_file for host_file in abs_host_files
|
||||
if not any(blacklist_re.match(host_file) for blacklist_re in _BLACKLIST)]
|
||||
return [(f, DevicePathComponentsFor(f, output_directory))
|
||||
for f in filtered_abs_host_files]
|
|
@ -1,56 +0,0 @@
|
|||
#! /usr/bin/env python
|
||||
# Copyright 2016 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 os
|
||||
import unittest
|
||||
|
||||
from pylib import constants
|
||||
from pylib.utils import device_dependencies
|
||||
|
||||
|
||||
class DevicePathComponentsForTest(unittest.TestCase):
|
||||
|
||||
def testCheckedInFile(self):
|
||||
test_path = os.path.join(constants.DIR_SOURCE_ROOT, 'foo', 'bar', 'baz.txt')
|
||||
output_directory = os.path.join(
|
||||
constants.DIR_SOURCE_ROOT, 'out-foo', 'Release')
|
||||
self.assertEquals(
|
||||
[None, 'foo', 'bar', 'baz.txt'],
|
||||
device_dependencies.DevicePathComponentsFor(
|
||||
test_path, output_directory))
|
||||
|
||||
def testOutputDirectoryFile(self):
|
||||
test_path = os.path.join(constants.DIR_SOURCE_ROOT, 'out-foo', 'Release',
|
||||
'icudtl.dat')
|
||||
output_directory = os.path.join(
|
||||
constants.DIR_SOURCE_ROOT, 'out-foo', 'Release')
|
||||
self.assertEquals(
|
||||
[None, 'icudtl.dat'],
|
||||
device_dependencies.DevicePathComponentsFor(
|
||||
test_path, output_directory))
|
||||
|
||||
def testOutputDirectorySubdirFile(self):
|
||||
test_path = os.path.join(constants.DIR_SOURCE_ROOT, 'out-foo', 'Release',
|
||||
'test_dir', 'icudtl.dat')
|
||||
output_directory = os.path.join(
|
||||
constants.DIR_SOURCE_ROOT, 'out-foo', 'Release')
|
||||
self.assertEquals(
|
||||
[None, 'test_dir', 'icudtl.dat'],
|
||||
device_dependencies.DevicePathComponentsFor(
|
||||
test_path, output_directory))
|
||||
|
||||
def testOutputDirectoryPakFile(self):
|
||||
test_path = os.path.join(constants.DIR_SOURCE_ROOT, 'out-foo', 'Release',
|
||||
'foo.pak')
|
||||
output_directory = os.path.join(
|
||||
constants.DIR_SOURCE_ROOT, 'out-foo', 'Release')
|
||||
self.assertEquals(
|
||||
[None, 'paks', 'foo.pak'],
|
||||
device_dependencies.DevicePathComponentsFor(
|
||||
test_path, output_directory))
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
unittest.main()
|
|
@ -0,0 +1,192 @@
|
|||
# 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 fnmatch
|
||||
import glob
|
||||
import os
|
||||
import shutil
|
||||
import sys
|
||||
import tempfile
|
||||
|
||||
from devil.utils import cmd_helper
|
||||
from pylib import constants
|
||||
from pylib.constants import host_paths
|
||||
|
||||
|
||||
_ISOLATE_SCRIPT = os.path.join(
|
||||
host_paths.DIR_SOURCE_ROOT, 'tools', 'swarming_client', 'isolate.py')
|
||||
|
||||
|
||||
def DefaultPathVariables():
|
||||
return {
|
||||
'DEPTH': host_paths.DIR_SOURCE_ROOT,
|
||||
'PRODUCT_DIR': constants.GetOutDirectory(),
|
||||
}
|
||||
|
||||
|
||||
def DefaultConfigVariables():
|
||||
# Note: This list must match the --config-vars in build/isolate.gypi
|
||||
return {
|
||||
'CONFIGURATION_NAME': constants.GetBuildType(),
|
||||
'OS': 'android',
|
||||
'asan': '0',
|
||||
'branding': 'Chromium',
|
||||
'chromeos': '0',
|
||||
'component': 'static_library',
|
||||
'enable_pepper_cdms': '0',
|
||||
'enable_plugins': '0',
|
||||
'fastbuild': '0',
|
||||
'icu_use_data_file_flag': '1',
|
||||
'kasko': '0',
|
||||
'lsan': '0',
|
||||
'msan': '0',
|
||||
# TODO(maruel): This may not always be true.
|
||||
'target_arch': 'arm',
|
||||
'tsan': '0',
|
||||
'use_custom_libcxx': '0',
|
||||
'use_instrumented_libraries': '0',
|
||||
'use_prebuilt_instrumented_libraries': '0',
|
||||
'use_ozone': '0',
|
||||
'use_x11': '0',
|
||||
'v8_use_external_startup_data': '1',
|
||||
'msvs_version': '0',
|
||||
}
|
||||
|
||||
|
||||
def IsIsolateEmpty(isolate_path):
|
||||
"""Returns whether there are no files in the .isolate."""
|
||||
with open(isolate_path) as f:
|
||||
return "'files': []" in f.read()
|
||||
|
||||
|
||||
class Isolator(object):
|
||||
"""Manages calls to isolate.py for the android test runner scripts."""
|
||||
|
||||
def __init__(self):
|
||||
self._isolate_deps_dir = tempfile.mkdtemp()
|
||||
|
||||
@property
|
||||
def isolate_deps_dir(self):
|
||||
return self._isolate_deps_dir
|
||||
|
||||
def Clear(self):
|
||||
"""Deletes the isolate dependency directory."""
|
||||
if os.path.exists(self._isolate_deps_dir):
|
||||
shutil.rmtree(self._isolate_deps_dir)
|
||||
|
||||
def Remap(self, isolate_abs_path, isolated_abs_path,
|
||||
path_variables=None, config_variables=None):
|
||||
"""Remaps data dependencies into |self._isolate_deps_dir|.
|
||||
|
||||
Args:
|
||||
isolate_abs_path: The absolute path to the .isolate file, which specifies
|
||||
data dependencies in the source tree.
|
||||
isolated_abs_path: The absolute path to the .isolated file, which is
|
||||
generated by isolate.py and specifies data dependencies in
|
||||
|self._isolate_deps_dir| and their digests.
|
||||
path_variables: A dict containing everything that should be passed
|
||||
as a |--path-variable| to the isolate script. Defaults to the return
|
||||
value of |DefaultPathVariables()|.
|
||||
config_variables: A dict containing everything that should be passed
|
||||
as a |--config-variable| to the isolate script. Defaults to the return
|
||||
value of |DefaultConfigVariables()|.
|
||||
Raises:
|
||||
Exception if the isolate command fails for some reason.
|
||||
"""
|
||||
if not path_variables:
|
||||
path_variables = DefaultPathVariables()
|
||||
if not config_variables:
|
||||
config_variables = DefaultConfigVariables()
|
||||
|
||||
isolate_cmd = [
|
||||
sys.executable, _ISOLATE_SCRIPT, 'remap',
|
||||
'--isolate', isolate_abs_path,
|
||||
'--isolated', isolated_abs_path,
|
||||
'--outdir', self._isolate_deps_dir,
|
||||
]
|
||||
for k, v in path_variables.iteritems():
|
||||
isolate_cmd.extend(['--path-variable', k, v])
|
||||
for k, v in config_variables.iteritems():
|
||||
isolate_cmd.extend(['--config-variable', k, v])
|
||||
|
||||
exit_code, _ = cmd_helper.GetCmdStatusAndOutput(isolate_cmd)
|
||||
if exit_code:
|
||||
raise Exception('isolate command failed: %s' % ' '.join(isolate_cmd))
|
||||
|
||||
def VerifyHardlinks(self):
|
||||
"""Checks |isolate_deps_dir| for a hardlink.
|
||||
|
||||
Returns:
|
||||
True if a hardlink is found.
|
||||
False if nothing is found.
|
||||
Raises:
|
||||
Exception if a non-hardlink is found.
|
||||
"""
|
||||
for root, _, filenames in os.walk(self._isolate_deps_dir):
|
||||
if filenames:
|
||||
linked_file = os.path.join(root, filenames[0])
|
||||
orig_file = os.path.join(
|
||||
self._isolate_deps_dir,
|
||||
os.path.relpath(linked_file, self._isolate_deps_dir))
|
||||
if os.stat(linked_file).st_ino == os.stat(orig_file).st_ino:
|
||||
return True
|
||||
else:
|
||||
raise Exception('isolate remap command did not use hardlinks.')
|
||||
return False
|
||||
|
||||
def PurgeExcluded(self, deps_exclusion_list):
|
||||
"""Deletes anything on |deps_exclusion_list| from |self._isolate_deps_dir|.
|
||||
|
||||
Args:
|
||||
deps_exclusion_list: A list of globs to exclude from the isolate
|
||||
dependency directory.
|
||||
"""
|
||||
excluded_paths = (
|
||||
x for y in deps_exclusion_list
|
||||
for x in glob.glob(
|
||||
os.path.abspath(os.path.join(self._isolate_deps_dir, y))))
|
||||
for p in excluded_paths:
|
||||
if os.path.isdir(p):
|
||||
shutil.rmtree(p)
|
||||
else:
|
||||
os.remove(p)
|
||||
|
||||
@classmethod
|
||||
def _DestructiveMerge(cls, src, dest):
|
||||
if os.path.exists(dest) and os.path.isdir(dest):
|
||||
for p in os.listdir(src):
|
||||
cls._DestructiveMerge(os.path.join(src, p), os.path.join(dest, p))
|
||||
os.rmdir(src)
|
||||
else:
|
||||
shutil.move(src, dest)
|
||||
|
||||
|
||||
def MoveOutputDeps(self):
|
||||
"""Moves files from the output directory to the top level of
|
||||
|self._isolate_deps_dir|.
|
||||
|
||||
Moves pak files from the output directory to to <isolate_deps_dir>/paks
|
||||
Moves files from the product directory to <isolate_deps_dir>
|
||||
"""
|
||||
# On Android, all pak files need to be in the top-level 'paks' directory.
|
||||
paks_dir = os.path.join(self._isolate_deps_dir, 'paks')
|
||||
os.mkdir(paks_dir)
|
||||
|
||||
deps_out_dir = os.path.join(
|
||||
self._isolate_deps_dir,
|
||||
os.path.relpath(os.path.join(constants.GetOutDirectory(), os.pardir),
|
||||
host_paths.DIR_SOURCE_ROOT))
|
||||
for root, _, filenames in os.walk(deps_out_dir):
|
||||
for filename in fnmatch.filter(filenames, '*.pak'):
|
||||
shutil.move(os.path.join(root, filename), paks_dir)
|
||||
|
||||
# Move everything in PRODUCT_DIR to top level.
|
||||
deps_product_dir = os.path.join(
|
||||
deps_out_dir, os.path.basename(constants.GetOutDirectory()))
|
||||
if os.path.isdir(deps_product_dir):
|
||||
for p in os.listdir(deps_product_dir):
|
||||
Isolator._DestructiveMerge(os.path.join(deps_product_dir, p),
|
||||
os.path.join(self._isolate_deps_dir, p))
|
||||
os.rmdir(deps_product_dir)
|
||||
os.rmdir(deps_out_dir)
|
|
@ -196,16 +196,12 @@ def AddGTestOptions(parser):
|
|||
dest='shard_timeout', type=int, default=120,
|
||||
help='Timeout to wait for each test '
|
||||
'(default: %(default)s).')
|
||||
# TODO(jbudorick): Remove this after ensuring nothing else uses it.
|
||||
group.add_argument('--isolate_file_path',
|
||||
'--isolate-file-path',
|
||||
dest='isolate_file_path',
|
||||
type=os.path.realpath,
|
||||
help=argparse.SUPPRESS)
|
||||
group.add_argument('--runtime-deps-path',
|
||||
dest='runtime_deps_path',
|
||||
type=os.path.realpath,
|
||||
help='Runtime data dependency file from GN.')
|
||||
help='.isolate file path to override the default '
|
||||
'path')
|
||||
group.add_argument('--app-data-file', action='append', dest='app_data_files',
|
||||
help='A file path relative to the app data directory '
|
||||
'that should be saved to the host.')
|
||||
|
@ -364,16 +360,12 @@ def AddInstrumentationTestOptions(parser):
|
|||
group.add_argument('--device-flags-file', type=os.path.realpath,
|
||||
help='The relative filepath to a file containing '
|
||||
'command-line flags to set on the device')
|
||||
# TODO(jbudorick): Remove this after ensuring nothing else uses it.
|
||||
group.add_argument('--isolate_file_path',
|
||||
'--isolate-file-path',
|
||||
dest='isolate_file_path',
|
||||
type=os.path.realpath,
|
||||
help=argparse.SUPPRESS)
|
||||
group.add_argument('--runtime-deps-path',
|
||||
dest='runtime_deps_path',
|
||||
type=os.path.realpath,
|
||||
help='Runtime data dependency file from GN.')
|
||||
help='.isolate file path to override the default '
|
||||
'path')
|
||||
group.add_argument('--delete-stale-data', dest='delete_stale_data',
|
||||
action='store_true',
|
||||
help='Delete stale test data on the device.')
|
||||
|
|
|
@ -124,7 +124,7 @@ pylib/results/flakiness_dashboard/results_uploader.py
|
|||
pylib/results/json_results.py
|
||||
pylib/results/report_results.py
|
||||
pylib/utils/__init__.py
|
||||
pylib/utils/device_dependencies.py
|
||||
pylib/utils/isolator.py
|
||||
pylib/utils/proguard.py
|
||||
pylib/utils/repo_utils.py
|
||||
pylib/valgrind_tools.py
|
||||
|
|
|
@ -417,6 +417,55 @@ template("copy_ex") {
|
|||
}
|
||||
}
|
||||
|
||||
template("device_isolate") {
|
||||
testonly = true
|
||||
_runtime_deps_file = "$target_gen_dir/$target_name.runtime_deps"
|
||||
group("${target_name}__write_deps") {
|
||||
forward_variables_from(invoker,
|
||||
[
|
||||
"data",
|
||||
"data_deps",
|
||||
"deps",
|
||||
"public_deps",
|
||||
])
|
||||
write_runtime_deps = _runtime_deps_file
|
||||
}
|
||||
|
||||
action(target_name) {
|
||||
script = "//build/android/gn/generate_isolate.py"
|
||||
inputs = [
|
||||
_runtime_deps_file,
|
||||
]
|
||||
outputs = [
|
||||
invoker.output,
|
||||
]
|
||||
args = [
|
||||
"--output-directory=.",
|
||||
"--out-file",
|
||||
rebase_path(invoker.output, root_build_dir),
|
||||
"--runtime-deps-file",
|
||||
rebase_path(_runtime_deps_file, root_build_dir),
|
||||
"--apply-android-filters",
|
||||
"--apply-device-filters",
|
||||
]
|
||||
_assert_no_odd_data =
|
||||
defined(invoker.assert_no_odd_data) && invoker.assert_no_odd_data
|
||||
if (_assert_no_odd_data) {
|
||||
args += [ "--assert-no-odd-data" ]
|
||||
}
|
||||
if (defined(invoker.command)) {
|
||||
_isolate_dir = get_path_info(invoker.output, "dir")
|
||||
args += [
|
||||
"--command",
|
||||
rebase_path(invoker.command, _isolate_dir),
|
||||
]
|
||||
}
|
||||
deps = [
|
||||
":${invoker.target_name}__write_deps",
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
# Generates a script in the output bin directory which runs the test
|
||||
# target using the test runner script in build/android/test_runner.py.
|
||||
template("test_runner_script") {
|
||||
|
@ -426,24 +475,6 @@ template("test_runner_script") {
|
|||
_incremental_install =
|
||||
defined(invoker.incremental_install) && invoker.incremental_install
|
||||
|
||||
_runtime_deps =
|
||||
!defined(invoker.ignore_all_data_deps) || !invoker.ignore_all_data_deps
|
||||
|
||||
if (_runtime_deps) {
|
||||
_runtime_deps_file = "$target_gen_dir/$target_name.runtime_deps"
|
||||
_runtime_deps_target = "${target_name}__write_deps"
|
||||
group(_runtime_deps_target) {
|
||||
forward_variables_from(invoker,
|
||||
[
|
||||
"data",
|
||||
"data_deps",
|
||||
"deps",
|
||||
"public_deps",
|
||||
])
|
||||
write_runtime_deps = _runtime_deps_file
|
||||
}
|
||||
}
|
||||
|
||||
action(target_name) {
|
||||
forward_variables_from(invoker,
|
||||
[
|
||||
|
@ -469,15 +500,6 @@ template("test_runner_script") {
|
|||
rebase_path(root_build_dir, root_build_dir),
|
||||
]
|
||||
|
||||
if (_runtime_deps) {
|
||||
deps += [ ":$_runtime_deps_target" ]
|
||||
data += [ _runtime_deps_file ]
|
||||
test_runner_args += [
|
||||
"--runtime-deps-path",
|
||||
rebase_path(_runtime_deps_file, root_build_dir),
|
||||
]
|
||||
}
|
||||
|
||||
# apk_target is not used for native executable tests
|
||||
# (e.g. breakpad_unittests).
|
||||
if (defined(invoker.apk_target)) {
|
||||
|
@ -554,6 +576,13 @@ template("test_runner_script") {
|
|||
]
|
||||
}
|
||||
}
|
||||
if (defined(invoker.isolate_file)) {
|
||||
data += [ invoker.isolate_file ]
|
||||
test_runner_args += [
|
||||
"--isolate-file-path",
|
||||
rebase_path(invoker.isolate_file, root_build_dir),
|
||||
]
|
||||
}
|
||||
if (defined(invoker.shard_timeout)) {
|
||||
test_runner_args += [ "--shard-timeout=${invoker.shard_timeout}" ]
|
||||
}
|
||||
|
|
|
@ -2260,23 +2260,36 @@ if (enable_java_templates) {
|
|||
template("instrumentation_test_apk") {
|
||||
testonly = true
|
||||
_apk_target_name = "${target_name}__apk"
|
||||
_gen_isolate_target_name = "${target_name}__isolate"
|
||||
_test_runner_target_name = "${target_name}__test_runner_script"
|
||||
_install_script_name = "install_$target_name"
|
||||
|
||||
_target_dir_name = get_label_info(":$target_name", "dir")
|
||||
_device_isolate_path = "$root_out_dir/gen.runtime/$_target_dir_name/$target_name.device.isolate"
|
||||
device_isolate(_gen_isolate_target_name) {
|
||||
forward_variables_from(invoker,
|
||||
[
|
||||
"data",
|
||||
"data_deps",
|
||||
"deps",
|
||||
"public_deps",
|
||||
])
|
||||
output = _device_isolate_path
|
||||
}
|
||||
|
||||
test_runner_script(_test_runner_target_name) {
|
||||
forward_variables_from(invoker,
|
||||
[
|
||||
"additional_apks",
|
||||
"apk_under_test",
|
||||
"data",
|
||||
"data_deps",
|
||||
"deps",
|
||||
"ignore_all_data_deps",
|
||||
"public_deps",
|
||||
])
|
||||
test_name = invoker.target_name
|
||||
test_type = "instrumentation"
|
||||
apk_target = ":$_apk_target_name"
|
||||
isolate_file = _device_isolate_path
|
||||
deps = [
|
||||
":$_gen_isolate_target_name",
|
||||
]
|
||||
}
|
||||
|
||||
test_runner_script("${_test_runner_target_name}_incremental") {
|
||||
|
@ -2284,16 +2297,15 @@ if (enable_java_templates) {
|
|||
[
|
||||
"additional_apks",
|
||||
"apk_under_test",
|
||||
"data",
|
||||
"data_deps",
|
||||
"deps",
|
||||
"ignore_all_data_deps",
|
||||
"public_deps",
|
||||
])
|
||||
test_name = "${invoker.target_name}_incremental"
|
||||
test_type = "instrumentation"
|
||||
apk_target = ":$_apk_target_name"
|
||||
incremental_install = true
|
||||
isolate_file = _device_isolate_path
|
||||
deps = [
|
||||
":$_gen_isolate_target_name",
|
||||
]
|
||||
}
|
||||
|
||||
android_apk(_apk_target_name) {
|
||||
|
|
|
@ -0,0 +1,14 @@
|
|||
# Copyright 2016 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.
|
||||
|
||||
group("isolate_py") {
|
||||
_py_files =
|
||||
read_file("//build/secondary/tools/swarming_client/isolate.pydeps",
|
||||
"list lines")
|
||||
|
||||
# Filter out comments.
|
||||
set_sources_assignment_filter([ "#*" ])
|
||||
sources = _py_files
|
||||
data = sources
|
||||
}
|
|
@ -0,0 +1,298 @@
|
|||
# Generated by running:
|
||||
# build/print_python_deps.py --root tools/swarming_client --output build/secondary/tools/swarming_client/isolate.pydeps --whitelist tools/swarming_client/libs --whitelist tools/swarming_client/third_party tools/swarming_client/isolate.py
|
||||
auth.py
|
||||
cipd.py
|
||||
isolate.py
|
||||
isolate_format.py
|
||||
isolated_format.py
|
||||
isolateserver.py
|
||||
libs/__init__.py
|
||||
libs/arfile/__init__.py
|
||||
libs/arfile/arfile.py
|
||||
libs/arfile/cli.py
|
||||
libs/logdog/__init__.py
|
||||
libs/logdog/bootstrap.py
|
||||
libs/logdog/stream.py
|
||||
libs/logdog/streamname.py
|
||||
libs/logdog/varint.py
|
||||
libs/luci_context/__init__.py
|
||||
libs/luci_context/luci_context.py
|
||||
named_cache.py
|
||||
run_isolated.py
|
||||
third_party/__init__.py
|
||||
third_party/chromium/__init__.py
|
||||
third_party/chromium/natsort.py
|
||||
third_party/colorama/__init__.py
|
||||
third_party/colorama/ansi.py
|
||||
third_party/colorama/ansitowin32.py
|
||||
third_party/colorama/initialise.py
|
||||
third_party/colorama/win32.py
|
||||
third_party/colorama/winterm.py
|
||||
third_party/depot_tools/__init__.py
|
||||
third_party/depot_tools/auto_stub.py
|
||||
third_party/depot_tools/fix_encoding.py
|
||||
third_party/depot_tools/subcommand.py
|
||||
third_party/google/__init__.py
|
||||
third_party/google/protobuf/__init__.py
|
||||
third_party/google/protobuf/any_pb2.py
|
||||
third_party/google/protobuf/any_test_pb2.py
|
||||
third_party/google/protobuf/api_pb2.py
|
||||
third_party/google/protobuf/compiler/__init__.py
|
||||
third_party/google/protobuf/compiler/plugin_pb2.py
|
||||
third_party/google/protobuf/descriptor.py
|
||||
third_party/google/protobuf/descriptor_database.py
|
||||
third_party/google/protobuf/descriptor_pb2.py
|
||||
third_party/google/protobuf/descriptor_pool.py
|
||||
third_party/google/protobuf/duration_pb2.py
|
||||
third_party/google/protobuf/empty_pb2.py
|
||||
third_party/google/protobuf/field_mask_pb2.py
|
||||
third_party/google/protobuf/internal/__init__.py
|
||||
third_party/google/protobuf/internal/_parameterized.py
|
||||
third_party/google/protobuf/internal/any_test_pb2.py
|
||||
third_party/google/protobuf/internal/api_implementation.py
|
||||
third_party/google/protobuf/internal/containers.py
|
||||
third_party/google/protobuf/internal/decoder.py
|
||||
third_party/google/protobuf/internal/descriptor_pool_test1_pb2.py
|
||||
third_party/google/protobuf/internal/descriptor_pool_test2_pb2.py
|
||||
third_party/google/protobuf/internal/encoder.py
|
||||
third_party/google/protobuf/internal/enum_type_wrapper.py
|
||||
third_party/google/protobuf/internal/factory_test1_pb2.py
|
||||
third_party/google/protobuf/internal/factory_test2_pb2.py
|
||||
third_party/google/protobuf/internal/file_options_test_pb2.py
|
||||
third_party/google/protobuf/internal/import_test_package/__init__.py
|
||||
third_party/google/protobuf/internal/import_test_package/inner_pb2.py
|
||||
third_party/google/protobuf/internal/import_test_package/outer_pb2.py
|
||||
third_party/google/protobuf/internal/message_listener.py
|
||||
third_party/google/protobuf/internal/message_set_extensions_pb2.py
|
||||
third_party/google/protobuf/internal/missing_enum_values_pb2.py
|
||||
third_party/google/protobuf/internal/more_extensions_dynamic_pb2.py
|
||||
third_party/google/protobuf/internal/more_extensions_pb2.py
|
||||
third_party/google/protobuf/internal/more_messages_pb2.py
|
||||
third_party/google/protobuf/internal/packed_field_test_pb2.py
|
||||
third_party/google/protobuf/internal/python_message.py
|
||||
third_party/google/protobuf/internal/test_bad_identifiers_pb2.py
|
||||
third_party/google/protobuf/internal/test_util.py
|
||||
third_party/google/protobuf/internal/type_checkers.py
|
||||
third_party/google/protobuf/internal/well_known_types.py
|
||||
third_party/google/protobuf/internal/wire_format.py
|
||||
third_party/google/protobuf/json_format.py
|
||||
third_party/google/protobuf/map_unittest_pb2.py
|
||||
third_party/google/protobuf/message.py
|
||||
third_party/google/protobuf/message_factory.py
|
||||
third_party/google/protobuf/proto_builder.py
|
||||
third_party/google/protobuf/pyext/__init__.py
|
||||
third_party/google/protobuf/pyext/cpp_message.py
|
||||
third_party/google/protobuf/pyext/python_pb2.py
|
||||
third_party/google/protobuf/reflection.py
|
||||
third_party/google/protobuf/service.py
|
||||
third_party/google/protobuf/service_reflection.py
|
||||
third_party/google/protobuf/source_context_pb2.py
|
||||
third_party/google/protobuf/struct_pb2.py
|
||||
third_party/google/protobuf/symbol_database.py
|
||||
third_party/google/protobuf/text_encoding.py
|
||||
third_party/google/protobuf/text_format.py
|
||||
third_party/google/protobuf/timestamp_pb2.py
|
||||
third_party/google/protobuf/type_pb2.py
|
||||
third_party/google/protobuf/unittest_arena_pb2.py
|
||||
third_party/google/protobuf/unittest_custom_options_pb2.py
|
||||
third_party/google/protobuf/unittest_import_pb2.py
|
||||
third_party/google/protobuf/unittest_import_public_pb2.py
|
||||
third_party/google/protobuf/unittest_mset_pb2.py
|
||||
third_party/google/protobuf/unittest_mset_wire_format_pb2.py
|
||||
third_party/google/protobuf/unittest_no_arena_import_pb2.py
|
||||
third_party/google/protobuf/unittest_no_arena_pb2.py
|
||||
third_party/google/protobuf/unittest_no_generic_services_pb2.py
|
||||
third_party/google/protobuf/unittest_pb2.py
|
||||
third_party/google/protobuf/unittest_proto3_arena_pb2.py
|
||||
third_party/google/protobuf/util/__init__.py
|
||||
third_party/google/protobuf/util/json_format_proto3_pb2.py
|
||||
third_party/google/protobuf/wrappers_pb2.py
|
||||
third_party/googleapiclient/__init__.py
|
||||
third_party/googleapiclient/channel.py
|
||||
third_party/googleapiclient/discovery.py
|
||||
third_party/googleapiclient/discovery_cache/__init__.py
|
||||
third_party/googleapiclient/discovery_cache/appengine_memcache.py
|
||||
third_party/googleapiclient/discovery_cache/base.py
|
||||
third_party/googleapiclient/discovery_cache/file_cache.py
|
||||
third_party/googleapiclient/errors.py
|
||||
third_party/googleapiclient/http.py
|
||||
third_party/googleapiclient/mimeparse.py
|
||||
third_party/googleapiclient/model.py
|
||||
third_party/googleapiclient/sample_tools.py
|
||||
third_party/googleapiclient/schema.py
|
||||
third_party/httplib2/__init__.py
|
||||
third_party/httplib2/iri2uri.py
|
||||
third_party/httplib2/socks.py
|
||||
third_party/infra_libs/__init__.py
|
||||
third_party/infra_libs/_command_line_linux.py
|
||||
third_party/infra_libs/_command_line_stub.py
|
||||
third_party/infra_libs/app.py
|
||||
third_party/infra_libs/authentication.py
|
||||
third_party/infra_libs/event_mon/__init__.py
|
||||
third_party/infra_libs/event_mon/checkouts.py
|
||||
third_party/infra_libs/event_mon/config.py
|
||||
third_party/infra_libs/event_mon/monitoring.py
|
||||
third_party/infra_libs/event_mon/protos/__init__.py
|
||||
third_party/infra_libs/event_mon/protos/chrome_infra_log_pb2.py
|
||||
third_party/infra_libs/event_mon/protos/goma_stats_pb2.py
|
||||
third_party/infra_libs/event_mon/protos/log_request_lite_pb2.py
|
||||
third_party/infra_libs/event_mon/router.py
|
||||
third_party/infra_libs/experiments.py
|
||||
third_party/infra_libs/httplib2_utils.py
|
||||
third_party/infra_libs/infra_types/__init__.py
|
||||
third_party/infra_libs/infra_types/infra_types.py
|
||||
third_party/infra_libs/instrumented_requests.py
|
||||
third_party/infra_libs/logs/__init__.py
|
||||
third_party/infra_libs/logs/logs.py
|
||||
third_party/infra_libs/memoize.py
|
||||
third_party/infra_libs/time_functions/__init__.py
|
||||
third_party/infra_libs/time_functions/parser.py
|
||||
third_party/infra_libs/time_functions/testing.py
|
||||
third_party/infra_libs/time_functions/timestamp.py
|
||||
third_party/infra_libs/time_functions/zulu.py
|
||||
third_party/infra_libs/ts_mon/__init__.py
|
||||
third_party/infra_libs/ts_mon/common/__init__.py
|
||||
third_party/infra_libs/ts_mon/common/distribution.py
|
||||
third_party/infra_libs/ts_mon/common/errors.py
|
||||
third_party/infra_libs/ts_mon/common/helpers.py
|
||||
third_party/infra_libs/ts_mon/common/http_metrics.py
|
||||
third_party/infra_libs/ts_mon/common/interface.py
|
||||
third_party/infra_libs/ts_mon/common/metric_store.py
|
||||
third_party/infra_libs/ts_mon/common/metrics.py
|
||||
third_party/infra_libs/ts_mon/common/monitors.py
|
||||
third_party/infra_libs/ts_mon/common/pb_to_popo.py
|
||||
third_party/infra_libs/ts_mon/common/standard_metrics.py
|
||||
third_party/infra_libs/ts_mon/common/targets.py
|
||||
third_party/infra_libs/ts_mon/config.py
|
||||
third_party/infra_libs/ts_mon/protos/__init__.py
|
||||
third_party/infra_libs/ts_mon/protos/current/__init__.py
|
||||
third_party/infra_libs/ts_mon/protos/current/acquisition_network_device_pb2.py
|
||||
third_party/infra_libs/ts_mon/protos/current/acquisition_task_pb2.py
|
||||
third_party/infra_libs/ts_mon/protos/current/metrics_pb2.py
|
||||
third_party/infra_libs/ts_mon/protos/new/__init__.py
|
||||
third_party/infra_libs/ts_mon/protos/new/acquisition_network_device_pb2.py
|
||||
third_party/infra_libs/ts_mon/protos/new/acquisition_task_pb2.py
|
||||
third_party/infra_libs/ts_mon/protos/new/any_pb2.py
|
||||
third_party/infra_libs/ts_mon/protos/new/metrics_pb2.py
|
||||
third_party/infra_libs/ts_mon/protos/new/timestamp_pb2.py
|
||||
third_party/infra_libs/utils.py
|
||||
third_party/oauth2client/__init__.py
|
||||
third_party/oauth2client/_helpers.py
|
||||
third_party/oauth2client/_openssl_crypt.py
|
||||
third_party/oauth2client/_pycrypto_crypt.py
|
||||
third_party/oauth2client/client.py
|
||||
third_party/oauth2client/clientsecrets.py
|
||||
third_party/oauth2client/crypt.py
|
||||
third_party/oauth2client/file.py
|
||||
third_party/oauth2client/gce.py
|
||||
third_party/oauth2client/keyring_storage.py
|
||||
third_party/oauth2client/locked_file.py
|
||||
third_party/oauth2client/multistore_file.py
|
||||
third_party/oauth2client/service_account.py
|
||||
third_party/oauth2client/tools.py
|
||||
third_party/oauth2client/util.py
|
||||
third_party/oauth2client/xsrfutil.py
|
||||
third_party/pyasn1/pyasn1/__init__.py
|
||||
third_party/pyasn1/pyasn1/codec/__init__.py
|
||||
third_party/pyasn1/pyasn1/codec/ber/__init__.py
|
||||
third_party/pyasn1/pyasn1/codec/ber/decoder.py
|
||||
third_party/pyasn1/pyasn1/codec/ber/encoder.py
|
||||
third_party/pyasn1/pyasn1/codec/ber/eoo.py
|
||||
third_party/pyasn1/pyasn1/codec/cer/__init__.py
|
||||
third_party/pyasn1/pyasn1/codec/cer/decoder.py
|
||||
third_party/pyasn1/pyasn1/codec/cer/encoder.py
|
||||
third_party/pyasn1/pyasn1/codec/der/__init__.py
|
||||
third_party/pyasn1/pyasn1/codec/der/decoder.py
|
||||
third_party/pyasn1/pyasn1/codec/der/encoder.py
|
||||
third_party/pyasn1/pyasn1/compat/__init__.py
|
||||
third_party/pyasn1/pyasn1/compat/binary.py
|
||||
third_party/pyasn1/pyasn1/compat/octets.py
|
||||
third_party/pyasn1/pyasn1/debug.py
|
||||
third_party/pyasn1/pyasn1/error.py
|
||||
third_party/pyasn1/pyasn1/type/__init__.py
|
||||
third_party/pyasn1/pyasn1/type/base.py
|
||||
third_party/pyasn1/pyasn1/type/char.py
|
||||
third_party/pyasn1/pyasn1/type/constraint.py
|
||||
third_party/pyasn1/pyasn1/type/error.py
|
||||
third_party/pyasn1/pyasn1/type/namedtype.py
|
||||
third_party/pyasn1/pyasn1/type/namedval.py
|
||||
third_party/pyasn1/pyasn1/type/tag.py
|
||||
third_party/pyasn1/pyasn1/type/tagmap.py
|
||||
third_party/pyasn1/pyasn1/type/univ.py
|
||||
third_party/pyasn1/pyasn1/type/useful.py
|
||||
third_party/requests/__init__.py
|
||||
third_party/requests/adapters.py
|
||||
third_party/requests/api.py
|
||||
third_party/requests/auth.py
|
||||
third_party/requests/certs.py
|
||||
third_party/requests/compat.py
|
||||
third_party/requests/cookies.py
|
||||
third_party/requests/exceptions.py
|
||||
third_party/requests/hooks.py
|
||||
third_party/requests/models.py
|
||||
third_party/requests/packages/__init__.py
|
||||
third_party/requests/packages/urllib3/__init__.py
|
||||
third_party/requests/packages/urllib3/_collections.py
|
||||
third_party/requests/packages/urllib3/connection.py
|
||||
third_party/requests/packages/urllib3/connectionpool.py
|
||||
third_party/requests/packages/urllib3/contrib/__init__.py
|
||||
third_party/requests/packages/urllib3/contrib/appengine.py
|
||||
third_party/requests/packages/urllib3/contrib/ntlmpool.py
|
||||
third_party/requests/packages/urllib3/contrib/pyopenssl.py
|
||||
third_party/requests/packages/urllib3/exceptions.py
|
||||
third_party/requests/packages/urllib3/fields.py
|
||||
third_party/requests/packages/urllib3/filepost.py
|
||||
third_party/requests/packages/urllib3/packages/__init__.py
|
||||
third_party/requests/packages/urllib3/packages/ordered_dict.py
|
||||
third_party/requests/packages/urllib3/packages/six.py
|
||||
third_party/requests/packages/urllib3/packages/ssl_match_hostname/__init__.py
|
||||
third_party/requests/packages/urllib3/packages/ssl_match_hostname/_implementation.py
|
||||
third_party/requests/packages/urllib3/poolmanager.py
|
||||
third_party/requests/packages/urllib3/request.py
|
||||
third_party/requests/packages/urllib3/response.py
|
||||
third_party/requests/packages/urllib3/util/__init__.py
|
||||
third_party/requests/packages/urllib3/util/connection.py
|
||||
third_party/requests/packages/urllib3/util/request.py
|
||||
third_party/requests/packages/urllib3/util/response.py
|
||||
third_party/requests/packages/urllib3/util/retry.py
|
||||
third_party/requests/packages/urllib3/util/ssl_.py
|
||||
third_party/requests/packages/urllib3/util/timeout.py
|
||||
third_party/requests/packages/urllib3/util/url.py
|
||||
third_party/requests/sessions.py
|
||||
third_party/requests/status_codes.py
|
||||
third_party/requests/structures.py
|
||||
third_party/requests/utils.py
|
||||
third_party/rsa/rsa/__init__.py
|
||||
third_party/rsa/rsa/_compat.py
|
||||
third_party/rsa/rsa/_version133.py
|
||||
third_party/rsa/rsa/_version200.py
|
||||
third_party/rsa/rsa/asn1.py
|
||||
third_party/rsa/rsa/bigfile.py
|
||||
third_party/rsa/rsa/cli.py
|
||||
third_party/rsa/rsa/common.py
|
||||
third_party/rsa/rsa/core.py
|
||||
third_party/rsa/rsa/key.py
|
||||
third_party/rsa/rsa/parallel.py
|
||||
third_party/rsa/rsa/pem.py
|
||||
third_party/rsa/rsa/pkcs1.py
|
||||
third_party/rsa/rsa/prime.py
|
||||
third_party/rsa/rsa/randnum.py
|
||||
third_party/rsa/rsa/transform.py
|
||||
third_party/rsa/rsa/util.py
|
||||
third_party/rsa/rsa/varblock.py
|
||||
third_party/six/__init__.py
|
||||
third_party/uritemplate/__init__.py
|
||||
utils/__init__.py
|
||||
utils/authenticators.py
|
||||
utils/file_path.py
|
||||
utils/fs.py
|
||||
utils/large.py
|
||||
utils/logging_utils.py
|
||||
utils/lru.py
|
||||
utils/net.py
|
||||
utils/oauth.py
|
||||
utils/on_error.py
|
||||
utils/subprocess42.py
|
||||
utils/threading_utils.py
|
||||
utils/tools.py
|
||||
utils/zip_package.py
|
Загрузка…
Ссылка в новой задаче