diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 4ad879e..6f689e1 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -11,26 +11,26 @@ repos: # Autoformat: Python code - repo: https://github.com/ambv/black - rev: stable + rev: 22.3.0 hooks: - id: black # Autoformat: markdown, yaml - repo: https://github.com/pre-commit/mirrors-prettier - rev: v2.3.0 + rev: v2.6.2 hooks: - id: prettier exclude: tests/.* # Autoformat: https://github.com/asottile/reorder_python_imports - repo: https://github.com/asottile/reorder_python_imports - rev: v2.5.0 + rev: v3.0.1 hooks: - id: reorder-python-imports # Misc... - repo: https://github.com/pre-commit/pre-commit-hooks - rev: v3.4.0 + rev: v4.2.0 # ref: https://github.com/pre-commit/pre-commit-hooks#hooks-available hooks: # Autoformat: Makes sure files end in a newline and only a newline. @@ -49,6 +49,6 @@ repos: # Lint: Python code - repo: https://github.com/pycqa/flake8 - rev: "3.9.2" + rev: "4.0.1" hooks: - id: flake8 diff --git a/github_activity/cli.py b/github_activity/cli.py index 0236c0b..34d17ba 100644 --- a/github_activity/cli.py +++ b/github_activity/cli.py @@ -7,6 +7,7 @@ from .git import _git_installed_check from .github_activity import _parse_target from .github_activity import generate_activity_md +from .github_activity import generate_all_activity_md DESCRIPTION = "Generate a markdown changelog of GitHub activity within a date window." parser = argparse.ArgumentParser(description=DESCRIPTION) @@ -109,6 +110,12 @@ default=None, help=("""The branch or reference name to filter pull requests by"""), ) +parser.add_argument( + "--all", + default=False, + action="store_true", + help=("""Whether to include all the GitHub tags"""), +) def main(): @@ -151,19 +158,28 @@ def main(): except Exception: raise ValueError(err) - md = generate_activity_md( - args.target, - since=args.since, - until=args.until, + common_kwargs = dict( kind=args.kind, auth=args.auth, tags=tags, include_issues=bool(args.include_issues), include_opened=bool(args.include_opened), strip_brackets=bool(args.strip_brackets), - heading_level=args.heading_level, branch=args.branch, ) + + if args.all: + md = generate_all_activity_md(args.target, **common_kwargs) + + else: + md = generate_activity_md( + args.target, + since=args.since, + until=args.until, + heading_level=args.heading_level, + **common_kwargs, + ) + if not md: return diff --git a/github_activity/github_activity.py b/github_activity/github_activity.py index 69c528a..0df2d75 100644 --- a/github_activity/github_activity.py +++ b/github_activity/github_activity.py @@ -1,11 +1,15 @@ """Use the GraphQL api to grab issues/PRs that match a query.""" import datetime import os +import re +import shlex +import subprocess import sys import urllib from pathlib import Path from subprocess import PIPE from subprocess import run +from tempfile import TemporaryDirectory import dateutil import numpy as np @@ -153,6 +157,129 @@ def get_activity( return query_data +def generate_all_activity_md( + target, + pattern=r"(v?\d+\.\d+\.\d+)$", + kind=None, + auth=None, + tags=None, + include_issues=False, + include_opened=False, + strip_brackets=False, + branch=None, +): + """Generate a full markdown changelog of GitHub activity of a repo based on release tags. + + Parameters + ---------- + target : string + The GitHub organization/repo for which you want to grab recent issues/PRs. + Can either be *just* and organization (e.g., `jupyter`) or a combination + organization and repo (e.g., `jupyter/notebook`). If the former, all + repositories for that org will be used. If the latter, only the specified + repository will be used. Can also be a URL to a GitHub org or repo. + pattern: str + The expression used to match a release tag. + kind : ["issue", "pr"] | None + Return only issues or PRs. If None, both will be returned. + auth : string | None + An authentication token for GitHub. If None, then the environment + variable `GITHUB_ACCESS_TOKEN` will be tried. + tags : list of strings | None + A list of the tags to use in generating subsets of PRs for the markdown report. + Must be one of: + + ['enhancement', 'bugs', 'maintenance', 'documentation', 'api_change'] + + If None, all of the above tags will be used. + include_issues : bool + Include Issues in the markdown output. Default is False. + include_opened : bool + Include a list of opened items in the markdown output. Default is False. + strip_brackets : bool + If True, strip any text between brackets at the beginning of the issue/PR title. + E.g., [MRG], [DOC], etc. + branch : string | None + The branch or reference name to filter pull requests by. + + Returns + ------- + entry: str + The markdown changelog entry for all of the release tags in the repo. + """ + # Get the sha and tag name for each tag in the target repo + with TemporaryDirectory() as td: + + subprocess.run( + shlex.split(f"git clone https://github.com/{target} repo"), cwd=td + ) + repo = os.path.join(td, "repo") + subprocess.run(shlex.split("git fetch origin --tags"), cwd=repo) + + cmd = 'git log --tags --simplify-by-decoration --pretty="format:%h | %D"' + data = ( + subprocess.check_output(shlex.split(cmd), cwd=repo) + .decode("utf-8") + .splitlines() + ) + + # Clean up the raw data + pattern = f"tag: {pattern}" + + def filter(datum): + _, tag = datum + # Handle the HEAD tag if it exists + if "," in tag: + tag = tag.split(", ")[1] + return re.match(pattern, tag) is not None + + data = [d.split(" | ") for (i, d) in enumerate(data)] + data = [d for d in data if filter(d)] + + # Generate a changelog entry for each version and sha range + output = "" + + for i in range(len(data) - 1): + curr_data = data[i] + prev_data = data[i + 1] + + since = prev_data[0] + until = curr_data[0] + + # Handle the HEAD tag if it exists + if "," in curr_data[1]: + curr_data[1] = curr_data[1].split(",")[1] + + match = re.search(pattern, curr_data[1]) + tag = match.groups()[0] + + print(f"\n({i + 1}/{len(data)})", since, until, tag, file=sys.stderr) + md = generate_activity_md( + target, + since=since, + heading_level=2, + until=until, + auth=auth, + kind=kind, + include_issues=include_issues, + include_opened=include_opened, + strip_brackets=strip_brackets, + branch=branch, + ) + + if not md: + continue + + # Replace the header line with our version tag + md = "\n".join(md.splitlines()[1:]) + + output += f""" +## {tag} +{md} +""" + return output + + def generate_activity_md( target, since=None, @@ -208,13 +335,12 @@ def generate_activity_md( By default, top-level heading is h1, sections are h2. With heading_level=2 those are increased to h2 and h3, respectively. branch : string | None - The branch or reference name to filter pull requests by + The branch or reference name to filter pull requests by. Returns ------- - query_data : pandas DataFrame - A munged collection of data returned from your query. This - will be a combination of issues and PRs. + entry: str + The markdown changelog entry. """ org, repo = _parse_target(target) diff --git a/tests/test_cli.py b/tests/test_cli.py index 9329c97..6e191a0 100644 --- a/tests/test_cli.py +++ b/tests/test_cli.py @@ -69,3 +69,14 @@ def test_pr_split(tmpdir, file_regression): md = path_output.read_text() md = md.split("## Contributors to this release")[0] file_regression.check(md, extension=".md") + + +def test_cli_all(tmpdir, file_regression): + """Test that a full changelog is created""" + path_tmp = Path(tmpdir) + path_output = path_tmp.joinpath("out.md") + cmd = f"github-activity executablebooks/github-activity --all -o {path_output}" + run(cmd.split(), check=True) + md = path_output.read_text() + index = md.index("## v0.2.0") + file_regression.check(md[index:], extension=".md") diff --git a/tests/test_cli/test_cli_all.md b/tests/test_cli/test_cli_all.md new file mode 100644 index 0000000..90b1550 --- /dev/null +++ b/tests/test_cli/test_cli_all.md @@ -0,0 +1,74 @@ +## v0.2.0 + +([full changelog](https://github.com/executablebooks/github-activity/compare/ca2819b...f994a69)) + +### Enhancements made + +- Use auth for all usages of requests [#60](https://github.com/executablebooks/github-activity/pull/60) ([@blink1073](https://github.com/blink1073)) +- Handle detection of target from SSH based remotes [#51](https://github.com/executablebooks/github-activity/pull/51) ([@consideRatio](https://github.com/consideRatio)) +- ✨ ENH: Auto-detecting the target [#45](https://github.com/executablebooks/github-activity/pull/45) ([@choldgraf](https://github.com/choldgraf)) + +### Bugs fixed + +- πŸ› FIX: write status messages to sys.stderr [#47](https://github.com/executablebooks/github-activity/pull/47) ([@minrk](https://github.com/minrk)) + +### Maintenance and upkeep improvements + +- πŸ”§ MAINT: Split test_cli using @pytest.mark.parameterize [#56](https://github.com/executablebooks/github-activity/pull/56) ([@manics](https://github.com/manics)) +- pre-commit configured and executed [#55](https://github.com/executablebooks/github-activity/pull/55) ([@consideRatio](https://github.com/consideRatio)) +- πŸ”§ MAINT: _get_latest_tag should use the remote repo [#52](https://github.com/executablebooks/github-activity/pull/52) ([@manics](https://github.com/manics)) +- πŸ”§ MAINT: hyphen instead of asterisk [#44](https://github.com/executablebooks/github-activity/pull/44) ([@choldgraf](https://github.com/choldgraf)) + +### Contributors to this release + +([GitHub contributors page for this release](https://github.com/executablebooks/github-activity/graphs/contributors?from=2021-02-20&to=2021-12-01&type=c)) + +[@blink1073](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Ablink1073+updated%3A2021-02-20..2021-12-01&type=Issues) | [@choldgraf](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Acholdgraf+updated%3A2021-02-20..2021-12-01&type=Issues) | [@consideRatio](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3AconsideRatio+updated%3A2021-02-20..2021-12-01&type=Issues) | [@manics](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Amanics+updated%3A2021-02-20..2021-12-01&type=Issues) | [@minrk](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Aminrk+updated%3A2021-02-20..2021-12-01&type=Issues) | [@welcome](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Awelcome+updated%3A2021-02-20..2021-12-01&type=Issues) | [@wolfv](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Awolfv+updated%3A2021-02-20..2021-12-01&type=Issues) + +## v0.1.3 + +([full changelog](https://github.com/executablebooks/github-activity/compare/60c7f06...ca2819b)) + +### New features added + +- ✨NEW: heading_level argument for increasing heading level [#38](https://github.com/executablebooks/github-activity/pull/38) ([@minrk](https://github.com/minrk)) + +### Enhancements made + +- πŸ‘ŒIMPROVE: add blank lines below headings [#36](https://github.com/executablebooks/github-activity/pull/36) ([@minrk](https://github.com/minrk)) +- πŸ‘Œ IMPROVE: since/until: assume git reference, fallback to datetime [#33](https://github.com/executablebooks/github-activity/pull/33) ([@consideRatio](https://github.com/consideRatio)) + +### Bugs fixed + +- πŸ› FIX: tags like 'doctor' would trigger 'doc' tag [#40](https://github.com/executablebooks/github-activity/pull/40) ([@consideRatio](https://github.com/consideRatio)) + +### Documentation improvements + +- πŸ“š DOC: Minor docs changes [#43](https://github.com/executablebooks/github-activity/pull/43) ([@choldgraf](https://github.com/choldgraf)) + +### Other merged PRs + +- Adding filtering by branch [#42](https://github.com/executablebooks/github-activity/pull/42) ([@choldgraf](https://github.com/choldgraf)) +- use tqdm for progress [#39](https://github.com/executablebooks/github-activity/pull/39) ([@minrk](https://github.com/minrk)) +- Remove no longer used code [#37](https://github.com/executablebooks/github-activity/pull/37) ([@consideRatio](https://github.com/consideRatio)) +- [FIX,TST] resolve refs when not run from a repo [#35](https://github.com/executablebooks/github-activity/pull/35) ([@minrk](https://github.com/minrk)) + +### Contributors to this release + +([GitHub contributors page for this release](https://github.com/executablebooks/github-activity/graphs/contributors?from=2020-08-31&to=2021-02-20&type=c)) + +[@choldgraf](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Acholdgraf+updated%3A2020-08-31..2021-02-20&type=Issues) | [@consideRatio](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3AconsideRatio+updated%3A2020-08-31..2021-02-20&type=Issues) | [@minrk](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Aminrk+updated%3A2020-08-31..2021-02-20&type=Issues) | [@welcome](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Awelcome+updated%3A2020-08-31..2021-02-20&type=Issues) + +## v0.1.2 + +([full changelog](https://github.com/executablebooks/github-activity/compare/32f89fd...60c7f06)) + +### Merged PRs + +- adding thumbsup to query [#31](https://github.com/executablebooks/github-activity/pull/31) ([@choldgraf](https://github.com/choldgraf)) + +### Contributors to this release + +([GitHub contributors page for this release](https://github.com/executablebooks/github-activity/graphs/contributors?from=2020-08-07&to=2020-08-31&type=c)) + +[@choldgraf](https://github.com/search?q=repo%3Aexecutablebooks%2Fgithub-activity+involves%3Acholdgraf+updated%3A2020-08-07..2020-08-31&type=Issues)