mirror of
https://github.com/flatcar/scripts.git
synced 2025-08-09 05:56:58 +02:00
Robustify and speed up cros_mark_all_as_stable.
What's new? - cros_mark_all_as_stable is now in Python and has unit tests. - We now detect and report coding errors that can cause incorrect behavior. E.g., if 9999 ebuild or stable ebuild can't be found, we report a hard failure so that developers will know about the problem. - We now check that git hashes we report actually match up with the right repository. - Unified diff of changes are now printed to stdout, so that developers can see a list of the changes and debug any problems. - cros_mark_all_as_stable now takes 2.5 seconds to run. BUG=chromium-os:7795 TEST=Manually examined diff output from run of cros_mark_all_as_stable on full repository. Change-Id: I762597c9b94e5f8e8171b83c966ad54e21a65c1b Review URL: http://codereview.chromium.org/3798003
This commit is contained in:
parent
aa4670315b
commit
6be0f08169
@ -184,19 +184,15 @@ def _UprevFromRevisionList(buildroot, revision_list):
|
|||||||
return
|
return
|
||||||
|
|
||||||
package_str = ''
|
package_str = ''
|
||||||
commit_str = ''
|
|
||||||
for package, revision in revision_list:
|
for package, revision in revision_list:
|
||||||
package_str += package + ' '
|
package_str += package + ' '
|
||||||
commit_str += revision + ' '
|
|
||||||
|
|
||||||
package_str = package_str.strip()
|
package_str = package_str.strip()
|
||||||
commit_str = commit_str.strip()
|
|
||||||
|
|
||||||
cwd = os.path.join(buildroot, 'src', 'scripts')
|
cwd = os.path.join(buildroot, 'src', 'scripts')
|
||||||
RunCommand(['./cros_mark_as_stable',
|
RunCommand(['./cros_mark_as_stable',
|
||||||
'--tracking_branch="cros/master"',
|
'--tracking_branch="cros/master"',
|
||||||
'--packages="%s"' % package_str,
|
'--packages="%s"' % package_str,
|
||||||
'--commit_ids="%s"' % commit_str,
|
|
||||||
'commit'],
|
'commit'],
|
||||||
cwd=cwd, enter_chroot=True)
|
cwd=cwd, enter_chroot=True)
|
||||||
|
|
||||||
@ -204,8 +200,8 @@ def _UprevFromRevisionList(buildroot, revision_list):
|
|||||||
def _UprevAllPackages(buildroot):
|
def _UprevAllPackages(buildroot):
|
||||||
"""Uprevs all packages that have been updated since last uprev."""
|
"""Uprevs all packages that have been updated since last uprev."""
|
||||||
cwd = os.path.join(buildroot, 'src', 'scripts')
|
cwd = os.path.join(buildroot, 'src', 'scripts')
|
||||||
RunCommand(['./cros_mark_all_as_stable',
|
RunCommand(['./cros_mark_as_stable', '--all',
|
||||||
'--tracking_branch="cros/master"'],
|
'--tracking_branch="cros/master"', 'commit'],
|
||||||
cwd=cwd, enter_chroot=True)
|
cwd=cwd, enter_chroot=True)
|
||||||
|
|
||||||
|
|
||||||
|
@ -113,8 +113,8 @@ class CBuildBotTest(mox.MoxTestBase):
|
|||||||
m_file.read().AndReturn(self._test_string)
|
m_file.read().AndReturn(self._test_string)
|
||||||
m_file.close()
|
m_file.close()
|
||||||
|
|
||||||
cbuildbot.RunCommand(['./cros_mark_all_as_stable',
|
cbuildbot.RunCommand(['./cros_mark_as_stable', '--all',
|
||||||
'--tracking_branch="cros/master"'],
|
'--tracking_branch="cros/master"', 'commit'],
|
||||||
cwd='%s/src/scripts' % self._buildroot,
|
cwd='%s/src/scripts' % self._buildroot,
|
||||||
enter_chroot=True)
|
enter_chroot=True)
|
||||||
|
|
||||||
@ -133,8 +133,8 @@ class CBuildBotTest(mox.MoxTestBase):
|
|||||||
m_file.read().AndReturn('None')
|
m_file.read().AndReturn('None')
|
||||||
m_file.close()
|
m_file.close()
|
||||||
|
|
||||||
cbuildbot.RunCommand(['./cros_mark_all_as_stable',
|
cbuildbot.RunCommand(['./cros_mark_as_stable', '--all',
|
||||||
'--tracking_branch="cros/master"'],
|
'--tracking_branch="cros/master"', 'commit'],
|
||||||
cwd='%s/src/scripts' % self._buildroot,
|
cwd='%s/src/scripts' % self._buildroot,
|
||||||
enter_chroot=True)
|
enter_chroot=True)
|
||||||
|
|
||||||
|
@ -1,104 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
|
|
||||||
# Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
|
|
||||||
# Use of this source code is governed by a BSD-style license that can be
|
|
||||||
# found in the LICENSE file.
|
|
||||||
|
|
||||||
# Wrapper scripts around cros_mark_as_stable that marks all packages as stable
|
|
||||||
# that have CROS_WORKON_COMMIT that is different than the current HEAD commit
|
|
||||||
# of the corresponding git repository.
|
|
||||||
|
|
||||||
# Load common constants. This should be the first executable line.
|
|
||||||
# The path to common.sh should be relative to your script's location.
|
|
||||||
. "$(dirname "$0")/common.sh"
|
|
||||||
|
|
||||||
# Load common functions for workon scripts.
|
|
||||||
. "$(dirname "$0")/lib/cros_workon_common.sh"
|
|
||||||
|
|
||||||
get_default_board
|
|
||||||
|
|
||||||
DEFINE_string board "${DEFAULT_BOARD}" \
|
|
||||||
"The board to set package keywords for."
|
|
||||||
DEFINE_string tracking_branch "origin" \
|
|
||||||
"Used with commit to specify branch to track against."
|
|
||||||
|
|
||||||
FLAGS "$@" || exit 1
|
|
||||||
eval set -- "${FLAGS_ARGV}"
|
|
||||||
|
|
||||||
set -e
|
|
||||||
|
|
||||||
BOARD_DIR=/build/"${FLAGS_board}"
|
|
||||||
EQUERYCMD=equery-"${FLAGS_board}"
|
|
||||||
EBUILDCMD=ebuild-"${FLAGS_board}"
|
|
||||||
|
|
||||||
PACKAGES=$( show_workon_ebuilds )
|
|
||||||
|
|
||||||
GRAB_HEAD_COMMIT_CMD="git show HEAD | head -1 | cut -f 2 -d ' '"
|
|
||||||
|
|
||||||
# Packages to mark as stable.
|
|
||||||
PACKAGE_LIST=""
|
|
||||||
# List of commit ids corresponding to package list.
|
|
||||||
COMMIT_ID_LIST=""
|
|
||||||
# List of IFS-delimited ebuilds to ignore.
|
|
||||||
PACKAGE_BLACKLIST=""
|
|
||||||
# File containing the names of blacklisted packages.
|
|
||||||
BLACKLIST_FILE=$(dirname "${0}")/cros_mark_as_stable_blacklist
|
|
||||||
|
|
||||||
[ -f "${BLACKLIST_FILE}" ] && \
|
|
||||||
PACKAGE_BLACKLIST=$(cat "${BLACKLIST_FILE}")
|
|
||||||
|
|
||||||
function package_is_blacklisted() {
|
|
||||||
# Makes a list that looks like "\|package1\|package2\|...packagen".
|
|
||||||
local blist_regex=$(for i in ${PACKAGE_BLACKLIST}; do echo -n "\\|${i}"; done)
|
|
||||||
expr "${1}" : "^\(${blist_regex/\\|/}\)$" &> /dev/null && return 0 || return 1
|
|
||||||
}
|
|
||||||
|
|
||||||
# For each package, compares the head commit id to the commit id in the ebuild.
|
|
||||||
# If they do not match, add the package and its commit id into ${PACKAGE_LIST}
|
|
||||||
# and ${COMMIT_ID_LIST}
|
|
||||||
for package in ${PACKAGES}; do
|
|
||||||
if package_is_blacklisted ${package}; then
|
|
||||||
info "${package} blacklisted, skipping"
|
|
||||||
continue
|
|
||||||
fi
|
|
||||||
# We need to pick up any stable ebuilds for any platform.
|
|
||||||
ebuild_path=$(ACCEPT_KEYWORDS="arm x86 amd64" ${EQUERYCMD} which ${package})\
|
|
||||||
|| continue
|
|
||||||
# Get 9999 ebuild path to see if it got changed.
|
|
||||||
ebuild_9999_path=$(ACCEPT_KEYWORDS="~*" ${EQUERYCMD} which ${package}) \
|
|
||||||
|| continue
|
|
||||||
# Sets ${CROS_WORKON_SRCDIR} from the ebuild.
|
|
||||||
eval $(${EBUILDCMD} ${ebuild_path} info) &> /dev/null || continue
|
|
||||||
head_commit=$( cd "${CROS_WORKON_SRCDIR}" &&\
|
|
||||||
bash -c "${GRAB_HEAD_COMMIT_CMD}" ) || continue
|
|
||||||
egit_commit=$(\
|
|
||||||
eval echo $(grep CROS_WORKON_COMMIT ${ebuild_path} | cut -f 2 -d '=')) ||\
|
|
||||||
echo "No CROS_WORKON_COMMIT found in ${ebuild_path}"
|
|
||||||
if [[ ${head_commit} != ${egit_commit} ]] && \
|
|
||||||
[ -n "${head_commit}" ]; then
|
|
||||||
info\
|
|
||||||
"HEAD ${head_commit} != CROS_WORKON_COMMIT ${egit_commit} for ${package}"
|
|
||||||
PACKAGE_LIST="${PACKAGE_LIST} ${package}"
|
|
||||||
COMMIT_ID_LIST="${COMMIT_ID_LIST} ${head_commit}"
|
|
||||||
elif [[ ${head_commit} = ${egit_commit} ]]; then
|
|
||||||
info "Commit id's match for ${package}, checking for 9999 ebuild change."
|
|
||||||
# egrep succeeds if there are important differences between the ebuilds.
|
|
||||||
if diff "${ebuild_path}" "${ebuild_9999_path}" | \
|
|
||||||
egrep -v "KEYWORDS|CROS_WORKON_COMMIT|^---|^[<>]\ *$|^[0-9]"; then
|
|
||||||
info "Detected 9999 ebuild change for ${package}."
|
|
||||||
PACKAGE_LIST="${PACKAGE_LIST} ${package}"
|
|
||||||
COMMIT_ID_LIST="${COMMIT_ID_LIST} ${egit_commit}"
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
done
|
|
||||||
|
|
||||||
if [ -n "${PACKAGE_LIST}" ] ; then
|
|
||||||
info "Candidate package list ${PACKAGE_LIST}"
|
|
||||||
info "With commit id list ${COMMIT_ID_LIST}"
|
|
||||||
|
|
||||||
./cros_mark_as_stable --board ${FLAGS_board} -p "${PACKAGE_LIST}" \
|
|
||||||
-i "${COMMIT_ID_LIST}" -t ${FLAGS_tracking_branch} commit || \
|
|
||||||
die "Could not mark all packages as stable"
|
|
||||||
else
|
|
||||||
info "No candidate packages to be marked"
|
|
||||||
fi
|
|
@ -14,9 +14,10 @@ import re
|
|||||||
import shutil
|
import shutil
|
||||||
import subprocess
|
import subprocess
|
||||||
import sys
|
import sys
|
||||||
|
from portage.versions import pkgsplit, pkgsplit, vercmp
|
||||||
|
|
||||||
sys.path.append(os.path.join(os.path.dirname(__file__), 'lib'))
|
sys.path.append(os.path.join(os.path.dirname(__file__), 'lib'))
|
||||||
from cros_build_lib import Info, Warning, Die
|
from cros_build_lib import Info, RunCommand, Warning, Die
|
||||||
|
|
||||||
|
|
||||||
gflags.DEFINE_string('board', 'x86-generic',
|
gflags.DEFINE_string('board', 'x86-generic',
|
||||||
@ -38,6 +39,8 @@ gflags.DEFINE_string('srcroot', '%s/trunk/src' % os.environ['HOME'],
|
|||||||
gflags.DEFINE_string('tracking_branch', 'cros/master',
|
gflags.DEFINE_string('tracking_branch', 'cros/master',
|
||||||
'Used with commit to specify branch to track against.',
|
'Used with commit to specify branch to track against.',
|
||||||
short_name='t')
|
short_name='t')
|
||||||
|
gflags.DEFINE_boolean('all', False,
|
||||||
|
'Mark all packages as stable.')
|
||||||
gflags.DEFINE_boolean('verbose', False,
|
gflags.DEFINE_boolean('verbose', False,
|
||||||
'Prints out verbose information about what is going on.',
|
'Prints out verbose information about what is going on.',
|
||||||
short_name='v')
|
short_name='v')
|
||||||
@ -69,22 +72,81 @@ def _Print(message):
|
|||||||
Info(message)
|
Info(message)
|
||||||
|
|
||||||
|
|
||||||
def _BuildEBuildDictionary(overlays, package_list, commit_id_list):
|
def _BestEBuild(ebuilds):
|
||||||
for index in range(len(package_list)):
|
"""Returns the newest EBuild from a list of EBuild objects."""
|
||||||
package = package_list[index]
|
winner = ebuilds[0]
|
||||||
commit_id = ''
|
for ebuild in ebuilds[1:]:
|
||||||
if commit_id_list:
|
if vercmp(winner.version, ebuild.version) < 0:
|
||||||
commit_id = commit_id_list[index]
|
winner = ebuild
|
||||||
ebuild = _EBuild(package, commit_id)
|
return winner
|
||||||
if ebuild.ebuild_path:
|
|
||||||
for overlay in overlays:
|
|
||||||
if ebuild.ebuild_path.startswith(overlay):
|
def _FindStableEBuilds(files):
|
||||||
overlays[overlay].append(ebuild)
|
"""Return a list of stable ebuilds from specified list of files.
|
||||||
break
|
|
||||||
else:
|
Args:
|
||||||
Die('No overlay found for %s' % ebuild.ebuild_path)
|
files: List of files.
|
||||||
else:
|
"""
|
||||||
Die('No ebuild found for %s' % package)
|
workon_dir = False
|
||||||
|
stable_ebuilds = []
|
||||||
|
unstable_ebuilds = []
|
||||||
|
for path in files:
|
||||||
|
if path.endswith('.ebuild') and not os.path.islink(path):
|
||||||
|
ebuild = _EBuild(path)
|
||||||
|
if ebuild.is_workon:
|
||||||
|
workon_dir = True
|
||||||
|
if ebuild.is_stable:
|
||||||
|
stable_ebuilds.append(ebuild)
|
||||||
|
else:
|
||||||
|
unstable_ebuilds.append(ebuild)
|
||||||
|
|
||||||
|
# If we found a workon ebuild in this directory, apply some sanity checks.
|
||||||
|
if workon_dir:
|
||||||
|
if len(unstable_ebuilds) > 1:
|
||||||
|
Die('Found multiple unstable ebuilds in %s' % root)
|
||||||
|
if len(stable_ebuilds) > 1:
|
||||||
|
stable_ebuilds = [_BestEBuild(stable_ebuilds)]
|
||||||
|
|
||||||
|
# Print a warning if multiple stable ebuilds are found in the same
|
||||||
|
# directory. Storing multiple stable ebuilds is error-prone because
|
||||||
|
# the older ebuilds will not get rev'd.
|
||||||
|
#
|
||||||
|
# We make a special exception for x11-drivers/xf86-video-msm for legacy
|
||||||
|
# reasons.
|
||||||
|
if stable_ebuilds[0].package != 'x11-drivers/xf86-video-msm':
|
||||||
|
Warning('Found multiple stable ebuilds in %s' % root)
|
||||||
|
|
||||||
|
if not unstable_ebuilds:
|
||||||
|
Die('Missing 9999 ebuild in %s' % root)
|
||||||
|
if not stable_ebuilds:
|
||||||
|
Die('Missing stable ebuild in %s' % root)
|
||||||
|
|
||||||
|
if stable_ebuilds:
|
||||||
|
return stable_ebuilds[0]
|
||||||
|
else:
|
||||||
|
return None
|
||||||
|
|
||||||
|
|
||||||
|
def _BuildEBuildDictionary(overlays, all, packages):
|
||||||
|
"""Build a dictionary of the ebuilds in the specified overlays.
|
||||||
|
|
||||||
|
overlays: A map which maps overlay directories to arrays of stable EBuilds
|
||||||
|
inside said directories.
|
||||||
|
all: Whether to include all ebuilds in the specified directories. If true,
|
||||||
|
then we gather all packages in the directories regardless of whether
|
||||||
|
they are in our set of packages.
|
||||||
|
packages: A set of the packages we want to gather.
|
||||||
|
"""
|
||||||
|
for overlay in overlays:
|
||||||
|
for root_dir, dirs, files in os.walk(overlay):
|
||||||
|
# Add stable ebuilds to overlays[overlay].
|
||||||
|
paths = [os.path.join(root_dir, path) for path in files]
|
||||||
|
ebuild = _FindStableEBuilds(paths)
|
||||||
|
|
||||||
|
# If the --all option isn't used, we only want to update packages that
|
||||||
|
# are in packages.
|
||||||
|
if ebuild and (all or ebuild.package in packages):
|
||||||
|
overlays[overlay].append(ebuild)
|
||||||
|
|
||||||
|
|
||||||
def _CheckOnStabilizingBranch():
|
def _CheckOnStabilizingBranch():
|
||||||
@ -93,19 +155,16 @@ def _CheckOnStabilizingBranch():
|
|||||||
return current_branch == _STABLE_BRANCH_NAME
|
return current_branch == _STABLE_BRANCH_NAME
|
||||||
|
|
||||||
|
|
||||||
def _CheckSaneArguments(package_list, commit_id_list, command):
|
def _CheckSaneArguments(package_list, command):
|
||||||
"""Checks to make sure the flags are sane. Dies if arguments are not sane."""
|
"""Checks to make sure the flags are sane. Dies if arguments are not sane."""
|
||||||
if not command in _COMMAND_DICTIONARY.keys():
|
if not command in _COMMAND_DICTIONARY.keys():
|
||||||
_PrintUsageAndDie('%s is not a valid command' % command)
|
_PrintUsageAndDie('%s is not a valid command' % command)
|
||||||
if not gflags.FLAGS.packages and command == 'commit':
|
if not gflags.FLAGS.packages and command == 'commit' and not gflags.FLAGS.all:
|
||||||
_PrintUsageAndDie('Please specify at least one package')
|
_PrintUsageAndDie('Please specify at least one package')
|
||||||
if not gflags.FLAGS.board and command == 'commit':
|
if not gflags.FLAGS.board and command == 'commit':
|
||||||
_PrintUsageAndDie('Please specify a board')
|
_PrintUsageAndDie('Please specify a board')
|
||||||
if not os.path.isdir(gflags.FLAGS.srcroot):
|
if not os.path.isdir(gflags.FLAGS.srcroot):
|
||||||
_PrintUsageAndDie('srcroot is not a valid path')
|
_PrintUsageAndDie('srcroot is not a valid path')
|
||||||
if commit_id_list and (len(package_list) != len(commit_id_list)):
|
|
||||||
_PrintUsageAndDie(
|
|
||||||
'Package list is not the same length as the commit id list')
|
|
||||||
|
|
||||||
|
|
||||||
def _Clean():
|
def _Clean():
|
||||||
@ -214,30 +273,76 @@ class _GitBranch(object):
|
|||||||
class _EBuild(object):
|
class _EBuild(object):
|
||||||
"""Wrapper class for an ebuild."""
|
"""Wrapper class for an ebuild."""
|
||||||
|
|
||||||
def __init__(self, package, commit_id=None):
|
def __init__(self, path):
|
||||||
"""Initializes all data about an ebuild.
|
"""Initializes all data about an ebuild.
|
||||||
|
|
||||||
Uses equery to find the ebuild path and sets data about an ebuild for
|
Uses equery to find the ebuild path and sets data about an ebuild for
|
||||||
easy reference.
|
easy reference.
|
||||||
"""
|
"""
|
||||||
self.package = package
|
self.ebuild_path = path
|
||||||
self.ebuild_path = self._FindEBuildPath(package)
|
|
||||||
(self.ebuild_path_no_revision,
|
(self.ebuild_path_no_revision,
|
||||||
self.ebuild_path_no_version,
|
self.ebuild_path_no_version,
|
||||||
self.current_revision) = self._ParseEBuildPath(self.ebuild_path)
|
self.current_revision) = self._ParseEBuildPath(self.ebuild_path)
|
||||||
self.commit_id = commit_id
|
_, self.category, pkgpath, filename = path.rsplit('/', 3)
|
||||||
|
filename_no_suffix = os.path.join(filename.replace('.ebuild', ''))
|
||||||
|
self.pkgname, version_no_rev, rev = pkgsplit(filename_no_suffix)
|
||||||
|
self.version = '%s-%s' % (version_no_rev, rev)
|
||||||
|
self.package = '%s/%s' % (self.category, self.pkgname)
|
||||||
|
self.is_workon = False
|
||||||
|
self.is_stable = False
|
||||||
|
|
||||||
@classmethod
|
for line in fileinput.input(path):
|
||||||
def _FindEBuildPath(cls, package):
|
if line.startswith('inherit ') and 'cros-workon' in line:
|
||||||
"""Static method that returns the full path of an ebuild."""
|
self.is_workon = True
|
||||||
_Print('Looking for unstable ebuild for %s' % package)
|
elif (line.startswith('KEYWORDS=') and '~' not in line and
|
||||||
equery_cmd = (
|
('amd64' in line or 'x86' in line or 'arm' in line)):
|
||||||
'ACCEPT_KEYWORDS="x86 arm amd64" equery-%s which %s 2> /dev/null'
|
self.is_stable = True
|
||||||
% (gflags.FLAGS.board, package))
|
fileinput.close()
|
||||||
path = _SimpleRunCommand(equery_cmd)
|
|
||||||
if path:
|
def GetCommitId(self):
|
||||||
_Print('Unstable ebuild found at %s' % path)
|
"""Get the commit id for this ebuild."""
|
||||||
return path.rstrip()
|
|
||||||
|
# Grab and evaluate CROS_WORKON variables from this ebuild.
|
||||||
|
unstable_ebuild = '%s-9999.ebuild' % self.ebuild_path_no_version
|
||||||
|
cmd = ('CROS_WORKON_LOCALNAME="%s" CROS_WORKON_PROJECT="%s" '
|
||||||
|
'eval $(grep -E "^CROS_WORKON" %s) && '
|
||||||
|
'echo $CROS_WORKON_PROJECT '
|
||||||
|
'$CROS_WORKON_LOCALNAME/$CROS_WORKON_SUBDIR'
|
||||||
|
% (self.pkgname, self.pkgname, unstable_ebuild))
|
||||||
|
project, subdir = _SimpleRunCommand(cmd).split()
|
||||||
|
|
||||||
|
# Calculate srcdir.
|
||||||
|
srcroot = gflags.FLAGS.srcroot
|
||||||
|
if self.category == 'chromeos-base':
|
||||||
|
dir = 'platform'
|
||||||
|
else:
|
||||||
|
dir = 'third_party'
|
||||||
|
srcdir = os.path.join(srcroot, dir, subdir)
|
||||||
|
|
||||||
|
# TODO(anush): This hack is only necessary because the kernel ebuild has
|
||||||
|
# 'if' statements, so we can't grab the CROS_WORKON_LOCALNAME properly.
|
||||||
|
# We should clean up the kernel ebuild and remove this hack.
|
||||||
|
if not os.path.exists(srcdir) and subdir == 'kernel/':
|
||||||
|
srcdir = os.path.join(srcroot, 'third_party/kernel/files')
|
||||||
|
|
||||||
|
if not os.path.exists(srcdir):
|
||||||
|
Die('Cannot find commit id for %s' % self.ebuild_path)
|
||||||
|
|
||||||
|
# Verify that we're grabbing the commit id from the right project name.
|
||||||
|
# NOTE: chromeos-kernel has the wrong project name, so it fails this
|
||||||
|
# check.
|
||||||
|
# TODO(davidjames): Fix the project name in the chromeos-kernel ebuild.
|
||||||
|
cmd = 'cd %s && git config --get remote.cros.projectname' % srcdir
|
||||||
|
actual_project =_SimpleRunCommand(cmd).rstrip()
|
||||||
|
if project not in (actual_project, 'chromeos-kernel'):
|
||||||
|
Die('Project name mismatch for %s (%s != %s)' % (unstable_ebuild, project,
|
||||||
|
actual_project))
|
||||||
|
|
||||||
|
# Get commit id.
|
||||||
|
output = _SimpleRunCommand('cd %s && git rev-parse HEAD' % srcdir)
|
||||||
|
if not output:
|
||||||
|
Die('Missing commit id for %s' % self.ebuild_path)
|
||||||
|
return output.rstrip()
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def _ParseEBuildPath(cls, ebuild_path):
|
def _ParseEBuildPath(cls, ebuild_path):
|
||||||
@ -317,11 +422,21 @@ class EBuildStableMarker(object):
|
|||||||
redirect_file.write(line)
|
redirect_file.write(line)
|
||||||
fileinput.close()
|
fileinput.close()
|
||||||
|
|
||||||
_Print('Adding new stable ebuild to git')
|
# If the new ebuild is identical to the old ebuild, return False and
|
||||||
_SimpleRunCommand('git add %s' % new_ebuild_path)
|
# delete our changes.
|
||||||
|
old_ebuild_path = self._ebuild.ebuild_path
|
||||||
|
diff_cmd = ['diff', '-Bu', old_ebuild_path, new_ebuild_path]
|
||||||
|
if 0 == RunCommand(diff_cmd, exit_code=True,
|
||||||
|
print_cmd=gflags.FLAGS.verbose):
|
||||||
|
os.unlink(new_ebuild_path)
|
||||||
|
return False
|
||||||
|
else:
|
||||||
|
_Print('Adding new stable ebuild to git')
|
||||||
|
_SimpleRunCommand('git add %s' % new_ebuild_path)
|
||||||
|
|
||||||
_Print('Removing old ebuild from git')
|
_Print('Removing old ebuild from git')
|
||||||
_SimpleRunCommand('git rm %s' % self._ebuild.ebuild_path)
|
_SimpleRunCommand('git rm %s' % old_ebuild_path)
|
||||||
|
return True
|
||||||
|
|
||||||
def CommitChange(self, message):
|
def CommitChange(self, message):
|
||||||
"""Commits current changes in git locally.
|
"""Commits current changes in git locally.
|
||||||
@ -352,17 +467,16 @@ def main(argv):
|
|||||||
_PrintUsageAndDie(str(e))
|
_PrintUsageAndDie(str(e))
|
||||||
|
|
||||||
package_list = gflags.FLAGS.packages.split()
|
package_list = gflags.FLAGS.packages.split()
|
||||||
if gflags.FLAGS.commit_ids:
|
_CheckSaneArguments(package_list, command)
|
||||||
commit_id_list = gflags.FLAGS.commit_ids.split()
|
|
||||||
else:
|
|
||||||
commit_id_list = None
|
|
||||||
_CheckSaneArguments(package_list, commit_id_list, command)
|
|
||||||
|
|
||||||
overlays = {
|
overlays = {
|
||||||
'%s/private-overlays/chromeos-overlay' % gflags.FLAGS.srcroot: [],
|
'%s/private-overlays/chromeos-overlay' % gflags.FLAGS.srcroot: [],
|
||||||
'%s/third_party/chromiumos-overlay' % gflags.FLAGS.srcroot: []
|
'%s/third_party/chromiumos-overlay' % gflags.FLAGS.srcroot: []
|
||||||
}
|
}
|
||||||
_BuildEBuildDictionary(overlays, package_list, commit_id_list)
|
all = gflags.FLAGS.all
|
||||||
|
|
||||||
|
if command == 'commit':
|
||||||
|
_BuildEBuildDictionary(overlays, all, package_list)
|
||||||
|
|
||||||
for overlay, ebuilds in overlays.items():
|
for overlay, ebuilds in overlays.items():
|
||||||
if not os.path.exists(overlay):
|
if not os.path.exists(overlay):
|
||||||
@ -374,17 +488,19 @@ def main(argv):
|
|||||||
elif command == 'push':
|
elif command == 'push':
|
||||||
_PushChange()
|
_PushChange()
|
||||||
elif command == 'commit' and ebuilds:
|
elif command == 'commit' and ebuilds:
|
||||||
work_branch = _GitBranch(_STABLE_BRANCH_NAME)
|
|
||||||
work_branch.CreateBranch()
|
|
||||||
if not work_branch.Exists():
|
|
||||||
Die('Unable to create stabilizing branch in %s' % overlay)
|
|
||||||
for ebuild in ebuilds:
|
for ebuild in ebuilds:
|
||||||
try:
|
try:
|
||||||
_Print('Working on %s' % ebuild.package)
|
_Print('Working on %s' % ebuild.package)
|
||||||
worker = EBuildStableMarker(ebuild)
|
worker = EBuildStableMarker(ebuild)
|
||||||
worker.RevEBuild(ebuild.commit_id)
|
commit_id = ebuild.GetCommitId()
|
||||||
message = _GIT_COMMIT_MESSAGE % (ebuild.package, ebuild.commit_id)
|
if worker.RevEBuild(commit_id):
|
||||||
worker.CommitChange(message)
|
if not _CheckOnStabilizingBranch():
|
||||||
|
work_branch = _GitBranch(_STABLE_BRANCH_NAME)
|
||||||
|
work_branch.CreateBranch()
|
||||||
|
if not work_branch.Exists():
|
||||||
|
Die('Unable to create stabilizing branch in %s' % overlay)
|
||||||
|
message = _GIT_COMMIT_MESSAGE % (ebuild.package, commit_id)
|
||||||
|
worker.CommitChange(message)
|
||||||
except (OSError, IOError):
|
except (OSError, IOError):
|
||||||
Warning('Cannot rev %s\n' % ebuild.package,
|
Warning('Cannot rev %s\n' % ebuild.package,
|
||||||
'Note you will have to go into %s '
|
'Note you will have to go into %s '
|
||||||
|
@ -89,46 +89,35 @@ class EBuildTest(mox.MoxTestBase):
|
|||||||
|
|
||||||
def setUp(self):
|
def setUp(self):
|
||||||
mox.MoxTestBase.setUp(self)
|
mox.MoxTestBase.setUp(self)
|
||||||
self.package = 'test_package'
|
|
||||||
self.ebuild_path = '/path/test_package-0.0.1-r1.ebuild'
|
|
||||||
self.ebuild_path_no_rev = '/path/test_package-0.0.1.ebuild'
|
|
||||||
|
|
||||||
def testInit(self):
|
def testInit(self):
|
||||||
self.mox.StubOutWithMock(cros_mark_as_stable._EBuild, '_FindEBuildPath')
|
|
||||||
self.mox.StubOutWithMock(cros_mark_as_stable._EBuild, '_ParseEBuildPath')
|
self.mox.StubOutWithMock(cros_mark_as_stable._EBuild, '_ParseEBuildPath')
|
||||||
|
|
||||||
cros_mark_as_stable._EBuild._FindEBuildPath(
|
ebuild_path = '/overlay/cat/test_package/test_package-0.0.1-r1.ebuild'
|
||||||
self.package).AndReturn(self.ebuild_path)
|
|
||||||
cros_mark_as_stable._EBuild._ParseEBuildPath(
|
cros_mark_as_stable._EBuild._ParseEBuildPath(
|
||||||
self.ebuild_path).AndReturn(['/path/test_package-0.0.1',
|
ebuild_path).AndReturn(['/overlay/cat/test_package-0.0.1',
|
||||||
'/path/test_package',
|
'/overlay/cat/test_package',
|
||||||
1])
|
1])
|
||||||
self.mox.ReplayAll()
|
self.mox.StubOutWithMock(cros_mark_as_stable.fileinput, 'input')
|
||||||
ebuild = cros_mark_as_stable._EBuild(self.package, 'my_id')
|
mock_file = ['EAPI=2', 'CROS_WORKON_COMMIT=old_id',
|
||||||
self.mox.VerifyAll()
|
'KEYWORDS=\"~x86 ~arm\"', 'src_unpack(){}']
|
||||||
self.assertEquals(ebuild.package, self.package)
|
cros_mark_as_stable.fileinput.input(ebuild_path).AndReturn(mock_file)
|
||||||
self.assertEquals(ebuild.ebuild_path, self.ebuild_path)
|
|
||||||
self.assertEquals(ebuild.ebuild_path_no_revision,
|
|
||||||
'/path/test_package-0.0.1')
|
|
||||||
self.assertEquals(ebuild.ebuild_path_no_version, '/path/test_package')
|
|
||||||
self.assertEquals(ebuild.current_revision, 1)
|
|
||||||
self.assertEquals(ebuild.commit_id, 'my_id')
|
|
||||||
|
|
||||||
def testFindEBuildPath(self):
|
|
||||||
self.mox.StubOutWithMock(cros_mark_as_stable, '_SimpleRunCommand')
|
|
||||||
cmd = ('ACCEPT_KEYWORDS="x86 arm amd64" '
|
|
||||||
'equery-x86-generic which %s 2> /dev/null')
|
|
||||||
cros_mark_as_stable._SimpleRunCommand(cmd % self.package).AndReturn(
|
|
||||||
self.ebuild_path)
|
|
||||||
self.mox.ReplayAll()
|
self.mox.ReplayAll()
|
||||||
path = cros_mark_as_stable._EBuild._FindEBuildPath(self.package)
|
ebuild = cros_mark_as_stable._EBuild(ebuild_path)
|
||||||
self.mox.VerifyAll()
|
self.mox.VerifyAll()
|
||||||
self.assertEquals(path, self.ebuild_path)
|
self.assertEquals(ebuild.package, 'cat/test_package')
|
||||||
|
self.assertEquals(ebuild.ebuild_path, ebuild_path)
|
||||||
|
self.assertEquals(ebuild.ebuild_path_no_revision,
|
||||||
|
'/overlay/cat/test_package-0.0.1')
|
||||||
|
self.assertEquals(ebuild.ebuild_path_no_version,
|
||||||
|
'/overlay/cat/test_package')
|
||||||
|
self.assertEquals(ebuild.current_revision, 1)
|
||||||
|
|
||||||
def testParseEBuildPath(self):
|
def testParseEBuildPath(self):
|
||||||
# Test with ebuild with revision number.
|
# Test with ebuild with revision number.
|
||||||
no_rev, no_version, revision = cros_mark_as_stable._EBuild._ParseEBuildPath(
|
no_rev, no_version, revision = cros_mark_as_stable._EBuild._ParseEBuildPath(
|
||||||
self.ebuild_path)
|
'/path/test_package-0.0.1-r1.ebuild')
|
||||||
self.assertEquals(no_rev, '/path/test_package-0.0.1')
|
self.assertEquals(no_rev, '/path/test_package-0.0.1')
|
||||||
self.assertEquals(no_version, '/path/test_package')
|
self.assertEquals(no_version, '/path/test_package')
|
||||||
self.assertEquals(revision, 1)
|
self.assertEquals(revision, 1)
|
||||||
@ -136,7 +125,7 @@ class EBuildTest(mox.MoxTestBase):
|
|||||||
def testParseEBuildPathNoRevisionNumber(self):
|
def testParseEBuildPathNoRevisionNumber(self):
|
||||||
# Test with ebuild without revision number.
|
# Test with ebuild without revision number.
|
||||||
no_rev, no_version, revision = cros_mark_as_stable._EBuild._ParseEBuildPath(
|
no_rev, no_version, revision = cros_mark_as_stable._EBuild._ParseEBuildPath(
|
||||||
self.ebuild_path_no_rev)
|
'/path/test_package-0.0.1.ebuild')
|
||||||
self.assertEquals(no_rev, '/path/test_package-0.0.1')
|
self.assertEquals(no_rev, '/path/test_package-0.0.1')
|
||||||
self.assertEquals(no_version, '/path/test_package')
|
self.assertEquals(no_version, '/path/test_package')
|
||||||
self.assertEquals(revision, 0)
|
self.assertEquals(revision, 0)
|
||||||
@ -147,6 +136,8 @@ class EBuildStableMarkerTest(mox.MoxTestBase):
|
|||||||
def setUp(self):
|
def setUp(self):
|
||||||
mox.MoxTestBase.setUp(self)
|
mox.MoxTestBase.setUp(self)
|
||||||
self.mox.StubOutWithMock(cros_mark_as_stable, '_SimpleRunCommand')
|
self.mox.StubOutWithMock(cros_mark_as_stable, '_SimpleRunCommand')
|
||||||
|
self.mox.StubOutWithMock(cros_mark_as_stable, 'RunCommand')
|
||||||
|
self.mox.StubOutWithMock(os, 'unlink')
|
||||||
self.m_ebuild = self.mox.CreateMock(cros_mark_as_stable._EBuild)
|
self.m_ebuild = self.mox.CreateMock(cros_mark_as_stable._EBuild)
|
||||||
self.m_ebuild.package = 'test_package'
|
self.m_ebuild.package = 'test_package'
|
||||||
self.m_ebuild.current_revision = 1
|
self.m_ebuild.current_revision = 1
|
||||||
@ -175,6 +166,10 @@ class EBuildStableMarkerTest(mox.MoxTestBase):
|
|||||||
m_file.write('CROS_WORKON_COMMIT="my_id"\n')
|
m_file.write('CROS_WORKON_COMMIT="my_id"\n')
|
||||||
m_file.write('KEYWORDS="x86 arm"')
|
m_file.write('KEYWORDS="x86 arm"')
|
||||||
m_file.write('src_unpack(){}')
|
m_file.write('src_unpack(){}')
|
||||||
|
diff_cmd = ['diff', '-Bu', self.m_ebuild.ebuild_path,
|
||||||
|
self.revved_ebuild_path]
|
||||||
|
cros_mark_as_stable.RunCommand(diff_cmd, exit_code=True,
|
||||||
|
print_cmd=False).AndReturn(1)
|
||||||
cros_mark_as_stable._SimpleRunCommand('git add ' + self.revved_ebuild_path)
|
cros_mark_as_stable._SimpleRunCommand('git add ' + self.revved_ebuild_path)
|
||||||
cros_mark_as_stable._SimpleRunCommand('git rm ' + self.m_ebuild.ebuild_path)
|
cros_mark_as_stable._SimpleRunCommand('git rm ' + self.m_ebuild.ebuild_path)
|
||||||
|
|
||||||
@ -183,6 +178,37 @@ class EBuildStableMarkerTest(mox.MoxTestBase):
|
|||||||
marker.RevEBuild('my_id', redirect_file=m_file)
|
marker.RevEBuild('my_id', redirect_file=m_file)
|
||||||
self.mox.VerifyAll()
|
self.mox.VerifyAll()
|
||||||
|
|
||||||
|
def testRevUnchangedEBuild(self):
|
||||||
|
self.mox.StubOutWithMock(cros_mark_as_stable.fileinput, 'input')
|
||||||
|
self.mox.StubOutWithMock(cros_mark_as_stable.os.path, 'exists')
|
||||||
|
self.mox.StubOutWithMock(cros_mark_as_stable.shutil, 'copyfile')
|
||||||
|
m_file = self.mox.CreateMock(file)
|
||||||
|
|
||||||
|
# Prepare mock fileinput. This tests to make sure both the commit id
|
||||||
|
# and keywords are changed correctly.
|
||||||
|
mock_file = ['EAPI=2', 'CROS_WORKON_COMMIT=old_id',
|
||||||
|
'KEYWORDS=\"~x86 ~arm\"', 'src_unpack(){}']
|
||||||
|
|
||||||
|
ebuild_9999 = self.m_ebuild.ebuild_path_no_version + '-9999.ebuild'
|
||||||
|
cros_mark_as_stable.os.path.exists(ebuild_9999).AndReturn(True)
|
||||||
|
cros_mark_as_stable.shutil.copyfile(ebuild_9999, self.revved_ebuild_path)
|
||||||
|
cros_mark_as_stable.fileinput.input(self.revved_ebuild_path,
|
||||||
|
inplace=1).AndReturn(mock_file)
|
||||||
|
m_file.write('EAPI=2')
|
||||||
|
m_file.write('CROS_WORKON_COMMIT="my_id"\n')
|
||||||
|
m_file.write('KEYWORDS="x86 arm"')
|
||||||
|
m_file.write('src_unpack(){}')
|
||||||
|
diff_cmd = ['diff', '-Bu', self.m_ebuild.ebuild_path,
|
||||||
|
self.revved_ebuild_path]
|
||||||
|
cros_mark_as_stable.RunCommand(diff_cmd, exit_code=True,
|
||||||
|
print_cmd=False).AndReturn(0)
|
||||||
|
cros_mark_as_stable.os.unlink(self.revved_ebuild_path)
|
||||||
|
|
||||||
|
self.mox.ReplayAll()
|
||||||
|
marker = cros_mark_as_stable.EBuildStableMarker(self.m_ebuild)
|
||||||
|
marker.RevEBuild('my_id', redirect_file=m_file)
|
||||||
|
self.mox.VerifyAll()
|
||||||
|
|
||||||
def testRevMissingEBuild(self):
|
def testRevMissingEBuild(self):
|
||||||
self.mox.StubOutWithMock(cros_mark_as_stable.fileinput, 'input')
|
self.mox.StubOutWithMock(cros_mark_as_stable.fileinput, 'input')
|
||||||
self.mox.StubOutWithMock(cros_mark_as_stable.os.path, 'exists')
|
self.mox.StubOutWithMock(cros_mark_as_stable.os.path, 'exists')
|
||||||
@ -205,6 +231,10 @@ class EBuildStableMarkerTest(mox.MoxTestBase):
|
|||||||
m_file.write('CROS_WORKON_COMMIT="my_id"\n')
|
m_file.write('CROS_WORKON_COMMIT="my_id"\n')
|
||||||
m_file.write('KEYWORDS="x86 arm"')
|
m_file.write('KEYWORDS="x86 arm"')
|
||||||
m_file.write('src_unpack(){}')
|
m_file.write('src_unpack(){}')
|
||||||
|
diff_cmd = ['diff', '-Bu', self.m_ebuild.ebuild_path,
|
||||||
|
self.revved_ebuild_path]
|
||||||
|
cros_mark_as_stable.RunCommand(diff_cmd, exit_code=True,
|
||||||
|
print_cmd=False).AndReturn(1)
|
||||||
cros_mark_as_stable._SimpleRunCommand('git add ' + self.revved_ebuild_path)
|
cros_mark_as_stable._SimpleRunCommand('git add ' + self.revved_ebuild_path)
|
||||||
cros_mark_as_stable._SimpleRunCommand('git rm ' + self.m_ebuild.ebuild_path)
|
cros_mark_as_stable._SimpleRunCommand('git rm ' + self.m_ebuild.ebuild_path)
|
||||||
|
|
||||||
@ -231,49 +261,44 @@ class EBuildStableMarkerTest(mox.MoxTestBase):
|
|||||||
#self.mox.VerifyAll()
|
#self.mox.VerifyAll()
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class _Package(object):
|
||||||
|
def __init__(self, package):
|
||||||
|
self.package = package
|
||||||
|
|
||||||
|
|
||||||
class BuildEBuildDictionaryTest(mox.MoxTestBase):
|
class BuildEBuildDictionaryTest(mox.MoxTestBase):
|
||||||
|
|
||||||
def setUp(self):
|
def setUp(self):
|
||||||
mox.MoxTestBase.setUp(self)
|
mox.MoxTestBase.setUp(self)
|
||||||
self.mox.StubOutWithMock(cros_mark_as_stable, '_SimpleRunCommand')
|
self.mox.StubOutWithMock(cros_mark_as_stable.os, 'walk')
|
||||||
self.ebuild_path = '/path/test_package-0.0.1-r1.ebuild'
|
self.mox.StubOutWithMock(cros_mark_as_stable, 'RunCommand')
|
||||||
self.package = "test_package"
|
self.package = 'chromeos-base/test_package'
|
||||||
|
self.root = '/overlay/chromeos-base/test_package'
|
||||||
|
self.package_path = self.root + '/test_package-0.0.1.ebuild'
|
||||||
|
paths = [[self.root, [], []]]
|
||||||
|
cros_mark_as_stable.os.walk("/overlay").AndReturn(paths)
|
||||||
|
self.mox.StubOutWithMock(cros_mark_as_stable, '_FindStableEBuilds')
|
||||||
|
|
||||||
def testValidPackage(self):
|
|
||||||
overlays = {"/path": []}
|
def testWantedPackage(self):
|
||||||
cmd = ('ACCEPT_KEYWORDS="x86 arm amd64" '
|
overlays = {"/overlay": []}
|
||||||
'equery-x86-generic which %s 2> /dev/null' % self.package)
|
package = _Package(self.package)
|
||||||
cros_mark_as_stable._SimpleRunCommand(cmd).AndReturn(self.ebuild_path)
|
cros_mark_as_stable._FindStableEBuilds([]).AndReturn(package)
|
||||||
self.mox.ReplayAll()
|
self.mox.ReplayAll()
|
||||||
cros_mark_as_stable._BuildEBuildDictionary(overlays, [self.package], [])
|
cros_mark_as_stable._BuildEBuildDictionary(overlays, False, [self.package])
|
||||||
self.assertEquals(len(overlays), 1)
|
|
||||||
self.assertEquals(overlays["/path"][0].package, self.package)
|
|
||||||
self.mox.VerifyAll()
|
self.mox.VerifyAll()
|
||||||
|
|
||||||
def testPackageInDifferentOverlay(self):
|
|
||||||
self.mox.StubOutWithMock(cros_mark_as_stable, 'Die')
|
|
||||||
cros_mark_as_stable.Die("No overlay found for %s" % self.ebuild_path)
|
|
||||||
cmd = ('ACCEPT_KEYWORDS="x86 arm amd64" '
|
|
||||||
'equery-x86-generic which %s 2> /dev/null' % self.package)
|
|
||||||
cros_mark_as_stable._SimpleRunCommand(cmd).AndReturn(self.ebuild_path)
|
|
||||||
overlays = {"/newpath": []}
|
|
||||||
self.mox.ReplayAll()
|
|
||||||
cros_mark_as_stable._BuildEBuildDictionary(overlays, [self.package], [])
|
|
||||||
self.assertEquals(len(overlays), 1)
|
self.assertEquals(len(overlays), 1)
|
||||||
self.assertEquals(overlays["/newpath"], [])
|
self.assertEquals(overlays["/overlay"], [package])
|
||||||
self.mox.VerifyAll()
|
|
||||||
|
|
||||||
def testMissingPackage(self):
|
def testUnwantedPackage(self):
|
||||||
self.mox.StubOutWithMock(cros_mark_as_stable, 'Die')
|
overlays = {"/overlay": []}
|
||||||
cros_mark_as_stable.Die("No ebuild found for %s" % self.package)
|
package = _Package(self.package)
|
||||||
cmd = ('ACCEPT_KEYWORDS="x86 arm amd64" '
|
cros_mark_as_stable._FindStableEBuilds([]).AndReturn(package)
|
||||||
'equery-x86-generic which %s 2> /dev/null' % self.package)
|
|
||||||
cros_mark_as_stable._SimpleRunCommand(cmd).AndReturn("")
|
|
||||||
self.mox.ReplayAll()
|
self.mox.ReplayAll()
|
||||||
overlays = {"/path": []}
|
cros_mark_as_stable._BuildEBuildDictionary(overlays, False, [])
|
||||||
cros_mark_as_stable._BuildEBuildDictionary(overlays, [self.package], [])
|
|
||||||
self.assertEquals(len(overlays), 1)
|
self.assertEquals(len(overlays), 1)
|
||||||
self.assertEquals(overlays["/path"], [])
|
self.assertEquals(overlays["/overlay"], [])
|
||||||
self.mox.VerifyAll()
|
self.mox.VerifyAll()
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user