Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support self hosted git repo #139

Merged
merged 1 commit into from
Aug 9, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,14 @@ Extension options (``conf.py``)
provided, the build will still pass but the changelog will not be built, and
a link to the ``changelog-url`` will be displayed (if provided).

- ``sphinx_github_changelog_root_repo`` (optional): Root url to the repository,
defaults to "https://github.com/". Useful if you're using a self-hosted GitHub
instance.

- ``sphinx_github_changelog_graphql_url`` (optional): Url to graphql api, defaults
to "https://api.github.com/graphql". Useful if you're using a self-hosted GitHub
instance.

.. _ReadTheDocs: https://readthedocs.org/

Directive
Expand Down
13 changes: 13 additions & 0 deletions sphinx_github_changelog/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,19 @@ def setup(app):
app.add_config_value(
name=token_name, default=os.environ.get(token_name.upper()), rebuild="html"
)
root_repo_name = "sphinx_github_changelog_root_repo"
app.add_config_value(
name=root_repo_name,
default=os.environ.get(root_repo_name.upper()),
rebuild="html",
)
graphql_url_name = "sphinx_github_changelog_graphql_url"
app.add_config_value(
name=graphql_url_name,
default=os.environ.get(graphql_url_name.upper()),
rebuild="html",
)

app.add_directive("changelog", changelog.ChangelogDirective)

return {
Expand Down
33 changes: 24 additions & 9 deletions sphinx_github_changelog/changelog.py
Original file line number Diff line number Diff line change
Expand Up @@ -31,20 +31,28 @@ def run(self) -> List[nodes.Node]:
config = self.state.document.settings.env.config
try:
return compute_changelog(
token=config.sphinx_github_changelog_token, options=self.options
token=config.sphinx_github_changelog_token,
options=self.options,
root_url=config.sphinx_github_changelog_root_repo,
graphql_url=config.sphinx_github_changelog_graphql_url,
)
except ChangelogError as exc:
raise self.error(str(exc))


def compute_changelog(
token: Optional[str], options: Dict[str, str]
token: Optional[str],
options: Dict[str, str],
root_url: Optional[str] = None,
graphql_url: Optional[str] = None,
) -> List[nodes.Node]:
if not token:
return no_token(changelog_url=options.get("changelog-url"))

owner_repo = extract_github_repo_name(url=options["github"])
releases = extract_releases(owner_repo=owner_repo, token=token)
owner_repo = extract_github_repo_name(url=options["github"], root_url=root_url)
releases = extract_releases(
owner_repo=owner_repo, token=token, graphql_url=graphql_url
)

pypi_name = extract_pypi_package_name(url=options.get("pypi"))

Expand Down Expand Up @@ -72,14 +80,19 @@ def no_token(changelog_url: Optional[str]) -> List[nodes.Node]:
return result


def extract_github_repo_name(url: str) -> str:
def extract_github_repo_name(url: str, root_url: Optional[str] = None) -> str:
stripped_url = url.rstrip("/")
prefix, postfix = "https://github.com/", "/releases"
prefix, postfix = (
root_url if root_url is not None else "https://github.com/",
"/releases",
)
if not prefix.endswith("/"):
prefix += "/"
url_is_correct = stripped_url.startswith(prefix) and stripped_url.endswith(postfix)
if not url_is_correct:
raise ChangelogError(
"Changelog needs a Github releases URL "
f"(https://github.com/:owner/:repo/releases). Received {url}"
f"({prefix}:owner/:repo/releases). Received {url}"
)

return stripped_url[len(prefix) : -len(postfix)]
Expand Down Expand Up @@ -142,7 +155,9 @@ def node_for_release(
return section


def extract_releases(owner_repo: str, token: str) -> Iterable[Dict[str, Any]]:
def extract_releases(
owner_repo: str, token: str, graphql_url: Optional[str] = None
) -> Iterable[Dict[str, Any]]:
# Necessary for GraphQL
owner, repo = owner_repo.split("/")
query = """
Expand All @@ -161,7 +176,7 @@ def extract_releases(owner_repo: str, token: str) -> Iterable[Dict[str, Any]]:
)
full_query = {"query": query.replace("\n", "")}

url = "https://api.github.com/graphql"
url = "https://api.github.com/graphql" if graphql_url is None else graphql_url

try:
result = github_call(url=url, query=full_query, token=token)
Expand Down
34 changes: 34 additions & 0 deletions tests/unit/test_changelog.py
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,27 @@ def test_extract_github_repo_name_error():
changelog.extract_github_repo_name("https://example.com")


@pytest.mark.parametrize(
"url",
[
"https://git.privaterepo.com/a/b/releases",
"https://git.privaterepo.com/a/b/releases/",
],
)
def test_extract_github_repo_different_root_url(url):
with pytest.raises(
changelog.ChangelogError, match="^Changelog needs a Github releases URL"
):
changelog.extract_github_repo_name(url)

assert (
changelog.extract_github_repo_name(url, "https://git.privaterepo.com/") == "a/b"
)
assert (
changelog.extract_github_repo_name(url, "https://git.privaterepo.com") == "a/b"
)


@pytest.mark.parametrize(
"url", ["https://pypi.org/project/a", "https://pypi.org/project/a/"]
)
Expand Down Expand Up @@ -180,6 +201,19 @@ def test_extract_releases(github_payload, release_dict, mocker):
]


def test_extract_releases_custom_graphql_url(github_payload, release_dict, mocker):
mocker.patch(
"sphinx_github_changelog.changelog.github_call", return_value=github_payload
)
assert changelog.extract_releases(
owner_repo="a/b",
token="token",
graphql_url="https://git.privaterepo.com/graphql",
) == [
release_dict,
]
Comment on lines +204 to +214
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(We're not exactly testing that the graphql_url is used, but it could be good enough)



def test_extract_releases_remove_none(github_payload, release_dict, mocker):
mocker.patch(
"sphinx_github_changelog.changelog.github_call",
Expand Down
Loading