Esempio n. 1
0
    def f2f(self, args):
        """
        修复分支转修复分支,默认转到下个迭代
        :param list args:
        :return:
        """
        if '-n' not in args and '-s' not in args:
            args.append('-n')

        b_info = self.__branch_and_sprint(args)
        if not b_info['branch']:
            raise exception.FlowException(u'未指定分支名称')

        old_branch = igit.real_branch(
            b_info['branch'],
            iconfig.read_config('system', 'branch')['feature_prefix'])
        new_branch = igit.real_branch(
            '%s/%s' % (b_info['sprint'], b_info['branch'].split('/')[-1]),
            iconfig.read_config('system', 'branch')['feature_prefix'])

        if not old_branch or not new_branch:
            raise exception.FlowException(u'分支名称不合法')

        if old_branch not in igit.local_branches():
            raise exception.FlowException(u'分支不存在:%s' % old_branch)

        if ihelper.confirm(u'确定将特性分支%s转为特性分支%s吗?' %
                           (old_branch, new_branch)) == 'y':
            git.Git('rename', [old_branch, new_branch]).execute()
            ok()
        else:
            ok(u'取消操作')
Esempio n. 2
0
    def f2h(self, args):
        """
        本迭代的特性分支转修复分支
        :return:
        """
        branch = None
        while args:
            branch = args.pop(0)

        if not branch:
            raise exception.FlowException(u'未指定分支名称')

        old_branch = igit.real_branch(
            branch,
            iconfig.read_config('system', 'branch')['feature_prefix'])
        new_branch = igit.real_branch(
            branch.split('/')[-1],
            iconfig.read_config('system', 'branch')['hotfix_prefix'])

        if not old_branch or not new_branch:
            raise exception.FlowException(u'分支名称不合法')

        if old_branch not in igit.local_branches():
            raise exception.FlowException(u'分支不存在:%s' % old_branch)

        if ihelper.confirm(u'确定将特性分支%s转为修复分支%s吗?' %
                           (old_branch, new_branch)) == 'y':
            git.Git('rename', [old_branch, new_branch]).execute()
            ok()
        else:
            ok(u'取消操作')
Esempio n. 3
0
    def rename(self):
        """
        分支重命名。old和new需要时绝对分支名
        """
        if len(self.args) < 2:
            raise exception.FlowException('指令格式错误,请输入help查看使用说明')

        old = self.args[0]
        new = self.args[1]

        local_branches = igit.local_branches()

        if old not in local_branches:
            raise exception.FlowException(u'分支名称不存在:%s' % old)

        remote_branches = igit.remote_branches()

        # 名称重复性检测
        if new in local_branches or new in remote_branches:
            raise exception.FlowException(u'该分支已经存在:%s' % new)

        info(u'重命名分支:%s -> %s...' % (old, new))

        # 重命名本地分支
        ihelper.execute('git branch -m ' + old + ' ' + new, raise_err=True)
        # 删除远程分支(如果有的话)
        if old in remote_branches:
            ihelper.execute('git push --delete origin ' + old)
        # 上传新分支到远程
        ihelper.execute('git push -u origin ' + new + ':' + new)

        #防止重命名后检查master更新情况
        igit.set_last_sync_master_date(new)
Esempio n. 4
0
 def match_remoteonly_branch(self, prefix, text=None):
     """
     匹配远程存在而本地不存在的分支
     :param prefix:
     :param text:
     :return:
     """
     remote_only_branches = list(
         set(igit.remote_branches(True)) - set(igit.local_branches()))
     return self.__match_branch(prefix, text, remote_only_branches)
Esempio n. 5
0
    def match_branch(self, prefix, text=None, include_remote=False):
        """
        匹配当前项目的本地分支
        :param bool include_remote: 是否包括远程分支
        :type prefix: str|None
        :param text:
        :return:
        """
        branches = igit.local_branches()
        if include_remote:
            branches = list(set(branches + igit.remote_branches()))

        return self.__match_branch(prefix, text, branches)
Esempio n. 6
0
    def delete(self):
        """
        删除本地匹配模式的多个分支,并删除远程相应分支
        :return:
        """
        if not self.args:
            raise exception.FlowException(u'指令格式错误,请输入help查看使用说明')

        tag_pattern = None
        del_remote = True
        del_branches = []

        while self.args:
            c = self.args.pop(0)
            if c == '--no-remote':
                del_remote = False
            else:
                tag_pattern = c

        if not tag_pattern:
            raise exception.FlowException(u'请指定需要删除的分支匹配模式')

        for branch in igit.local_branches():
            if branch == igit.product_branch():
                continue
            if re.match(tag_pattern, branch):
                del_branches.append(branch)

        if not del_branches:
            warn(u'没有符合条件的分支')
            return

        #打印出将要删除的分支列表
        warn(u'将要删除以下分支%s:' % ('(以及其对应的远程分支)' if del_remote else ''))
        for del_branch in del_branches:
            ok(del_branch)

        print

        if (ihelper.confirm(
                u'确定删除吗%s?' %
            ('(同时删除远程分支,删除后不可恢复)' if del_remote else ''), 'n') != 'y'):
            return

        #删除分支
        for del_branch in del_branches:
            try:
                igit.delete_branch(del_branch, del_remote)
            except exception.FlowException, e:
                warn(str(e))
Esempio n. 7
0
    def create(self, args):
        """
        创建特性/修复分支。一次只能创建一个,会推到远端,且切换到此分支
        :return:
        """
        if not args:
            raise exception.FlowException(u'指令格式错误,请输入h %s查看使用说明' % self.cmd)

        branch = None
        auto_create_from_remote = False
        push_to_remote = True

        while args:
            c = args.pop(0)
            if c == '-y':
                auto_create_from_remote = True
            elif c == '--np' or c == '--no-push':
                push_to_remote = False
            else:
                branch = c

        if not branch:
            raise exception.FlowException(u'请输入分支名称')

        # 分支简称不可与项目、迭代名称相同(防止一些指令出现歧义)
        simple_branch = igit.simple_branch(branch)
        if simple_branch == iglobal.SPRINT or simple_branch in ihelper.projects(
        ):
            raise exception.FlowException(u'分支简称不可与项目或迭代名同名')

        branch = igit.real_branch(branch, self.cmd)

        # 检查当前分支下工作区状态
        if not igit.workspace_is_clean():
            raise exception.FlowException(
                u'工作区中尚有未提交的内容,请先用git commit提交或用git stash保存到Git栈中')

        # 分支名称重复性检查
        info(u'检查本地分支...')
        if branch in igit.local_branches():
            raise exception.FlowException(u'该分支名称已经存在')

        # 本地没有但远程有
        create_from_remote = False
        info(u'检查远程分支...')
        if branch in igit.remote_branches():
            if not auto_create_from_remote and ihelper.confirm(
                    u'远程仓库已存在%s,是否基于该远程分支创建本地分支?' % branch) != 'y':
                return
            else:
                create_from_remote = True

        say(('white', u'正在创建分支'), ('sky_blue', branch), ('white', '...'))

        if create_from_remote:
            # 基于远程分支创建本地分支,会自动追踪该远程分支
            ihelper.execute('git checkout -b ' + branch + ' origin/' + branch)
        else:
            # 切换到生产分支
            p_branch = igit.product_branch()
            ihelper.execute('git checkout ' + p_branch)
            igit.pull()

            # 基于本地生产分支创建新分支
            ihelper.execute('git checkout -b ' + branch)

            # 推送到远程
            if push_to_remote:
                ihelper.execute('git push -u origin ' + branch + ':' + branch)

        if igit.workspace_is_clean():
            #处理master更新检验,防止创建分支后执行master更新检查操作
            igit.set_last_sync_master_date(branch)

            ok(u'创建成功!已进入分支:' + branch)
        else:
            raise exception.FlowException(u'创建分支失败')