Example #1
0
    def test_commit_grouping_by_action_and_scope(self, commit_list):
        semantic_commits = commit_analyzer(commit_list,
                                           label_pattern="!{type}:{scope}")
        release_data = ReleaseDataTree(semantic_commits)

        assert len(release_data["fix"]["thing"]) == 1
        assert len(release_data["feat"]["scopeless"]) == 1
        assert len(release_data["feat"]["cli"]) == 1
        assert len(release_data["feat"]["music"]) == 2
        assert len(release_data["refactor"]["music"]) == 1
        assert len(release_data["refactor"]["lorem"]) == 1
Example #2
0
    def test_release_with_fixes(self, commit_registry):
        semantic_commits = commit_analyzer([commit_registry["4d17c1a"]],
                                           label_pattern="!{type}:{scope}")
        release_data = ReleaseDataTree(semantic_commits)
        version = Version(major=10, minor=3, patch=0)

        markup = _render_release(version, release_data=release_data)

        assert markup == (f"10.3.0 ({str(date.today())})\n"
                          "-------------------\n\n"
                          "Bug Fixes\n"
                          "~~~~~~~~~\n\n"
                          "* thing - Fix a thing\n\n")
Example #3
0
    def test_scopeless_label_pattern(self, isolated_filesystem):

        commit = self.Commit(header="Make it work", footer="!fix", message="")

        with isolated_filesystem:

            lst = commit_analyzer([commit],
                                  label_pattern="!{type}",
                                  label_position="footer")

            assert len(lst) == 1
            assert lst[0].subject == "Make it work"
            assert lst[0].scope is None
            assert lst[0].type == "fix"
Example #4
0
    def test_label_in_header(self, isolated_filesystem, label_pattern, header):

        commit = self.Commit(header=header, footer=None, message="")

        with isolated_filesystem:

            lst = commit_analyzer([commit],
                                  label_pattern=label_pattern,
                                  label_position="header")

            assert len(lst) == 1
            assert lst[0].subject == "Make it work"
            assert lst[0].scope == "cli"
            assert lst[0].type == "fix"
Example #5
0
    def test_release_with_features(self, commit_registry):
        reg = commit_registry
        version = Version(major=10, minor=3, patch=0)
        semantic_commits = commit_analyzer(
            [reg["ccaa185"], reg["bc0bcab"], reg["a6b655f"]],
            label_pattern="!{type}:{scope}",
        )
        release_data = ReleaseDataTree(semantic_commits)
        markup = _render_release(version, release_data=release_data)

        assert markup == (f"10.3.0 ({str(date.today())})\n"
                          "-------------------\n\n"
                          "Features\n"
                          "~~~~~~~~\n\n"
                          "* Add a thing\n"
                          "* music - Add more music please\n"
                          "* cli - Add a cli tool\n\n")
Example #6
0
    def test_release_with_fixes_and_features(self, commit_list):
        version = Version(major=10, minor=3, patch=0)
        semantic_commits = commit_analyzer(commit_list,
                                           label_pattern="!{type}:{scope}")
        release_data = ReleaseDataTree(semantic_commits)
        markup = _render_release(version, release_data=release_data)

        assert markup == (f"10.3.0 ({str(date.today())})\n"
                          "-------------------\n\n"
                          "Bug Fixes\n"
                          "~~~~~~~~~\n\n"
                          "* thing - Fix a thing\n\n"
                          "Features\n"
                          "~~~~~~~~\n\n"
                          "* Add a thing\n"
                          "* music\n\n"
                          "  - Add more music please\n"
                          "  - Add cool musics :D\n"
                          "* cli - Add a cli tool\n\n")
Example #7
0
def release(
    ctx,
    bump,
    bump_type,
    commit_flag,
    message,
    tag_flag,
    confirm_flag,
    changelog_file,
    files,
    label_pattern,
    label_position,
    tag_pattern,
    current_version,
    stage,
    merge_pre,
    current_tag=None,
    versions=None,
):
    """Release a new version.

    Determines the next version by inspecting commit messages, updates the
    changelog, commit the changes and tag the repository with the new version.
    """
    # If there isn't a current version, assume version 0.0.0
    current_version = current_version or Version()

    git = Git()
    from_tag = current_tag.name if current_tag else None

    # Delimiter of the block to be removed from the changelog file
    remove_pre_chglog = None

    # Look for the last final release version if the user want it
    if merge_pre and current_version.stage != "final":
        remove_pre_chglog = [current_version.string]

        for version in versions:
            if version.stage == "final":
                from_tag = version.tag.name
                remove_pre_chglog.append(version.string)
                break

    commit_list = git.log(_from=from_tag)

    msg(f'{label("Current version")} {current_version}')
    msg(f'{label("Commits found")} {len(commit_list)} since last release')

    if not commit_list:
        click.echo(" › Nothing to release.")
        ctx.exit()

    semantic_commits = commit_analyzer(commit_list, label_pattern,
                                       label_position)

    release_data = ReleaseDataTree(semantic_commits)

    bump_version_to = None

    # --bump, --major, --minor, --patch or commit message based version
    # are taken into account only if the current version is in final stage.
    if current_version.stage == "final":

        # --bump have precedence over any of --major, --minor or --patch
        bump_version_to = bump.string if bump else bump_type

        # Any manual bump have precedence over commit message based versions.
        bump_version_to = bump_version_to or release_data.bump_version_to

    try:
        new_version = get_next_version(current_version, bump_version_to, stage)
    except ValueError as e:
        ctx.fail(e)

    if not new_version:
        msg("The release of a lower versions is not supported for now.")
        ctx.abort()

    new_tag_name = tag_pattern.format(version=new_version.string)

    msg(f'{label("New version")} {new_version}')
    msg(f'{label("Changelog file")} {changelog_file.name}')

    # Messages about what tasks will be performed
    msg("Braulio will perform the next tasks :")
    msg(f"        Update {len(files) + 1} files.", prefix="")
    msg("        Add a release commit.", prefix="", silence=not commit_flag)
    msg(
        f"        Tag the repository with {new_tag_name}",
        prefix="",
        silence=not tag_flag,
    )

    msg("", prefix="")  # Print just a new line

    if confirm_flag or click.confirm(f"{prefix_mark}Continue?"):

        msg("Update changelog ", nl=False)

        update_chglog(
            changelog_file,
            new_version=new_version,
            current_version=current_version,
            release_data=release_data,
            remove=remove_pre_chglog,
        )

        msg(check_mark, prefix="")

        try:
            update_files(files, str(current_version), str(new_version))
        except ValueError as e:
            click.echo(e)
            ctx.abort()

        if commit_flag:
            message_args = {"new_version": new_version.string}

            if "{current_version}" in message:
                message_args["current_version"] = current_version.string

            commit_message = message.format(**message_args)

            msg(f"Add commit: {commit_message}", nl=False)

            files = [str(changelog_file)] + list(files)
            git.commit(commit_message, files=files)
            msg(f" {check_mark}", prefix="")

        if tag_flag:
            msg(f"Add tag {new_tag_name}", nl=False)
            git.tag(new_tag_name)
            msg(f" {check_mark}", prefix="")

        if "current_version" in ctx.obj.cfg_file_options:
            update_config_file("current_version", new_version.string)

        msg(f"Version {new_version} released successfully", suffix=" 🎉")