blob: a88f18602ab9982183a5762992c99ba0fddfe2f8 [file] [log] [blame]
# 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 json
import logging
import os
import re
import subprocess
import sys
import tempfile
# Install Infra build environment.
BUILD_ROOT = os.path.dirname(os.path.dirname(os.path.dirname(
os.path.abspath(__file__))))
sys.path.insert(0, os.path.join(BUILD_ROOT, 'scripts'))
from common import annotator
from common import env
LOGGER = logging.getLogger('update_scripts')
def _run_command(cmd, **kwargs):
LOGGER.debug('Executing command: %s', cmd)
kwargs.setdefault('stderr', subprocess.STDOUT)
proc = subprocess.Popen(cmd, **kwargs)
stdout, _ = proc.communicate()
LOGGER.debug('Process [%s] returned [%d] with output:\n%s',
cmd, proc.returncode, stdout)
return proc.returncode, stdout
def ensure_managed(dot_gclient_filename):
"""Rewrites a .gclient file to set "managed": True.
Returns:
True if the .gclient file was modified.
"""
with open(dot_gclient_filename) as fh:
contents = fh.read()
new_contents = re.sub(r'("managed"\s*:\s*)False', r'\1True', contents)
if contents != new_contents:
with open(dot_gclient_filename, 'w') as fh:
fh.write(new_contents)
return True
return False
def update_scripts():
if os.environ.get('RUN_SLAVE_UPDATED_SCRIPTS'):
os.environ.pop('RUN_SLAVE_UPDATED_SCRIPTS')
return False
stream = annotator.StructuredAnnotationStream()
with stream.step('update_scripts') as s:
if ensure_managed(os.path.join(env.Build, os.pardir, '.gclient')):
s.step_text('Top-level gclient solution was unmanaged, '
'changed to managed')
gclient_name = 'gclient'
if sys.platform.startswith('win'):
gclient_name += '.bat'
gclient_path = os.path.join(env.Build, os.pardir, 'depot_tools',
gclient_name)
gclient_cmd = [gclient_path, 'sync', '--force', '--verbose', '--jobs=2',
'--break_repo_locks']
try:
fd, output_json = tempfile.mkstemp()
os.close(fd)
gclient_cmd += ['--output-json', output_json]
except Exception:
# Super paranoia try block.
output_json = None
cmd_dict = {
'name': 'update_scripts',
'cmd': gclient_cmd,
'cwd': env.Build,
}
annotator.print_step(cmd_dict, os.environ, stream)
rv, _ = _run_command(gclient_cmd, cwd=env.Build)
if rv != 0:
s.step_text('gclient sync failed!')
s.step_exception()
elif output_json:
try:
with open(output_json, 'r') as f:
gclient_json = json.load(f)
for line in json.dumps(
gclient_json, sort_keys=True,
indent=4, separators=(',', ': ')).splitlines():
s.step_log_line('gclient_json', line)
s.step_log_end('gclient_json')
build_checkout = gclient_json['solutions'].get('build/')
if build_checkout:
s.step_text('%(scm)s - %(revision)s' % build_checkout)
s.set_build_property('build_scm', json.dumps(build_checkout['scm']))
s.set_build_property('build_revision',
json.dumps(build_checkout['revision']))
except Exception as e:
s.step_text('Unable to process gclient JSON %s' % repr(e))
s.step_exception()
finally:
try:
os.remove(output_json)
except Exception as e:
LOGGER.warning("LEAKED: %s", output_json, exc_info=True)
else:
s.step_text('Unable to get SCM data')
s.step_exception()
os.environ['RUN_SLAVE_UPDATED_SCRIPTS'] = '1'
# After running update scripts, set PYTHONIOENCODING=UTF-8 for the real
# annotated_run.
os.environ['PYTHONIOENCODING'] = 'UTF-8'
return True