Skip to content
Permalink

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also or learn more about diff comparisons.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also . Learn more about diff comparisons here.
base repository: gitpython-developers/GitPython
Failed to load repositories. Confirm that selected base ref is valid, then try again.
Loading
base: 3.1.41
Choose a base ref
...
head repository: gitpython-developers/GitPython
Failed to load repositories. Confirm that selected head ref is valid, then try again.
Loading
compare: 3.1.42
Choose a head ref
Loading
9 changes: 4 additions & 5 deletions .github/workflows/cygwin-test.yml
Original file line number Diff line number Diff line change
@@ -15,7 +15,7 @@ jobs:

defaults:
run:
shell: C:\cygwin\bin\bash.exe --login --norc -eo pipefail -o igncr "{0}"
shell: C:\tools\cygwin\bin\bash.exe --login --norc -eo pipefail -o igncr "{0}"

steps:
- name: Force LF line endings
@@ -27,11 +27,10 @@ jobs:
with:
fetch-depth: 0

- name: Install Cygwin
uses: cygwin/cygwin-install-action@v4
- name: Set up Cygwin
uses: egor-tensin/setup-cygwin@v4
with:
packages: python39 python39-pip python39-virtualenv git
add-to-path: false # No need to change $PATH outside the Cygwin environment.
packages: python39=3.9.16-1 python39-pip python39-virtualenv git

- name: Arrange for verbose output
run: |
2 changes: 1 addition & 1 deletion .github/workflows/lint.yml
Original file line number Diff line number Diff line change
@@ -13,7 +13,7 @@ jobs:
with:
python-version: "3.x"

- uses: pre-commit/action@v3.0.0
- uses: pre-commit/action@v3.0.1
with:
extra_args: --all-files --hook-stage manual
env:
11 changes: 9 additions & 2 deletions .github/workflows/pythonpackage.yml
Original file line number Diff line number Diff line change
@@ -13,8 +13,15 @@ jobs:
strategy:
fail-fast: false
matrix:
os: ["ubuntu-latest", "macos-13", "windows-latest"]
os: ["ubuntu-latest", "macos-13", "macos-14", "windows-latest"]
python-version: ["3.7", "3.8", "3.9", "3.10", "3.11", "3.12"]
exclude:
- os: "macos-14"
python-version: "3.7"
- os: "macos-14"
python-version: "3.8"
- os: "macos-14"
python-version: "3.9"
include:
- experimental: false

@@ -37,7 +44,7 @@ jobs:

- name: Set up WSL (Windows)
if: startsWith(matrix.os, 'windows')
uses: Vampire/setup-wsl@v2.0.2
uses: Vampire/setup-wsl@v3.0.0
with:
distribution: Debian

35 changes: 35 additions & 0 deletions .readthedocs.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
# Read the Docs configuration file for Sphinx projects
# See https://docs.readthedocs.io/en/stable/config-file/v2.html for details

# Required
version: 2

# Set the OS, Python version and other tools you might need
build:
os: ubuntu-22.04
tools:
python: "3.12"
# You can also specify other tool versions:
# nodejs: "20"
# rust: "1.70"
# golang: "1.20"

# Build documentation in the "docs/" directory with Sphinx
sphinx:
configuration: doc/source/conf.py
# You can configure Sphinx to use a different builder, for instance use the dirhtml builder for simpler URLs
# builder: "dirhtml"
# Fail on all warnings to avoid broken references
# fail_on_warning: true

# Optionally build your docs in additional formats such as PDF and ePub
# formats:
# - pdf
# - epub

# Optional but recommended, declare the Python requirements required
# to build your documentation
# See https://docs.readthedocs.io/en/stable/guides/reproducible-builds.html
# python:
# install:
# - requirements: docs/requirements.txt
1 change: 1 addition & 0 deletions AUTHORS
Original file line number Diff line number Diff line change
@@ -53,5 +53,6 @@ Contributors are:
-Santos Gallegos <stsewd _at_ proton.me>
-Wenhan Zhu <wzhu.cosmos _at_ gmail.com>
-Eliah Kagan <eliah.kagan _at_ gmail.com>
-Ethan Lin <et.repositories _at_ gmail.com>

Portions derived from other open source works and are clearly marked.
53 changes: 2 additions & 51 deletions README.md
Original file line number Diff line number Diff line change
@@ -17,6 +17,8 @@ probably the skills to scratch that itch of mine: implement `git` in a way that
If you like the idea and want to learn more, please head over to [gitoxide](https://github.com/Byron/gitoxide), an
implementation of 'git' in [Rust](https://www.rust-lang.org).

*(Please note that `gitoxide` is not currently available for use in Python, and that Rust is required)*

## GitPython

GitPython is a python library used to interact with git repositories, high-level like git-porcelain,
@@ -220,57 +222,6 @@ Please have a look at the [contributions file][contributing].
6. Run `make release`.
7. Go to [GitHub Releases](https://github.com/gitpython-developers/GitPython/releases) and publish a new one with the recently pushed tag. Generate the changelog.

### How to verify a release (DEPRECATED)

Note that what follows is deprecated and future releases won't be signed anymore.
More details about how it came to that can be found [in this issue](https://github.com/gitpython-developers/gitdb/issues/77).

----

Please only use releases from `pypi` as you can verify the respective source
tarballs.

This script shows how to verify the tarball was indeed created by the authors of
this project:

```bash
curl https://files.pythonhosted.org/packages/09/bc/ae32e07e89cc25b9e5c793d19a1e5454d30a8e37d95040991160f942519e/GitPython-3.1.8-py3-none-any.whl > gitpython.whl
curl https://files.pythonhosted.org/packages/09/bc/ae32e07e89cc25b9e5c793d19a1e5454d30a8e37d95040991160f942519e/GitPython-3.1.8-py3-none-any.whl.asc > gitpython-signature.asc
gpg --verify gitpython-signature.asc gitpython.whl
```

which outputs

```bash
gpg: Signature made Fr 4 Sep 10:04:50 2020 CST
gpg: using RSA key 27C50E7F590947D7273A741E85194C08421980C9
gpg: Good signature from "Sebastian Thiel (YubiKey USB-C) <byronimo@gmail.com>" [ultimate]
gpg: aka "Sebastian Thiel (In Rust I trust) <sebastian.thiel@icloud.com>" [ultimate]
```

You can verify that the keyid indeed matches the release-signature key provided in this
repository by looking at the keys details:

```bash
gpg --list-packets ./release-verification-key.asc
```

You can verify that the commit adding it was also signed by it using:

```bash
git show --show-signature ./release-verification-key.asc
```

If you would like to trust it permanently, you can import and sign it:

```bash
gpg --import ./release-verification-key.asc
gpg --edit-key 4C08421980C9

> sign
> save
```

### Projects using GitPython

- [PyDriller](https://github.com/ishepard/pydriller)
2 changes: 1 addition & 1 deletion VERSION
Original file line number Diff line number Diff line change
@@ -1 +1 @@
3.1.41
3.1.42
7 changes: 6 additions & 1 deletion doc/requirements.txt
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
sphinx==4.3.0
sphinx == 4.3.2
sphinx_rtd_theme
sphinxcontrib-applehelp >= 1.0.2, <= 1.0.4
sphinxcontrib-devhelp == 1.0.2
sphinxcontrib-htmlhelp >= 2.0.0, <= 2.0.1
sphinxcontrib-qthelp == 1.0.3
sphinxcontrib-serializinghtml == 1.1.5
sphinx-autodoc-typehints
8 changes: 7 additions & 1 deletion doc/source/changes.rst
Original file line number Diff line number Diff line change
@@ -2,6 +2,12 @@
Changelog
=========

3.1.42
======

See the following for all changes.
https://github.com/gitpython-developers/GitPython/releases/tag/3.1.42

3.1.41
======

@@ -12,7 +18,7 @@ See this PR for details: https://github.com/gitpython-developers/GitPython/pull/
An advisory is available soon at: https://github.com/gitpython-developers/GitPython/security/advisories/GHSA-2mqj-m65w-jghx

See the following for all changes.
https://github.com/gitpython-developers/GitPython/releases/tag/3.1.40
https://github.com/gitpython-developers/GitPython/releases/tag/3.1.41

3.1.40
======
2 changes: 1 addition & 1 deletion doc/source/conf.py
Original file line number Diff line number Diff line change
@@ -93,7 +93,7 @@
# Options for HTML output
# -----------------------

html_theme = "sphinx_rtd_theme"
# html_theme = "sphinx_rtd_theme"
html_theme_options = {}

# The name for this set of Sphinx documents. If None, it defaults to
54 changes: 27 additions & 27 deletions git/cmd.py
Original file line number Diff line number Diff line change
@@ -81,8 +81,7 @@
"strip_newline_in_stdout",
}

log = logging.getLogger(__name__)
log.addHandler(logging.NullHandler())
_logger = logging.getLogger(__name__)

__all__ = ("Git",)

@@ -146,7 +145,7 @@ def pump_stream(
handler(line)

except Exception as ex:
log.error(f"Pumping {name!r} of cmd({remove_password_if_present(cmdline)}) failed due to: {ex!r}")
_logger.error(f"Pumping {name!r} of cmd({remove_password_if_present(cmdline)}) failed due to: {ex!r}")
if "I/O operation on closed file" not in str(ex):
# Only reraise if the error was not due to the stream closing
raise CommandError([f"<{name}-pump>"] + remove_password_if_present(cmdline), ex) from ex
@@ -410,15 +409,15 @@ def refresh(cls, path: Union[None, PathLike] = None) -> bool:
# expect GIT_PYTHON_REFRESH to either be unset or be one of the
# following values:
#
# 0|q|quiet|s|silence|n|none
# 1|w|warn|warning
# 2|r|raise|e|error
# 0|q|quiet|s|silence|silent|n|none
# 1|w|warn|warning|l|log
# 2|r|raise|e|error|exception

mode = os.environ.get(cls._refresh_env_var, "raise").lower()

quiet = ["quiet", "q", "silence", "s", "none", "n", "0"]
warn = ["warn", "w", "warning", "1"]
error = ["error", "e", "raise", "r", "2"]
quiet = ["quiet", "q", "silence", "s", "silent", "none", "n", "0"]
warn = ["warn", "w", "warning", "log", "l", "1"]
error = ["error", "e", "exception", "raise", "r", "2"]

if mode in quiet:
pass
@@ -429,10 +428,10 @@ def refresh(cls, path: Union[None, PathLike] = None) -> bool:
%s
All git commands will error until this is rectified.
This initial warning can be silenced or aggravated in the future by setting the
This initial message can be silenced or aggravated in the future by setting the
$%s environment variable. Use one of the following values:
- %s: for no warning or exception
- %s: for a printed warning
- %s: for no message or exception
- %s: for a warning message (logged at level CRITICAL, displayed by default)
- %s: for a raised exception
Example:
@@ -451,7 +450,7 @@ def refresh(cls, path: Union[None, PathLike] = None) -> bool:
)

if mode in warn:
print("WARNING: %s" % err)
_logger.critical(err)
else:
raise ImportError(err)
else:
@@ -461,8 +460,8 @@ def refresh(cls, path: Union[None, PathLike] = None) -> bool:
%s environment variable has been set but it has been set with an invalid value.
Use only the following values:
- %s: for no warning or exception
- %s: for a printed warning
- %s: for no message or exception
- %s: for a warning message (logged at level CRITICAL, displayed by default)
- %s: for a raised exception
"""
)
@@ -475,14 +474,15 @@ def refresh(cls, path: Union[None, PathLike] = None) -> bool:
)
raise ImportError(err)

# We get here if this was the init refresh and the refresh mode was not
# error. Go ahead and set the GIT_PYTHON_GIT_EXECUTABLE such that we
# discern the difference between a first import and a second import.
# We get here if this was the initial refresh and the refresh mode was
# not error. Go ahead and set the GIT_PYTHON_GIT_EXECUTABLE such that we
# discern the difference between the first refresh at import time
# and subsequent calls to git.refresh or this refresh method.
cls.GIT_PYTHON_GIT_EXECUTABLE = cls.git_exec_name
else:
# After the first refresh (when GIT_PYTHON_GIT_EXECUTABLE is no longer
# None) we raise an exception.
raise GitCommandNotFound("git", err)
raise GitCommandNotFound(new_git, err)

return has_git

@@ -599,7 +599,7 @@ def _terminate(self) -> None:
self.status = self._status_code_if_terminate or proc.poll()
return
except OSError as ex:
log.info("Ignored error after process had died: %r", ex)
_logger.info("Ignored error after process had died: %r", ex)

# It can be that nothing really exists anymore...
if os is None or getattr(os, "kill", None) is None:
@@ -612,7 +612,7 @@ def _terminate(self) -> None:

self.status = self._status_code_if_terminate or status
except OSError as ex:
log.info("Ignored error after process had died: %r", ex)
_logger.info("Ignored error after process had died: %r", ex)
# END exception handling

def __del__(self) -> None:
@@ -653,7 +653,7 @@ def read_all_from_possibly_closed_stream(stream: Union[IO[bytes], None]) -> byte

if status != 0:
errstr = read_all_from_possibly_closed_stream(p_stderr)
log.debug("AutoInterrupt wait stderr: %r" % (errstr,))
_logger.debug("AutoInterrupt wait stderr: %r" % (errstr,))
raise GitCommandError(remove_password_if_present(self.args), status, errstr)
return status

@@ -1017,7 +1017,7 @@ def execute(
# Remove password for the command if present.
redacted_command = remove_password_if_present(command)
if self.GIT_PYTHON_TRACE and (self.GIT_PYTHON_TRACE != "full" or as_process):
log.info(" ".join(redacted_command))
_logger.info(" ".join(redacted_command))

# Allow the user to have the command executed in their working dir.
try:
@@ -1054,7 +1054,7 @@ def execute(
stdout_sink = PIPE if with_stdout else getattr(subprocess, "DEVNULL", None) or open(os.devnull, "wb")
if shell is None:
shell = self.USE_SHELL
log.debug(
_logger.debug(
"Popen(%s, cwd=%s, stdin=%s, shell=%s, universal_newlines=%s)",
redacted_command,
cwd,
@@ -1166,17 +1166,17 @@ def as_text(stdout_value: Union[bytes, str]) -> str:
# END as_text

if stderr_value:
log.info(
_logger.info(
"%s -> %d; stdout: '%s'; stderr: '%s'",
cmdstr,
status,
as_text(stdout_value),
safe_decode(stderr_value),
)
elif stdout_value:
log.info("%s -> %d; stdout: '%s'", cmdstr, status, as_text(stdout_value))
_logger.info("%s -> %d; stdout: '%s'", cmdstr, status, as_text(stdout_value))
else:
log.info("%s -> %d", cmdstr, status)
_logger.info("%s -> %d", cmdstr, status)
# END handle debug printing

if with_exceptions and status != 0:
Loading