Пример #1
0
    def bump_and_tag(repo, attempt, config, relbranch, revision, tags,
                     defaultBranch):
        relbranchChangesets = len(tags)
        defaultBranchChangesets = 0

        if relbranch in get_branches(reponame):
            update(reponame, revision=relbranch)
        else:
            update(reponame, revision=revision)
            run_cmd(['hg', 'branch', relbranch], cwd=reponame)

        if len(bumpFiles) > 0:
            # Bump files on the relbranch, if necessary
            bump(reponame, bumpFiles, 'version')
            run_cmd(['hg', 'diff'], cwd=repo)
            try:
                get_output(['hg', 'commit', '-u', config['hgUsername'],
                            '-m', getBumpCommitMessage(config['productName'], config['version'])],
                           cwd=reponame)
                relbranchChangesets += 1
                revision = get_revision(reponame)
            except subprocess.CalledProcessError, e:
                # We only want to ignore exceptions caused by having nothing to
                # commit, which are OK. We still want to raise exceptions caused
                # by any other thing.
                if e.returncode != 1 or "nothing changed" not in e.output:
                    raise
Пример #2
0
def tagRepo(config, repo, reponame, revision, tags, bumpFiles, relbranch,
            pushAttempts, defaultBranch='default'):
    remote = make_hg_url(HG, repo)
    mercurial(remote, reponame)

    def bump_and_tag(repo, attempt, config, relbranch, revision, tags,
                     defaultBranch):
        # set relbranchChangesets=1 because tag() generates exactly 1 commit
        relbranchChangesets = 1
        defaultBranchChangesets = 0

        if relbranch in get_branches(reponame):
            update(reponame, revision=relbranch)
        else:
            update(reponame, revision=revision)
            run_cmd(['hg', 'branch', relbranch], cwd=reponame)

        if len(bumpFiles) > 0:
            # Bump files on the relbranch, if necessary
            bump(reponame, bumpFiles, 'version')
            run_cmd(['hg', 'diff'], cwd=repo)
            try:
                get_output(['hg', 'commit', '-u', config['hgUsername'],
                            '-m', getBumpCommitMessage(config['productName'], config['version'])],
                           cwd=reponame)
                relbranchChangesets += 1
            except subprocess.CalledProcessError, e:
                # We only want to ignore exceptions caused by having nothing to
                # commit, which are OK. We still want to raise exceptions caused
                # by any other thing.
                if e.returncode != 1 or "nothing changed" not in e.output:
                    raise

        # We always want our tags pointing at the tip of the relbranch
        # so we need to grab the current revision after we've switched
        # branches and bumped versions.
        revision = get_revision(reponame)
        # Create the desired tags on the relbranch
        tag(repo, revision, tags, config['hgUsername'])

        # This is the bump of the version on the default branch
        # We do it after the other one in order to get the tip of the
        # repository back on default, thus avoiding confusion.
        if len(bumpFiles) > 0:
            update(reponame, revision=defaultBranch)
            bump(reponame, bumpFiles, 'nextVersion')
            run_cmd(['hg', 'diff'], cwd=repo)
            try:
                get_output(['hg', 'commit', '-u', config['hgUsername'],
                            '-m', getBumpCommitMessage(config['productName'], config['version'])],
                           cwd=reponame)
                defaultBranchChangesets += 1
            except subprocess.CalledProcessError, e:
                if e.returncode != 1 or "nothing changed" not in e.output:
                    raise
Пример #3
0
def tagRepo(config, repo, reponame, revision, tags, bumpFiles, relbranch,
            pushAttempts):
    remote = make_hg_url(HG, repo)
    mercurial(remote, reponame)

    def bump_and_tag(repo, attempt, config, relbranch, revision, tags):
        # set relbranchChangesets=1 because tag() generates exactly 1 commit
        relbranchChangesets = 1

        if relbranch in get_branches(reponame):
            update(reponame, revision=relbranch)
        else:
            update(reponame, revision=revision)
            run_cmd(['hg', 'branch', relbranch], cwd=reponame)

        if len(bumpFiles) > 0:
            # Bump files on the relbranch, if necessary
            bump(reponame, bumpFiles, 'version')
            run_cmd(['hg', 'diff'], cwd=repo)
            try:
                get_output([
                    'hg', 'commit', '-u', config['hgUsername'], '-m',
                    getBumpCommitMessage(config['productName'],
                                         config['version'])
                ],
                           cwd=reponame)
                relbranchChangesets += 1
            except subprocess.CalledProcessError, e:
                # We only want to ignore exceptions caused by having nothing to
                # commit, which are OK. We still want to raise exceptions caused
                # by any other thing.
                if e.returncode != 1 or "nothing changed" not in e.output:
                    raise

        # We always want our tags pointing at the tip of the relbranch
        # so we need to grab the current revision after we've switched
        # branches and bumped versions.
        revision = get_revision(reponame)
        # Create the desired tags on the relbranch
        tag(repo, revision, tags, config['hgUsername'])

        # Validate that the repository is only different from the remote in
        # ways we expect.
        outgoingRevs = out(src=reponame,
                           remote=remote,
                           ssh_username=config['hgUsername'],
                           ssh_key=config['hgSshKey'])

        if len([r for r in outgoingRevs if r[BRANCH] == relbranch
                ]) != relbranchChangesets:
            raise Exception("Incorrect number of revisions on %s" % relbranch)
        if len(outgoingRevs) != relbranchChangesets:
            raise Exception("Wrong number of outgoing revisions")
Пример #4
0
 def process(self):
     """
     Process this patchset, doing the following:
         1. Check permissions on patchset
         2. Clone the repository
         3. Apply patches, with 3 attempts
     """
     # 1. Check permissions on each patch
     outgoing = self.branch if not self.try_run else 'try'
     if not has_sufficient_permissions(self.user, outgoing):
         log.error('Insufficient permissions to push to %s.' % (outgoing))
         self.add_comment('Insufficient permissions to push to %s.' %
                          (outgoing))
         return (False, '\n'.join(self.comments))
     # 2. Clone the repository
     cloned_rev = None
     try:
         cloned_rev = clone_branch(self.branch, self.branch_url)
     except RetryException:
         log.error('[Branch %s] Could not clone from %s.' %
                   (self.branch, self.branch_url))
         self.add_comment('An error occurred while cloning %s.' %
                          (self.branch_url))
         return (False, '\n'.join(self.comments))
     # 3. Apply patches, with 3 attempts
     try:
         # make 3 attempts so that
         # 1st is on current clone,
         # 2nd attempt is after an update -C,
         # 3rd attempt is a fresh clone
         retry(apply_and_push,
               attempts=3,
               retry_exceptions=(RetryException, ),
               cleanup=RepoCleanup(self.branch, self.branch_url),
               args=(self.active_repo, self.push_url, self.apply_patches,
                     1),
               kwargs=dict(ssh_username=config['hg_username'],
                           ssh_key=config['hg_ssh_key'],
                           force=self.try_run))  # force only on try
         revision = get_revision(self.active_repo)
         shutil.rmtree(self.active_repo)
         for patch in self.patches:
             patch.delete()
     except (HgUtilError, RetryException, FailException), err:
         # Failed
         log.error('[PatchSet] Could not be applied and pushed.\n%s' %
                   (err))
         self.add_comment('Patchset could not be applied and pushed.'
                          '\n%s' % (err))
         return (False, '\n'.join(self.comments))
Пример #5
0
 def process(self):
     """
     Process this patchset, doing the following:
         1. Check permissions on patchset
         2. Clone the repository
         3. Apply patches, with 3 attempts
     """
     # 1. Check permissions on each patch
     outgoing = self.branch if not self.try_run else 'try'
     if not has_sufficient_permissions(self.user, outgoing):
         log.error('Insufficient permissions to push to %s.'
                 % (outgoing))
         self.add_comment('Insufficient permissions to push to %s.'
                 % (outgoing))
         return (False, '\n'.join(self.comments))
     # 2. Clone the repository
     cloned_rev = None
     try:
         cloned_rev = clone_branch(self.branch, self.branch_url)
     except RetryException:
         log.error('[Branch %s] Could not clone from %s.'
                 % (self.branch, self.branch_url))
         self.add_comment('An error occurred while cloning %s.'
                 % (self.branch_url))
         return (False, '\n'.join(self.comments))
     # 3. Apply patches, with 3 attempts
     try:
         # make 3 attempts so that
         # 1st is on current clone,
         # 2nd attempt is after an update -C,
         # 3rd attempt is a fresh clone
         retry(apply_and_push, attempts=3,
                 retry_exceptions=(RetryException,),
                 cleanup=RepoCleanup(self.branch, self.branch_url),
                 args=(self.active_repo, self.push_url,
                       self.apply_patches, 1),
                 kwargs=dict(ssh_username=config['hg_username'],
                             ssh_key=config['hg_ssh_key'],
                             force=self.try_run))    # force only on try
         revision = get_revision(self.active_repo)
         shutil.rmtree(self.active_repo)
         for patch in self.patches:
             patch.delete()
     except (HgUtilError, RetryException, FailException), err:
         # Failed
         log.error('[PatchSet] Could not be applied and pushed.\n%s'
                 % (err))
         self.add_comment('Patchset could not be applied and pushed.'
                          '\n%s' % (err))
         return (False, '\n'.join(self.comments))
Пример #6
0
def tagRepo(config, repo, reponame, revision, tags, bumpFiles, relbranch,
            pushAttempts):
    remote = make_hg_url(HG, repo)
    mercurial(remote, reponame)

    def bump_and_tag(repo, attempt, config, relbranch, revision, tags):
        # set relbranchChangesets=1 because tag() generates exactly 1 commit
        relbranchChangesets = 1

        if relbranch in get_branches(reponame):
            update(reponame, revision=relbranch)
        else:
            update(reponame, revision=revision)
            run_cmd(['hg', 'branch', relbranch], cwd=reponame)

        if len(bumpFiles) > 0:
            # Bump files on the relbranch, if necessary
            bump(reponame, bumpFiles, 'version')
            run_cmd(['hg', 'diff'], cwd=repo)
            try:
                get_output(['hg', 'commit', '-u', config['hgUsername'],
                            '-m', getBumpCommitMessage(config['productName'], config['version'])],
                           cwd=reponame)
                relbranchChangesets += 1
            except subprocess.CalledProcessError, e:
                # We only want to ignore exceptions caused by having nothing to
                # commit, which are OK. We still want to raise exceptions caused
                # by any other thing.
                if e.returncode != 1 or "nothing changed" not in e.output:
                    raise

        # We always want our tags pointing at the tip of the relbranch
        # so we need to grab the current revision after we've switched
        # branches and bumped versions.
        revision = get_revision(reponame)
        # Create the desired tags on the relbranch
        tag(repo, revision, tags, config['hgUsername'])

        # Validate that the repository is only different from the remote in
        # ways we expect.
        outgoingRevs = out(src=reponame, remote=remote,
                           ssh_username=config['hgUsername'],
                           ssh_key=config['hgSshKey'])

        if len([r for r in outgoingRevs if r[BRANCH] == relbranch]) != relbranchChangesets:
            raise Exception("Incorrect number of revisions on %s" % relbranch)
        if len(outgoingRevs) != relbranchChangesets:
            raise Exception("Wrong number of outgoing revisions")
Пример #7
0
def import_and_push(repo, bug, branch_name, patch_ids, patches_dir,
                    add_try_commit, try_syntax, pull_repo, push_repo,
                    ssh_username, ssh_key):

    def changer(repo, attempt):
        log.debug("Importing patches, attemp #%s", attempt)
        import_patches(bug=bug, branch_name=branch_name, patch_ids=patch_ids,
                       patches_dir=patches_dir, repo=repo,
                       add_try_commit=add_try_commit,
                       pull_repo=pull_repo, try_syntax=try_syntax)

    setup_repo(repo=repo, pull_repo=pull_repo)
    apply_and_push(localrepo=repo, remote=push_repo, changer=changer,
                   max_attempts=10, ssh_username=ssh_username, ssh_key=ssh_key,
                   force=False)
    return get_revision(repo)
Пример #8
0
def process_patchset(data):
    """
    Process, apply, and push the patchset to the correct location.
    If try_run is specified, it will be pushed to try, and otherwise
    will be pushed to branch if the credentials are correct.

    process_patchset returns a 2-tuple, (return_code, comment).
    Comment will be none in the case of an error, as the message is sent
    out by process_patchset.
    There should always be a comment posted.
    """
    active_repo = os.path.join('active/%s' % (data['branch']))
    try_run = (data['try_run'] == True)
    if 'push_url' in data:
        push_url = data['push_url']
    else:
        push_url = data['branch_url']
    push_url = push_url.replace('https', 'ssh', 1)

    # The comment header. The comment is constructed incrementally at any possible
    # failure/success point.
    comment_hdr = ['Autoland Patchset:\n\tPatches: %s\n\tBranch: %s%s\n\tDestination: %s'
            % (', '.join(map(lambda x: str(x['id']), data['patches'])), data['branch'],
               (' => try' if try_run else ''), push_url )]
    comment = comment_hdr

    class RETRY(Exception):
        pass

    def cleanup_wrapper():
        # use an attribute full_clean in order to keep track of
        # whether or not a full cleanup is required.
        # This is done since cleanup_wrapper's scope doesn't let us
        # access process_patchset globals, given the way it is used.
        if not hasattr(cleanup_wrapper, 'full_clean'):
            cleanup_wrapper.full_clean = False
        if not hasattr(cleanup_wrapper, 'branch'):
            cleanup_wrapper.branch = data['branch']
        if cleanup_wrapper.branch != data['branch']:
            cleanup_wrapper.full_clean = False
            cleanup_wrapper.branch = data['branch']
        # only wipe the repositories every second cleanup
        if cleanup_wrapper.full_clean:
            clear_branch(data['branch'])
            log_msg('Wiped repositories for: %s' % data['branch'])
        else:
            active_repo = os.path.join('active', data['branch'])
            update(active_repo)
            log_msg('Update -C on active repo for: %s' % data['branch'])
        cleanup_wrapper.full_clean = not cleanup_wrapper.full_clean

        clone_revision = clone_branch(data['branch'], data['branch_url'])
        if clone_revision == None:
            # TODO: Handle clone error
            log_msg('[HgPusher] Clone error...')
        return

    def apply_patchset(dir, attempt):
        if not clone_branch(data['branch'], data['branch_url']):
            msg = 'Branch %s could not be cloned.'
            log_msg('[Branch %s] Could not clone from %s.' \
                    % (data['branch'], data['branch_url']))
            comment.append(msg)
            raise RETRY

        for patch in data['patches']:
            log_msg("Getting patch %s" % (patch['id']), None)
            # store patches in 'patches/' below work_dir
            patch_file = bz.get_patch(patch['id'],
                    os.path.join('patches'),create_path=True)
            if not patch_file:
                msg = 'Patch %s could not be fetched.' % (patch['id'])
                log_msg(msg)
                if msg not in comment:
                    comment.append(msg)
                raise RETRY
            valid_header = has_valid_header(patch_file)
            if not try_run and not valid_header:
                log_msg('[Patch %s] Invalid header.' % (patch['id']))
                # append comment to comment
                msg = 'Patch %s does not have a properly formatted header.' \
                        % (patch['id'])
                if msg not in comment:
                    comment.append(msg)
                raise RETRY

            user = None
            if not valid_header:
                # This is a try run, since we haven't exited
                # so author header not needed. Place in the author information
                # from bugzilla as committer.
                user='******' % (patch['author']['name'], patch['author']['email'])

            (patch_success,err) = import_patch(active_repo, patch_file,
                    try_run, bug_id=data.get('bug_id', None),
                    user=user, try_syntax=data.get('try_syntax', None))
            if patch_success != 0:
                log_msg('[Patch %s] %s' % (patch['id'], err))
                msg = 'Error applying patch %s to %s.\n%s' \
                        % (patch['id'], data['branch'], err)
                if msg not in comment:
                    comment.append(msg)
                raise RETRY
        return True

    if not has_sufficient_permissions(data['patches'],
            data['branch'] if not try_run else 'try'):
        msg = 'Insufficient permissions to push to %s' \
                % ((data['branch'] if not try_run else 'try'))
        log_msg(msg)
        comment.append(msg)
        log_msg('Comment "%s" to bug %s' % ('\n'.join(comment), data['bug_id']), log.DEBUG)
        return (False, '\n'.join(comment))

    try:
        retry(apply_and_push, cleanup=cleanup_wrapper,
                retry_exceptions=(RETRY,),
                args=(active_repo, push_url, apply_patchset, 1),
                kwargs=dict(ssh_username=config['hg_username'],
                            ssh_key=config['hg_ssh_key'],
                            force=try_run))     # Force only on try pushes
        revision = get_revision(active_repo)
        shutil.rmtree(active_repo)
    except (HgUtilError, RETRY) as error:
        msg = 'Could not apply and push patchset:\n%s' % (error)
        log_msg('[PatchSet] %s' % (msg))
        comment.append(msg)
        log_msg('Comment "%s" to bug %s' % ('\n'.join(comment), data['bug_id']), log.DEBUG)
        # TODO need to remove whiteboard tag here or in autoland_queue?
        return (False, '\n'.join(comment))

    # Successful push. Clear any errors that might be in the comments
    comment = comment_hdr

    if try_run:
        # comment to bug with link to the try run on self-serve
        comment.append('Try run started, revision %s. To cancel or monitor the job, see: %s'
                % (revision, os.path.join(config['self_serve_url'],
                                          'try/rev/%s' % (revision))) )
    else:
        comment.append('Successfully applied and pushed patchset.\n\tRevision: %s'
                % (revision, data['branch'],
                   ', '.join(map(lambda x: x['id'], data['patches']))))
        comment.append('To monitor the commit, see: %s'
                % (os.path.join(config['self_serve_url'],
                   '%s/rev/%s' % (data['branch'], revision))))

    log_msg('Comment %s to bug %s' % ('\n'.join(comment), data['bug_id']), log.DEBUG)
    return (revision, '\n'.join(comment))
Пример #9
0
def main():
    logging.basicConfig(format="%(asctime)s - %(message)s", level=logging.INFO)
    parser = argparse.ArgumentParser()
    parser.add_argument("--from-dir", default="mozilla-beta",
                        help="Working directory of repo to be merged from")
    parser.add_argument("--from-repo",
                        default="ssh://hg.mozilla.org/releases/mozilla-beta",
                        help="Repo to be merged from")
    parser.add_argument("--to-dir", default="mozilla-release",
                        help="Working directory of repo to be merged to")
    parser.add_argument(
        "--to-repo", default="ssh://hg.mozilla.org/releases/mozilla-release",
        help="Repo to be merged to")
    parser.add_argument("--hg-user", default="ffxbld <*****@*****.**>",
                        help="Mercurial username to be passed to hg -u")
    parser.add_argument("--remove-locale", dest="remove_locales", action="append",
                        required=True,
                        help="Locales to be removed from release shipped-locales")

    args = parser.parse_args()
    from_dir = args.from_dir
    to_dir = args.to_dir
    from_repo = args.from_repo
    to_repo = args.to_repo
    hg_user = args.hg_user

    with retrying(mercurial) as clone:
        for (d, repo) in ((from_dir, from_repo), (to_dir, to_repo)):
            clone(repo, d)
            log.info("Cleaning up %s...", d)
            strip_outgoing(d)
            update(d, branch="default")
    beta_rev = get_revision(from_dir)
    release_rev = get_revision(to_dir)

    now = datetime.datetime.now()
    date = now.strftime("%Y%m%d")
    # TODO: make this tag consistent with other branches
    release_base_tag = "RELEASE_BASE_" + date

    log.info("Tagging %s beta with %s", beta_rev, release_base_tag)
    tag(from_dir, tags=[release_base_tag], rev=beta_rev, user=hg_user,
        msg="Added %s tag for changeset %s. DONTBUILD CLOSED TREE a=release" %
        (release_base_tag, beta_rev))
    new_beta_rev = get_revision(from_dir)
    raw_input("Push mozilla-beta and hit Return")

    pull(from_dir, dest=to_dir)
    merge_via_debugsetparents(
        to_dir, old_head=release_rev, new_head=new_beta_rev, user=hg_user,
        msg="Merge old head via |hg debugsetparents %s %s|. "
        "CLOSED TREE DONTBUILD a=release" % (new_beta_rev, release_rev))

    replace(
        path.join(to_dir, "browser/confvars.sh"),
        "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-beta,firefox-mozilla-release",
        "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-release")
    replace(path.join(to_dir, "browser/confvars.sh"),
            "MAR_CHANNEL_ID=firefox-mozilla-beta",
            "MAR_CHANNEL_ID=firefox-mozilla-release")

    for d in branding_dirs:
        for f in branding_files:
            replace(
                path.join(to_dir, d, f),
                "ac_add_options --with-branding=mobile/android/branding/beta",
                "ac_add_options --with-branding=mobile/android/branding/official")

    if args.remove_locales:
        log.info("Removing locales: %s", args.remove_locales)
        remove_locales(path.join(to_dir, "browser/locales/shipped-locales"),
                       args.remove_locales)

    log.warn("Apply any manual changes, such as disabling features.")
    raw_input("Hit 'return' to display channel, branding, and feature diffs onscreen")
    run_cmd(["hg", "diff"], cwd=to_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(to_dir, user=hg_user,
           msg="Update configs. CLOSED TREE a=release ba=release")
    raw_input("Go ahead and push mozilla-release changes.")
Пример #10
0
def tagRepo(config,
            repo,
            reponame,
            revision,
            tags,
            bumpFiles,
            relbranch,
            pushAttempts,
            defaultBranch='default'):
    remote = make_hg_url(HG, repo)
    retry(mercurial, args=(remote, reponame))

    def bump_and_tag(repo, attempt, config, relbranch, revision, tags,
                     defaultBranch):
        # set relbranchChangesets=1 because tag() generates exactly 1 commit
        relbranchChangesets = 1
        defaultBranchChangesets = 0

        if relbranch in get_branches(reponame):
            update(reponame, revision=relbranch)
        else:
            update(reponame, revision=revision)
            run_cmd(['hg', 'branch', relbranch], cwd=reponame)

        if len(bumpFiles) > 0:
            # Bump files on the relbranch, if necessary
            bump(reponame, bumpFiles, 'version')
            run_cmd(['hg', 'diff'], cwd=repo)
            try:
                get_output([
                    'hg', 'commit', '-u', config['hgUsername'], '-m',
                    getBumpCommitMessage(config['productName'],
                                         config['version'])
                ],
                           cwd=reponame)
                relbranchChangesets += 1
            except subprocess.CalledProcessError, e:
                # We only want to ignore exceptions caused by having nothing to
                # commit, which are OK. We still want to raise exceptions caused
                # by any other thing.
                if e.returncode != 1 or "nothing changed" not in e.output:
                    raise

        # We always want our tags pointing at the tip of the relbranch
        # so we need to grab the current revision after we've switched
        # branches and bumped versions.
        revision = get_revision(reponame)
        # Create the desired tags on the relbranch
        tag(repo, revision, tags, config['hgUsername'])

        # This is the bump of the version on the default branch
        # We do it after the other one in order to get the tip of the
        # repository back on default, thus avoiding confusion.
        if len(bumpFiles) > 0:
            update(reponame, revision=defaultBranch)
            bump(reponame, bumpFiles, 'nextVersion')
            run_cmd(['hg', 'diff'], cwd=repo)
            try:
                get_output([
                    'hg', 'commit', '-u', config['hgUsername'], '-m',
                    getBumpCommitMessage(config['productName'],
                                         config['version'])
                ],
                           cwd=reponame)
                defaultBranchChangesets += 1
            except subprocess.CalledProcessError, e:
                if e.returncode != 1 or "nothing changed" not in e.output:
                    raise
Пример #11
0
def main():
    logging.basicConfig(format="%(asctime)s - %(message)s", level=logging.INFO)
    parser = argparse.ArgumentParser()
    parser.add_argument("--hg-user", default="ffxbld <*****@*****.**>",
                        help="Mercurial username to be passed to hg -u")

    args = parser.parse_args()
    hg_user = args.hg_user

    # prep the repos
    for d, repo in ((mc_dir, mc_repo), (ma_dir, ma_repo), (mb_dir, mb_repo)):
        mercurial(repo, d)
        log.info("Cleaning up %s...", d)
        strip_outgoing(d)
        update(d, branch="default")

    curr_mc_version = get_major_version(mc_dir)
    curr_ma_version = get_major_version(ma_dir)
    curr_mb_version = get_major_version(mb_dir)

    next_mc_version = str(int(curr_mc_version) + 1)
    next_ma_version = str(int(curr_ma_version) + 1)
    next_mb_version = str(int(curr_mb_version) + 1)

    # mozilla-central
    mc_revision = get_revision(mc_dir)
    mc_tag = "FIREFOX_AURORA_%s_BASE" % curr_mc_version
    tag(mc_dir, tags=[mc_tag], rev=mc_revision, user=hg_user,
        msg="Added %s tag for changeset %s. IGNORE BROKEN CHANGESETS  DONTBUILD CLOSED TREE NO BUG a=release" %
        (mc_tag, mc_revision))
    new_mc_revision = get_revision(mc_dir)
    bump_version(mc_dir, curr_mc_version, next_mc_version, "a1", "a1",
                 bump_major=True)

    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=mc_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(mc_dir, user=hg_user,
           msg="Version bump. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release")
    raw_input("Go ahead and push mozilla-central...and continue to "
              "mozilla-aurora to mozilla-beta uplift ")

    # mozilla-aurora
    ma_revision = get_revision(ma_dir)
    ma_tag = "FIREFOX_BETA_%s_BASE" % curr_ma_version
    ma_end_tag = "FIREFOX_AURORA_%s_END" % curr_ma_version
    # pull must use revision not tag
    pull(mc_dir, dest=ma_dir, revision=new_mc_revision)
    merge_via_debugsetparents(
        ma_dir, old_head=ma_revision, new_head=new_mc_revision,
        user=hg_user, msg="Merge old head via |hg debugsetparents %s %s|. "
        "CLOSED TREE DONTBUILD a=release" % (new_mc_revision, ma_revision))
    tag(ma_dir, tags=[ma_tag, ma_end_tag], rev=ma_revision, user=hg_user,
        msg="Added %s %s tags for changeset %s. IGNORE BROKEN CHANGESETS DONTBUILD CLOSED TREE NO BUG a=release" %
        (ma_tag, ma_end_tag,  ma_revision))
    log.info("Reverting locales")
    for f in locale_files:
        run_cmd(["hg", "revert", "-r", ma_end_tag, f], cwd=ma_dir)
    bump_version(ma_dir, next_ma_version, next_ma_version, "a1", "a2")
    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=ma_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(ma_dir, user=hg_user, msg="Version bump. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release")

    replace(path.join(ma_dir, "browser/confvars.sh"),
            "MOZ_BRANDING_DIRECTORY=browser/branding/nightly",
            "MOZ_BRANDING_DIRECTORY=browser/branding/aurora")
    replace(path.join(ma_dir, "browser/confvars.sh"),
            "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-central",
            "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-aurora")
    replace(path.join(ma_dir, "browser/confvars.sh"),
            "MAR_CHANNEL_ID=firefox-mozilla-central",
            "MAR_CHANNEL_ID=firefox-mozilla-aurora")
    for d in branding_dirs:
        for f in branding_files:
            replace(path.join(ma_dir, d, f),
                    "ac_add_options --with-branding=mobile/android/branding/nightly",
                    "ac_add_options --with-branding=mobile/android/branding/aurora")
            if f == "l10n-nightly":
                replace(path.join(ma_dir, d, f),
                        "ac_add_options --with-l10n-base=../../l10n-central",
                        "ac_add_options --with-l10n-base=..")
    for f in profiling_files:
        replace(path.join(ma_dir, f), "ac_add_options --enable-profiling", "")
    for f in elf_hack_files:
        replace(path.join(ma_dir, f),
                "ac_add_options --disable-elf-hack # --enable-elf-hack conflicts with --enable-profiling", "")

    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=ma_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(ma_dir, user=hg_user,
           msg="Update configs. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release ba=release")
    raw_input("Go ahead and push mozilla-aurora changes.")

    # mozilla-beta
    mb_revision = get_revision(mb_dir)
    mb_tag = "FIREFOX_BETA_%s_END" % curr_mb_version
    # pull must use revision not tag
    pull(ma_dir, dest=mb_dir, revision=ma_revision)
    merge_via_debugsetparents(
        mb_dir, old_head=mb_revision, new_head=ma_revision,
        user=hg_user, msg="Merge old head via |hg debugsetparents %s %s|. "
        "CLOSED TREE DONTBUILD a=release" % (ma_revision, mb_revision))
    tag(mb_dir, tags=[mb_tag], rev=mb_revision, user=hg_user,
        msg="Added %s tag for changeset %s. IGNORE BROKEN CHANGESETS DONTBUILD CLOSED TREE NO BUG a=release" %
        (mb_tag, mb_revision))
    bump_version(mb_dir, next_mb_version, next_mb_version, "a2", "")
    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=mb_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(mb_dir, user=hg_user, msg="Version bump. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release")
    replace(path.join(mb_dir, "browser/confvars.sh"),
            "MOZ_BRANDING_DIRECTORY=browser/branding/aurora",
            "MOZ_BRANDING_DIRECTORY=browser/branding/nightly")
    replace(path.join(mb_dir, "browser/confvars.sh"),
            "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-aurora",
            "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-beta,firefox-mozilla-release")
    replace(path.join(mb_dir, "browser/confvars.sh"),
            "MAR_CHANNEL_ID=firefox-mozilla-aurora",
            "MAR_CHANNEL_ID=firefox-mozilla-beta")
    for d in branding_dirs:
        for f in branding_files:
            replace(path.join(mb_dir, d, f),
                    "ac_add_options --with-branding=mobile/android/branding/aurora",
                    "ac_add_options --with-branding=mobile/android/branding/beta")
    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=mb_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(mb_dir, user=hg_user,
           msg="Update configs. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release ba=release")
    raw_input("Go ahead and push mozilla-beta changes.")
Пример #12
0
def process_patchset(data):
    """
    Apply patches and push to branch repository.
    """
    remote = '%s%s' % (config['hg_base_url'], data['branch'])
    active_repo = 'active/%s' % (data['branch'])
    fail_messages = []
    def cleanup_wrapper():
        try:
            shutil.rmtree(active_repo)
            clone_branch(data['branch'])
        except subprocess.CalledProcessError:
            # something useful needs to be done here
            log_msg('Error while cleaning/replacing repository.')

    def apply_patchset(dir, attempt):
        for patch in data['patches']:
            log_msg("Getting patch %s" % (patch['id']), None)
            # store patches in 'patches/' below work_dir
            patch_file = bz.get_patch(patch['id'], 'patches', create_path=True)
            if not has_valid_header(patch_file, data['branch'] == 'try'):
                log_msg('[Patch %s] invalid header.' % (patch['id']))
                msg = {
                    'type'    : 'error',
                    'action'  : 'patch.header',
                    'bugid'   : data['bugid'],
                    'branch'  : data['branch'],
                    'patchid' : patch['id'],
                    'patchsetid' : data['patchsetid'],
                    }
                if msg not in fail_messages:
                    fail_messages.append(msg)
                return False

            # using import to patch, this will pull required header information
            # and automatically perform commit for each import.
            (out, err, rc) = run_hg(['import', '-R', active_repo, patch_file])
            if rc != 0:
                log_msg('[Patch %s] %s' % (patch['id'], err))
                msg = {
                    'type'       : 'error',
                    'action'     : 'patch.import',
                    'bugid'      : data['bugid'],
                    'branch'     : data['branch'],
                    'patchid'    : patch['id'],
                    'patchsetid' : data['patchsetid']
                    }
                if msg not in fail_messages:
                    fail_messages.append(msg)
                return False
        return True

    try:
        retry(apply_and_push, cleanup=cleanup_wrapper,
                retry_exceptions=Exception('E_RETRY'),
                args=(active_repo, remote, apply_patchset, 1),
                kwargs=dict(ssh_username=config['hg_username'],ssh_key=config['hg_ssh_key']))
    except HgUtilError as error:
        log_msg('[PatchSet] Could not apply and push patchset:\n%s' % (error))
        mq.send_message(fail_messages, config['mq_queue'],
                routing_keys=[config['mq_comment_topic'],
                              config['mq_db_topic']])
        return False
    except Exception('E_RETRY'):
        log_msg('[PatchSet] Could not apply and push patchset.')
        mq.send_message(fail_messages, config['mq_queue'],
                routing_keys=[config['mq_comment_topic'],
                              config['mq_db_topic']])
        return False
    revision = get_revision(active_repo)
    shutil.rmtree(active_repo)
    return revision
Пример #13
0
def main():
    logging.basicConfig(format="%(asctime)s - %(message)s", level=logging.INFO)
    parser = argparse.ArgumentParser()
    parser.add_argument("--hg-user",
                        default="ffxbld <*****@*****.**>",
                        help="Mercurial username to be passed to hg -u")

    args = parser.parse_args()
    hg_user = args.hg_user

    # prep the repos
    for d, repo in ((mc_dir, mc_repo), (ma_dir, ma_repo), (mb_dir, mb_repo)):
        mercurial(repo, d)
        log.info("Cleaning up %s...", d)
        strip_outgoing(d)
        update(d, branch="default")

    curr_mc_version = get_major_version(mc_dir)
    curr_ma_version = get_major_version(ma_dir)
    curr_mb_version = get_major_version(mb_dir)

    next_mc_version = str(int(curr_mc_version) + 1)
    next_ma_version = str(int(curr_ma_version) + 1)
    next_mb_version = str(int(curr_mb_version) + 1)

    # mozilla-central
    mc_revision = get_revision(mc_dir)
    mc_tag = "FIREFOX_AURORA_%s_BASE" % curr_mc_version
    tag(mc_dir,
        tags=[mc_tag],
        rev=mc_revision,
        user=hg_user,
        msg=
        "Added %s tag for changeset %s. IGNORE BROKEN CHANGESETS  DONTBUILD CLOSED TREE NO BUG a=release"
        % (mc_tag, mc_revision))
    new_mc_revision = get_revision(mc_dir)
    bump_version(mc_dir,
                 curr_mc_version,
                 next_mc_version,
                 "a1",
                 "a1",
                 bump_major=True)

    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=mc_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(
        mc_dir,
        user=hg_user,
        msg=
        "Version bump. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release")
    raw_input("Go ahead and push mozilla-central...and continue to "
              "mozilla-aurora to mozilla-beta uplift ")

    # mozilla-aurora
    ma_revision = get_revision(ma_dir)
    ma_tag = "FIREFOX_BETA_%s_BASE" % curr_ma_version
    ma_end_tag = "FIREFOX_AURORA_%s_END" % curr_ma_version
    # pull must use revision not tag
    pull(mc_dir, dest=ma_dir, revision=new_mc_revision)
    merge_via_debugsetparents(
        ma_dir,
        old_head=ma_revision,
        new_head=new_mc_revision,
        user=hg_user,
        msg="Merge old head via |hg debugsetparents %s %s|. "
        "CLOSED TREE DONTBUILD a=release" % (new_mc_revision, ma_revision))
    tag(ma_dir,
        tags=[ma_tag, ma_end_tag],
        rev=ma_revision,
        user=hg_user,
        msg=
        "Added %s %s tags for changeset %s. IGNORE BROKEN CHANGESETS DONTBUILD CLOSED TREE NO BUG a=release"
        % (ma_tag, ma_end_tag, ma_revision))
    log.info("Reverting locales")
    for f in locale_files:
        run_cmd(["hg", "revert", "-r", ma_end_tag, f], cwd=ma_dir)
    bump_version(ma_dir, next_ma_version, next_ma_version, "a1", "a2")
    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=ma_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(
        ma_dir,
        user=hg_user,
        msg=
        "Version bump. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release")

    replace(path.join(ma_dir, "browser/confvars.sh"),
            "MOZ_BRANDING_DIRECTORY=browser/branding/nightly",
            "MOZ_BRANDING_DIRECTORY=browser/branding/aurora")
    replace(path.join(ma_dir, "browser/confvars.sh"),
            "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-central",
            "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-aurora")
    replace(path.join(ma_dir, "browser/confvars.sh"),
            "MAR_CHANNEL_ID=firefox-mozilla-central",
            "MAR_CHANNEL_ID=firefox-mozilla-aurora")
    for d in branding_dirs:
        for f in branding_files:
            replace(
                path.join(ma_dir, d, f),
                "ac_add_options --with-branding=mobile/android/branding/nightly",
                "ac_add_options --with-branding=mobile/android/branding/aurora"
            )
            if f == "l10n-nightly":
                replace(path.join(ma_dir, d, f),
                        "ac_add_options --with-l10n-base=../../l10n-central",
                        "ac_add_options --with-l10n-base=..")
    for f in profiling_files:
        replace(path.join(ma_dir, f), "ac_add_options --enable-profiling", "")
    for f in elf_hack_files:
        replace(
            path.join(ma_dir, f),
            "ac_add_options --disable-elf-hack # --enable-elf-hack conflicts with --enable-profiling",
            "")

    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=ma_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(
        ma_dir,
        user=hg_user,
        msg=
        "Update configs. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release ba=release"
    )
    raw_input("Go ahead and push mozilla-aurora changes.")

    # mozilla-beta
    mb_revision = get_revision(mb_dir)
    mb_tag = "FIREFOX_BETA_%s_END" % curr_mb_version
    # pull must use revision not tag
    pull(ma_dir, dest=mb_dir, revision=ma_revision)
    merge_via_debugsetparents(
        mb_dir,
        old_head=mb_revision,
        new_head=ma_revision,
        user=hg_user,
        msg="Merge old head via |hg debugsetparents %s %s|. "
        "CLOSED TREE DONTBUILD a=release" % (ma_revision, mb_revision))
    tag(mb_dir,
        tags=[mb_tag],
        rev=mb_revision,
        user=hg_user,
        msg=
        "Added %s tag for changeset %s. IGNORE BROKEN CHANGESETS DONTBUILD CLOSED TREE NO BUG a=release"
        % (mb_tag, mb_revision))
    bump_version(mb_dir, next_mb_version, next_mb_version, "a2", "")
    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=mb_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(
        mb_dir,
        user=hg_user,
        msg=
        "Version bump. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release")
    replace(path.join(mb_dir, "browser/confvars.sh"),
            "MOZ_BRANDING_DIRECTORY=browser/branding/aurora",
            "MOZ_BRANDING_DIRECTORY=browser/branding/nightly")
    replace(
        path.join(mb_dir, "browser/confvars.sh"),
        "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-aurora",
        "ACCEPTED_MAR_CHANNEL_IDS=firefox-mozilla-beta,firefox-mozilla-release"
    )
    replace(path.join(mb_dir, "browser/confvars.sh"),
            "MAR_CHANNEL_ID=firefox-mozilla-aurora",
            "MAR_CHANNEL_ID=firefox-mozilla-beta")
    for d in branding_dirs:
        for f in branding_files:
            replace(
                path.join(mb_dir, d, f),
                "ac_add_options --with-branding=mobile/android/branding/aurora",
                "ac_add_options --with-branding=mobile/android/branding/beta")
    raw_input("Hit 'return' to display diffs onscreen")
    run_cmd(["hg", "diff"], cwd=mb_dir)
    raw_input("If the diff looks good hit return to commit those changes")
    commit(
        mb_dir,
        user=hg_user,
        msg=
        "Update configs. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release ba=release"
    )
    raw_input("Go ahead and push mozilla-beta changes.")