Red 3.5.5 - Changelog (#6249)

Co-authored-by: Michael Oliveira <34169552+Flame442@users.noreply.github.com>
This commit is contained in:
Jakub Kuczys 2023-09-14 21:50:17 +02:00 committed by GitHub
parent 4d4cb14725
commit 56377b0596
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 135 additions and 54 deletions

View File

@ -1,5 +1,38 @@
.. Red changelogs
Redbot 3.5.5 (2023-08-14)
=========================
| Thanks to all these amazing people that contributed to this release:
| :ghuser:`Flame442`, :ghuser:`Jackenmen`, :ghuser:`karlsbjorn`, :ghuser:`Kreusada`, :ghuser:`ltzmax`, :ghuser:`palmtree5`
End-user changelog
------------------
Changes
*******
- **Core - Dependencies** - Red's dependencies have been bumped (:issue:`6248`)
- **Cogs - Downloader** - Cogs in the ``[p]cog list`` command are now listed alphabetically (:issue:`6214`, :issue:`6215`)
Fixes
*****
- **Core - Bot Commands** - Fixed handling of an edge case in the ``[p]diagnoseissues`` command that involved commands without a cog (:issue:`6237`)
- **Core - Bot Commands** - Fixed the formatting of nested result lists in the ``[p]diagnoseissues`` command (:issue:`6238`)
- **Cogs - Mod** - Fixed the formatting of the help description for the ``[p]ban``, ``[p]kick``, and ``[p]tempban`` commands (:issue:`6245`)
- |cool| **Cogs - Streams** - Updated the implementation of Twitch streams to no longer use the "Get Users Follows" endpoint that was deprecated in February 2023 (:issue:`6246`, :issue:`6247`)
Documentation changes
---------------------
Changes
*******
- Updated Python version in ``pyenv`` instructions (:issue:`6241`)
----
Redbot 3.5.4 (2023-08-12)
=========================

View File

@ -12,9 +12,10 @@ import re
import shlex
import subprocess
import time
import urllib.parse
import webbrowser
from collections import defaultdict
from typing import Dict, List, Optional
from typing import Dict, List, Optional, Tuple
import click
import requests
@ -29,7 +30,7 @@ class ReleaseType(enum.Enum):
MAINTENANCE = 3
HOTFIX = 4
def __str__(self) -> None:
def __str__(self) -> str:
return f"{self.name.lower()} release"
@classmethod
@ -105,9 +106,7 @@ query getAllTagCommits {
nodes {
name
target {
... on Commit {
oid
}
commitResourcePath
}
}
}
@ -144,6 +143,27 @@ query getCommitHistory($refQualifiedName: String!, $after: String) {
}
}
"""
GET_LAST_ISSUE_NUMBER_QUERY = """
query getLastIssueNumber {
repository(owner: "Cog-Creators", name: "Red-DiscordBot") {
discussions(orderBy: {field: CREATED_AT, direction: DESC}, first: 1) {
nodes {
number
}
}
issues(orderBy: {field: CREATED_AT, direction: DESC}, first: 1) {
nodes {
number
}
}
pullRequests(orderBy: {field: CREATED_AT, direction: DESC}, first: 1) {
nodes {
number
}
}
}
}
"""
GH_URL = "https://github.com/Cog-Creators/Red-DiscordBot"
LINKIFY_ISSUE_REFS_RE = re.compile(r"#(\d+)")
@ -228,11 +248,11 @@ def get_git_config_value(key: str) -> str:
return ""
def set_git_config_value(key: str, value: str) -> str:
def set_git_config_value(key: str, value: str) -> None:
subprocess.check_call(("git", "config", "--local", f"red-release-helper.{key}", value))
def wipe_git_config_values() -> str:
def wipe_git_config_values() -> None:
try:
subprocess.check_output(
("git", "config", "--local", "--remove-section", "red-release-helper")
@ -304,7 +324,7 @@ def set_release_stage(stage: ReleaseStage) -> None:
@click.group(invoke_without_command=True)
@click.option("--continue", "abort", flag_value=False, default=None)
@click.option("--abort", "abort", flag_value=True, default=None)
def cli(*, abort: bool = None):
def cli(*, abort: Optional[bool] = None):
"""Red's release helper, guiding you through the whole process!"""
stage = get_release_stage()
if abort is True:
@ -516,40 +536,46 @@ def create_changelog(release_type: ReleaseType, version: str) -> None:
else:
changelog_branch = f"V3/changelogs/{version}"
subprocess.check_call(("git", "fetch", GH_URL))
try:
subprocess.check_call(("git", "checkout", "-b", changelog_branch, "FETCH_HEAD"))
except subprocess.CalledProcessError:
rich.print()
if click.confirm(
f"It seems that {changelog_branch} branch already exists, do you want to use it?"
):
subprocess.check_call(("git", "checkout", changelog_branch))
elif not click.confirm("Do you want to use a different branch?"):
raise click.ClickException("Can't continue without a changelog branch...")
elif click.confirm("Do you want to create a new branch?"):
while True:
changelog_branch = click.prompt("Input the name of the new branch")
try:
subprocess.check_call(
("git", "checkout", "-b", changelog_branch, "FETCH_HEAD")
)
except subprocess.CalledProcessError:
continue
else:
break
else:
while True:
changelog_branch = click.prompt("Input the name of the branch to check out")
try:
subprocess.check_call(("git", "checkout", changelog_branch))
except subprocess.CalledProcessError:
continue
else:
break
try:
subprocess.check_call(("git", "checkout", "-b", changelog_branch, "FETCH_HEAD"))
except subprocess.CalledProcessError:
rich.print()
if click.confirm(
f"It seems that {changelog_branch} branch already exists, do you want to use it?"
):
subprocess.check_call(("git", "checkout", changelog_branch))
elif not click.confirm("Do you want to use a different branch?"):
raise click.ClickException("Can't continue without a changelog branch...")
elif click.confirm("Do you want to create a new branch?"):
while True:
changelog_branch = click.prompt("Input the name of the new branch")
try:
subprocess.check_call(
("git", "checkout", "-b", changelog_branch, "FETCH_HEAD")
)
except subprocess.CalledProcessError:
continue
else:
break
else:
while True:
changelog_branch = click.prompt("Input the name of the branch to check out")
try:
subprocess.check_call(("git", "checkout", changelog_branch))
except subprocess.CalledProcessError:
continue
else:
break
set_changelog_branch(changelog_branch)
set_release_stage(ReleaseStage.CHANGELOG_BRANCH_EXISTS)
set_changelog_branch(changelog_branch)
set_release_stage(ReleaseStage.CHANGELOG_BRANCH_EXISTS)
title = f"Red {version} - Changelog"
commands = [
("git", "add", "."),
("git", "commit", "-m", title),
("git", "push", "-u", GH_URL, f"{changelog_branch}:{changelog_branch}"),
]
if get_release_stage() < ReleaseStage.CHANGELOG_COMMITTED:
rich.print(
"\n:pencil: At this point, you should have an up-to-date milestone"
@ -578,11 +604,6 @@ def create_changelog(release_type: ReleaseType, version: str) -> None:
if option == "4":
break
commands = [
("git", "add", "."),
("git", "commit", "-m", f"Red {version} - Changelog"),
("git", "push", "-u", GH_URL, f"{changelog_branch}:{changelog_branch}"),
]
print(
"Do you want to commit everything from repo's working tree and push it?"
" The following commands will run:"
@ -596,10 +617,37 @@ def create_changelog(release_type: ReleaseType, version: str) -> None:
else:
print("Okay, please open a changelog PR manually then.")
if get_release_stage() is ReleaseStage.CHANGELOG_COMMITTED:
token = get_github_token()
resp = requests.post(
"https://api.github.com/graphql",
json={"query": GET_LAST_ISSUE_NUMBER_QUERY},
headers={"Authorization": f"Bearer {token}"},
)
next_issue_number = (
max(
next(iter(data["nodes"]), {"number": 0})["number"]
for data in resp.json()["data"]["repository"].values()
)
+ 1
)
docs_preview_url = (
f"https://red-discordbot--{next_issue_number}.org.readthedocs.build"
f"/en/{next_issue_number}/changelog.html"
)
subprocess.check_call(commands[2])
query = {
"expand": "1",
"milestone": version,
"labels": "Type: Feature,Changelog Entry: Skipped",
"title": title,
"body": (
"### Description of the changes\n\n"
f"The PR for Red {version} changelog.\n\n"
f"Docs preview: {docs_preview_url}"
),
}
pr_url = (
f"{GH_URL}/compare/V3/develop...{changelog_branch}"
f"?expand=1&milestone={version}&labels=Type:+Feature"
f"{GH_URL}/compare/V3/develop...{changelog_branch}?{urllib.parse.urlencode(query)}"
)
print(f"Create new PR: {pr_url}")
webbrowser.open_new_tab(pr_url)
@ -782,11 +830,11 @@ STEPS = (
@cli.command(name="unreleased")
@click.argument("version")
@click.argument("base_branch")
def cli_unreleased(version: str, base_branch: str) -> int:
def cli_unreleased(version: str, base_branch: str) -> None:
show_unreleased_commits(version, base_branch)
def show_unreleased_commits(version: str, base_branch: str) -> int:
def show_unreleased_commits(version: str, base_branch: str) -> None:
token = get_github_token()
resp = requests.post(
@ -796,7 +844,8 @@ def show_unreleased_commits(version: str, base_branch: str) -> int:
)
json = resp.json()
tag_commits = {
node["target"]["oid"]: node["name"] for node in json["data"]["repository"]["refs"]["nodes"]
node["target"]["commitResourcePath"].rsplit("/", 1)[-1]: node["name"]
for node in json["data"]["repository"]["refs"]["nodes"]
}
after = None
@ -868,7 +917,7 @@ def cli_milestone(version: str) -> None:
def view_milestone_issues(version: str) -> None:
issue_views = []
issue_views: List[str] = []
for issue_type in ("pr", "issue"):
for number in subprocess.check_output(
(
@ -916,8 +965,8 @@ def get_contributors(version: str, *, show_not_merged: bool = False) -> None:
def _get_contributors(version: str, *, show_not_merged: bool = False) -> List[str]:
after = None
has_next_page = True
authors = {}
reviewers = {}
authors: Dict[str, List[Tuple[int, str]]] = {}
reviewers: Dict[str, List[Tuple[int, str]]] = {}
token = get_github_token()
states = ["MERGED"]
if show_not_merged:
@ -940,7 +989,6 @@ def _get_contributors(version: str, *, show_not_merged: bool = False) -> List[st
milestone_data = json["data"]["repository"]["milestones"]["nodes"][0]
except IndexError:
raise click.ClickException("Given milestone couldn't have been found.")
milestone_title = milestone_data["title"]
pull_requests = milestone_data["pullRequests"]
nodes = pull_requests["nodes"]
for pr_node in nodes: