Skip to content

Commit 24c4a0e

Browse files
committed
__init__: don't run refresh on import
Consumers of gitpython may not need to use it in all use cases, and may want to be able to run (without using gitpython) in environments where git is not available on PATH. While this can be worked around by setting the GIT_PYTHON_REFRESH environment variable, adding special handling for gitpython means that it can't be imported just like everything else in an import block at the top of the module, and environment variables have potentially undesired propagation behaviour. Previously, it was also nontrivial to distinguish gitpython failing to import because of missing git or because e.g. gitpython isn't installed at all, because the exception that's raised is an ImportError without further qualification (except in the error message). Thus, we now no longer perform `refresh` at the module top level, instead performing it lazily when an invocation of git is attempted. This also allows some functionality that doesn't rely on the git command to work without, e.g. ref listing.
1 parent 2d4c541 commit 24c4a0e

File tree

4 files changed

+20
-6
lines changed

4 files changed

+20
-6
lines changed

doc/source/changes.rst

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,19 @@
22
Changelog
33
=========
44

5+
4.0.0
6+
=====
7+
8+
GitPython will no longer throw an ImportError when no git executable can
9+
be found at import time. Instead, errors are deferred until the first
10+
attempt at using it. Consumers with special handling for
11+
the old ImportError behaviour should instead call `git.refresh` and handle
12+
GitCommandNotFoundErrors themselves.
13+
14+
See the following for all changes.
15+
https://github.com/gitpython-developers/GitPython/releases/tag/4.0.0
16+
17+
518
3.1.45
619
======
720

git/__init__.py

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -292,9 +292,4 @@ def refresh(path: Optional[PathLike] = None) -> None:
292292
GIT_OK = True
293293

294294

295-
try:
296-
refresh()
297-
except Exception as _exc:
298-
raise ImportError("Failed to initialize: {0}".format(_exc)) from _exc
299-
300295
# } END initialize git executable path

git/cmd.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -857,7 +857,7 @@ def refresh(cls, path: Union[None, PathLike] = None) -> bool:
857857
if mode in warn:
858858
_logger.critical(err)
859859
else:
860-
raise ImportError(err)
860+
raise GitCommandNotFound(new_git, err)
861861
else:
862862
err = dedent(
863863
"""\
@@ -1575,6 +1575,8 @@ def _call_process(
15751575
default (especially ``as_process = False``, ``stdout_as_string = True``) and
15761576
return :class:`str`.
15771577
"""
1578+
if not self.GIT_PYTHON_GIT_EXECUTABLE:
1579+
self.refresh()
15781580
# Handle optional arguments prior to calling transform_kwargs.
15791581
# Otherwise these'll end up in args, which is bad.
15801582
exec_kwargs = {k: v for k, v in kwargs.items() if k in execute_kwargs}

test/__init__.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,3 +2,7 @@
22
#
33
# This module is part of GitPython and is released under the
44
# 3-Clause BSD License: https://opensource.org/license/bsd-3-clause/
5+
#
6+
import git
7+
8+
git.refresh()

0 commit comments

Comments
 (0)