GitPython 3.1.61__py3-none-any.whl → 3.2.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- git/__init__.py +2 -2
- git/cmd.py +134 -40
- git/config.py +195 -64
- git/diff.py +12 -3
- git/index/base.py +67 -14
- git/index/fun.py +42 -12
- git/index/typ.py +15 -8
- git/objects/base.py +10 -2
- git/objects/blob.py +1 -5
- git/objects/commit.py +18 -15
- git/objects/fun.py +35 -43
- git/objects/submodule/base.py +129 -44
- git/objects/submodule/root.py +80 -68
- git/objects/tag.py +3 -8
- git/objects/tree.py +3 -9
- git/objects/util.py +4 -3
- git/refs/head.py +3 -3
- git/refs/reference.py +1 -1
- git/refs/remote.py +1 -1
- git/refs/symbolic.py +62 -16
- git/refs/tag.py +2 -2
- git/remote.py +27 -17
- git/repo/base.py +59 -22
- git/repo/fun.py +27 -101
- git/types.py +23 -17
- git/util.py +38 -10
- {gitpython-3.1.61.dist-info → gitpython-3.2.0.dist-info}/METADATA +8 -22
- gitpython-3.2.0.dist-info/RECORD +44 -0
- gitpython-3.1.61.dist-info/RECORD +0 -44
- {gitpython-3.1.61.dist-info → gitpython-3.2.0.dist-info}/WHEEL +0 -0
- {gitpython-3.1.61.dist-info → gitpython-3.2.0.dist-info}/licenses/AUTHORS +0 -0
- {gitpython-3.1.61.dist-info → gitpython-3.2.0.dist-info}/licenses/LICENSE +0 -0
- {gitpython-3.1.61.dist-info → gitpython-3.2.0.dist-info}/top_level.txt +0 -0
git/__init__.py
CHANGED
|
@@ -86,7 +86,7 @@ __all__ = [
|
|
|
86
86
|
"to_hex_sha",
|
|
87
87
|
]
|
|
88
88
|
|
|
89
|
-
__version__ = '3.
|
|
89
|
+
__version__ = '3.2.0'
|
|
90
90
|
|
|
91
91
|
from typing import Any, List, Optional, Sequence, TYPE_CHECKING, Tuple, Union
|
|
92
92
|
|
|
@@ -295,6 +295,6 @@ def refresh(path: Optional[PathLike] = None) -> None:
|
|
|
295
295
|
try:
|
|
296
296
|
refresh()
|
|
297
297
|
except Exception as _exc:
|
|
298
|
-
raise ImportError("Failed to initialize: {
|
|
298
|
+
raise ImportError(f"Failed to initialize: {_exc}") from _exc
|
|
299
299
|
|
|
300
300
|
# } END initialize git executable path
|
git/cmd.py
CHANGED
|
@@ -100,7 +100,7 @@ _logger = logging.getLogger(__name__)
|
|
|
100
100
|
|
|
101
101
|
|
|
102
102
|
def handle_process_output(
|
|
103
|
-
process: "Git.AutoInterrupt"
|
|
103
|
+
process: Union["Git.AutoInterrupt", Popen],
|
|
104
104
|
stdout_handler: Union[
|
|
105
105
|
None,
|
|
106
106
|
Callable[[AnyStr], None],
|
|
@@ -395,9 +395,7 @@ class _AutoInterrupt:
|
|
|
395
395
|
:raise git.exc.GitCommandError:
|
|
396
396
|
If the return status is not 0.
|
|
397
397
|
"""
|
|
398
|
-
|
|
399
|
-
stderr_b = b""
|
|
400
|
-
stderr_b = force_bytes(data=stderr, encoding="utf-8")
|
|
398
|
+
stderr_b = force_bytes(data=stderr, encoding="utf-8") or b""
|
|
401
399
|
status: Union[int, None]
|
|
402
400
|
if self.proc is not None:
|
|
403
401
|
status = self.proc.wait()
|
|
@@ -647,7 +645,9 @@ class Git(metaclass=_GitMeta):
|
|
|
647
645
|
"_version_info_token",
|
|
648
646
|
)
|
|
649
647
|
|
|
650
|
-
|
|
648
|
+
# Match Git's leading transport selector, including an empty helper name.
|
|
649
|
+
# Git also selects the command-executing ext helper for an ext:// URL.
|
|
650
|
+
re_unsafe_protocol = re.compile(r"([A-Za-z0-9][A-Za-z0-9+.-]*|)::|ext://")
|
|
651
651
|
|
|
652
652
|
unsafe_git_ls_remote_options = [
|
|
653
653
|
# This option allows arbitrary command execution in git-ls-remote.
|
|
@@ -947,7 +947,8 @@ class Git(metaclass=_GitMeta):
|
|
|
947
947
|
|
|
948
948
|
Apart from the usual protocols (http, git, ssh), Git allows "remote helpers"
|
|
949
949
|
that have the form ``<transport>::<address>``. One of these helpers (``ext::``)
|
|
950
|
-
can be used to invoke any arbitrary command.
|
|
950
|
+
can be used to invoke any arbitrary command. Git also selects that helper
|
|
951
|
+
for ``ext://`` URLs and interprets the URL as a command path.
|
|
951
952
|
|
|
952
953
|
See:
|
|
953
954
|
|
|
@@ -956,11 +957,19 @@ class Git(metaclass=_GitMeta):
|
|
|
956
957
|
"""
|
|
957
958
|
match = cls.re_unsafe_protocol.match(url)
|
|
958
959
|
if match:
|
|
959
|
-
protocol = match.group(
|
|
960
|
+
protocol = match.group(0)
|
|
960
961
|
raise UnsafeProtocolError(
|
|
961
|
-
f"The `{protocol}
|
|
962
|
+
f"The `{protocol}` protocol looks suspicious, use `allow_unsafe_protocols=True` to allow it."
|
|
962
963
|
)
|
|
963
964
|
|
|
965
|
+
def _check_unsafe_protocols_in_args(self, args: Sequence[Any], kwargs: Mapping[str, Any]) -> None:
|
|
966
|
+
"""Check positional operands and standalone values in rendered command options.
|
|
967
|
+
|
|
968
|
+
A short flag's split value can become the repository operand before ``--``.
|
|
969
|
+
"""
|
|
970
|
+
for arg in self._unpack_args(args) + self.transform_kwargs(**kwargs):
|
|
971
|
+
self.check_unsafe_protocols(arg)
|
|
972
|
+
|
|
964
973
|
@classmethod
|
|
965
974
|
def _canonicalize_option_name(cls, option: str) -> str:
|
|
966
975
|
"""Return the option name used for unsafe-option checks.
|
|
@@ -1131,16 +1140,23 @@ class Git(metaclass=_GitMeta):
|
|
|
1131
1140
|
self,
|
|
1132
1141
|
*args: Any,
|
|
1133
1142
|
allow_unsafe_options: bool = False,
|
|
1143
|
+
allow_unsafe_protocols: bool = False,
|
|
1134
1144
|
**kwargs: Any,
|
|
1135
1145
|
) -> Union[str, bytes, Tuple[int, Union[str, bytes], str], "Git.AutoInterrupt"]:
|
|
1136
1146
|
"""List references in a remote repository.
|
|
1137
1147
|
|
|
1138
1148
|
:param allow_unsafe_options:
|
|
1139
1149
|
Allow unsafe options, like ``--upload-pack`` or ``--exec``.
|
|
1150
|
+
|
|
1151
|
+
:param allow_unsafe_protocols:
|
|
1152
|
+
Allow unsafe protocols to be used, like ``ext``. Positional arguments
|
|
1153
|
+
and split short-option values are checked.
|
|
1140
1154
|
"""
|
|
1141
1155
|
if not allow_unsafe_options:
|
|
1142
1156
|
candidate_options = self._option_candidates(args, kwargs)
|
|
1143
1157
|
Git.check_unsafe_options(options=candidate_options, unsafe_options=self.unsafe_git_ls_remote_options)
|
|
1158
|
+
if not allow_unsafe_protocols:
|
|
1159
|
+
self._check_unsafe_protocols_in_args(args, kwargs)
|
|
1144
1160
|
return self._call_process("ls_remote", *args, **kwargs)
|
|
1145
1161
|
|
|
1146
1162
|
@property
|
|
@@ -1180,52 +1196,112 @@ class Git(metaclass=_GitMeta):
|
|
|
1180
1196
|
def execute(
|
|
1181
1197
|
self,
|
|
1182
1198
|
command: Union[str, Sequence[Any]],
|
|
1199
|
+
istream: Union[None, int, BinaryIO] = None,
|
|
1183
1200
|
*,
|
|
1184
1201
|
as_process: Literal[True],
|
|
1202
|
+
**subprocess_kwargs: Any,
|
|
1185
1203
|
) -> "AutoInterrupt": ...
|
|
1186
1204
|
|
|
1187
1205
|
@overload
|
|
1188
1206
|
def execute(
|
|
1189
1207
|
self,
|
|
1190
1208
|
command: Union[str, Sequence[Any]],
|
|
1209
|
+
istream: Union[None, int, BinaryIO] = None,
|
|
1191
1210
|
*,
|
|
1192
1211
|
as_process: Literal[False] = False,
|
|
1193
|
-
|
|
1194
|
-
|
|
1212
|
+
with_extended_output: Literal[False] = False,
|
|
1213
|
+
stdout_as_string: Literal[True] = True,
|
|
1214
|
+
with_stdout: Literal[True] = True,
|
|
1215
|
+
**subprocess_kwargs: Any,
|
|
1216
|
+
) -> str: ...
|
|
1195
1217
|
|
|
1196
1218
|
@overload
|
|
1197
1219
|
def execute(
|
|
1198
1220
|
self,
|
|
1199
1221
|
command: Union[str, Sequence[Any]],
|
|
1222
|
+
istream: Union[None, int, BinaryIO] = None,
|
|
1200
1223
|
*,
|
|
1201
1224
|
as_process: Literal[False] = False,
|
|
1202
|
-
|
|
1203
|
-
|
|
1225
|
+
with_extended_output: Literal[False] = False,
|
|
1226
|
+
stdout_as_string: Literal[False],
|
|
1227
|
+
universal_newlines: Literal[False] = False,
|
|
1228
|
+
with_stdout: Literal[True] = True,
|
|
1229
|
+
**subprocess_kwargs: Any,
|
|
1230
|
+
) -> bytes: ...
|
|
1204
1231
|
|
|
1205
1232
|
@overload
|
|
1206
1233
|
def execute(
|
|
1207
1234
|
self,
|
|
1208
1235
|
command: Union[str, Sequence[Any]],
|
|
1236
|
+
istream: Union[None, int, BinaryIO] = None,
|
|
1209
1237
|
*,
|
|
1210
|
-
|
|
1211
|
-
|
|
1212
|
-
stdout_as_string: Literal[True],
|
|
1213
|
-
|
|
1238
|
+
as_process: Literal[False] = False,
|
|
1239
|
+
with_extended_output: Literal[True],
|
|
1240
|
+
stdout_as_string: Literal[True] = True,
|
|
1241
|
+
with_stdout: Literal[True] = True,
|
|
1242
|
+
**subprocess_kwargs: Any,
|
|
1243
|
+
) -> Tuple[int, str, str]: ...
|
|
1214
1244
|
|
|
1215
1245
|
@overload
|
|
1216
1246
|
def execute(
|
|
1217
1247
|
self,
|
|
1218
1248
|
command: Union[str, Sequence[Any]],
|
|
1249
|
+
istream: Union[None, int, BinaryIO] = None,
|
|
1219
1250
|
*,
|
|
1220
|
-
|
|
1221
|
-
|
|
1251
|
+
as_process: Literal[False] = False,
|
|
1252
|
+
with_extended_output: Literal[True],
|
|
1222
1253
|
stdout_as_string: Literal[False],
|
|
1223
|
-
|
|
1254
|
+
universal_newlines: Literal[False] = False,
|
|
1255
|
+
with_stdout: Literal[True] = True,
|
|
1256
|
+
**subprocess_kwargs: Any,
|
|
1257
|
+
) -> Tuple[int, bytes, str]: ...
|
|
1224
1258
|
|
|
1259
|
+
@overload
|
|
1225
1260
|
def execute(
|
|
1226
1261
|
self,
|
|
1227
1262
|
command: Union[str, Sequence[Any]],
|
|
1228
|
-
istream: Union[None, BinaryIO] = None,
|
|
1263
|
+
istream: Union[None, int, BinaryIO] = None,
|
|
1264
|
+
*,
|
|
1265
|
+
as_process: Literal[False] = False,
|
|
1266
|
+
with_extended_output: Literal[True],
|
|
1267
|
+
**subprocess_kwargs: Any,
|
|
1268
|
+
) -> Tuple[int, Union[str, bytes, None], str]: ...
|
|
1269
|
+
|
|
1270
|
+
@overload
|
|
1271
|
+
def execute(
|
|
1272
|
+
self,
|
|
1273
|
+
command: Union[str, Sequence[Any]],
|
|
1274
|
+
istream: Union[None, int, BinaryIO] = None,
|
|
1275
|
+
*,
|
|
1276
|
+
as_process: Literal[False] = False,
|
|
1277
|
+
with_extended_output: Literal[False] = False,
|
|
1278
|
+
**subprocess_kwargs: Any,
|
|
1279
|
+
) -> Union[str, bytes, None]: ...
|
|
1280
|
+
|
|
1281
|
+
@overload
|
|
1282
|
+
def execute(
|
|
1283
|
+
self,
|
|
1284
|
+
command: Union[str, Sequence[Any]],
|
|
1285
|
+
istream: Union[None, int, BinaryIO] = None,
|
|
1286
|
+
with_extended_output: bool = False,
|
|
1287
|
+
with_exceptions: bool = True,
|
|
1288
|
+
as_process: bool = False,
|
|
1289
|
+
output_stream: Union[None, BinaryIO] = None,
|
|
1290
|
+
stdout_as_string: bool = True,
|
|
1291
|
+
kill_after_timeout: Union[None, float] = None,
|
|
1292
|
+
with_stdout: bool = True,
|
|
1293
|
+
universal_newlines: bool = False,
|
|
1294
|
+
shell: Union[None, bool] = None,
|
|
1295
|
+
env: Union[None, Mapping[str, str]] = None,
|
|
1296
|
+
max_chunk_size: int = io.DEFAULT_BUFFER_SIZE,
|
|
1297
|
+
strip_newline_in_stdout: bool = True,
|
|
1298
|
+
**subprocess_kwargs: Any,
|
|
1299
|
+
) -> Union[None, str, bytes, Tuple[int, Union[str, bytes, None], str], AutoInterrupt]: ...
|
|
1300
|
+
|
|
1301
|
+
def execute(
|
|
1302
|
+
self,
|
|
1303
|
+
command: Union[str, Sequence[Any]],
|
|
1304
|
+
istream: Union[None, int, BinaryIO] = None,
|
|
1229
1305
|
with_extended_output: bool = False,
|
|
1230
1306
|
with_exceptions: bool = True,
|
|
1231
1307
|
as_process: bool = False,
|
|
@@ -1239,7 +1315,7 @@ class Git(metaclass=_GitMeta):
|
|
|
1239
1315
|
max_chunk_size: int = io.DEFAULT_BUFFER_SIZE,
|
|
1240
1316
|
strip_newline_in_stdout: bool = True,
|
|
1241
1317
|
**subprocess_kwargs: Any,
|
|
1242
|
-
) -> Union[str, bytes, Tuple[int, Union[str, bytes], str], AutoInterrupt]:
|
|
1318
|
+
) -> Union[None, str, bytes, Tuple[int, Union[str, bytes, None], str], AutoInterrupt]:
|
|
1243
1319
|
R"""Handle executing the command, and consume and return the returned
|
|
1244
1320
|
information (stdout).
|
|
1245
1321
|
|
|
@@ -1303,9 +1379,9 @@ class Git(metaclass=_GitMeta):
|
|
|
1303
1379
|
carefully considered, due to the following limitations:
|
|
1304
1380
|
|
|
1305
1381
|
1. This feature is not supported at all on Windows.
|
|
1306
|
-
2.
|
|
1307
|
-
|
|
1308
|
-
|
|
1382
|
+
2. Enumerating child processes requires ``pgrep -P``, or a ``ps`` command
|
|
1383
|
+
supporting the POSIX ``-A`` and ``-o`` options if ``pgrep`` is not
|
|
1384
|
+
installed. Effectiveness may vary on systems without these commands.
|
|
1309
1385
|
3. Deeper descendants do not receive signals, though they may sometimes
|
|
1310
1386
|
terminate as a consequence of their parent processes being killed.
|
|
1311
1387
|
4. `kill_after_timeout` uses ``SIGKILL``, which can have negative side
|
|
@@ -1465,14 +1541,24 @@ class Git(metaclass=_GitMeta):
|
|
|
1465
1541
|
|
|
1466
1542
|
This callback implementation would be ineffective and unsafe on Windows.
|
|
1467
1543
|
"""
|
|
1468
|
-
p = Popen(["ps", "--ppid", str(pid)], stdout=PIPE)
|
|
1469
1544
|
child_pids = []
|
|
1470
|
-
|
|
1471
|
-
|
|
1472
|
-
|
|
1473
|
-
|
|
1474
|
-
|
|
1475
|
-
|
|
1545
|
+
try:
|
|
1546
|
+
p = Popen(["pgrep", "-P", str(pid)], stdout=PIPE)
|
|
1547
|
+
except FileNotFoundError:
|
|
1548
|
+
# POSIX ps does not support selecting by parent PID.
|
|
1549
|
+
with Popen(["ps", "-A", "-o", "pid=", "-o", "ppid="], stdout=PIPE) as p:
|
|
1550
|
+
if p.stdout is not None:
|
|
1551
|
+
for line in p.stdout:
|
|
1552
|
+
fields = line.split()
|
|
1553
|
+
if len(fields) == 2 and all(field.isdigit() for field in fields):
|
|
1554
|
+
if int(fields[1]) == pid:
|
|
1555
|
+
child_pids.append(int(fields[0]))
|
|
1556
|
+
else:
|
|
1557
|
+
with p:
|
|
1558
|
+
if p.stdout is not None:
|
|
1559
|
+
for line in p.stdout:
|
|
1560
|
+
if line.strip().isdigit():
|
|
1561
|
+
child_pids.append(int(line))
|
|
1476
1562
|
try:
|
|
1477
1563
|
os.kill(pid, signal.SIGKILL)
|
|
1478
1564
|
for child_pid in child_pids:
|
|
@@ -1493,7 +1579,7 @@ class Git(metaclass=_GitMeta):
|
|
|
1493
1579
|
err = f'Timeout: the command "{" ".join(redacted_command)}" did not complete in {timeout:g} secs.'
|
|
1494
1580
|
return err if universal_newlines else err.encode(defenc)
|
|
1495
1581
|
|
|
1496
|
-
def communicate() -> Tuple[
|
|
1582
|
+
def communicate() -> Tuple[Union[str, bytes, None], Union[str, bytes, None]]:
|
|
1497
1583
|
assert watchdog is not None
|
|
1498
1584
|
assert kill_check is not None
|
|
1499
1585
|
watchdog.start()
|
|
@@ -1513,8 +1599,8 @@ class Git(metaclass=_GitMeta):
|
|
|
1513
1599
|
|
|
1514
1600
|
# Wait for the process to return.
|
|
1515
1601
|
status = 0
|
|
1516
|
-
stdout_value: Union[str, bytes] = b""
|
|
1517
|
-
stderr_value: Union[str, bytes] = b""
|
|
1602
|
+
stdout_value: Union[str, bytes, None] = b""
|
|
1603
|
+
stderr_value: Union[str, bytes, None] = b""
|
|
1518
1604
|
newline = "\n" if universal_newlines else b"\n"
|
|
1519
1605
|
try:
|
|
1520
1606
|
if output_stream is None:
|
|
@@ -1556,7 +1642,7 @@ class Git(metaclass=_GitMeta):
|
|
|
1556
1642
|
if self.GIT_PYTHON_TRACE == "full":
|
|
1557
1643
|
cmdstr = " ".join(redacted_command)
|
|
1558
1644
|
|
|
1559
|
-
def as_text(stdout_value: Union[bytes, str]) -> str:
|
|
1645
|
+
def as_text(stdout_value: Union[bytes, str, None]) -> str:
|
|
1560
1646
|
return not output_stream and safe_decode(stdout_value) or "<OUTPUT_STREAM>"
|
|
1561
1647
|
|
|
1562
1648
|
# END as_text
|
|
@@ -1581,6 +1667,8 @@ class Git(metaclass=_GitMeta):
|
|
|
1581
1667
|
if isinstance(stdout_value, bytes) and stdout_as_string: # Could also be output_stream.
|
|
1582
1668
|
stdout_value = safe_decode(stdout_value)
|
|
1583
1669
|
|
|
1670
|
+
# stderr is always captured through PIPE.
|
|
1671
|
+
assert stderr_value is not None
|
|
1584
1672
|
# Allow access to the command's status code.
|
|
1585
1673
|
if with_extended_output:
|
|
1586
1674
|
return (status, stdout_value, safe_decode(stderr_value))
|
|
@@ -1725,6 +1813,12 @@ class Git(metaclass=_GitMeta):
|
|
|
1725
1813
|
This allows your commands to call git more conveniently, as ``None`` is
|
|
1726
1814
|
realized as non-existent.
|
|
1727
1815
|
|
|
1816
|
+
Positional arguments may intentionally contain command options. Higher-level
|
|
1817
|
+
APIs must separate their operands with ``--`` where the Git command supports
|
|
1818
|
+
it, or reject option-shaped operands where Git reparses them internally (for
|
|
1819
|
+
example, ``pull`` and ``remote update``). Shell quoting cannot prevent Git
|
|
1820
|
+
from interpreting a leading-dash argument as an option.
|
|
1821
|
+
|
|
1728
1822
|
:param kwargs:
|
|
1729
1823
|
Contains key-values for the following:
|
|
1730
1824
|
|
|
@@ -1819,7 +1913,7 @@ class Git(metaclass=_GitMeta):
|
|
|
1819
1913
|
raise ValueError("Failed to parse header: %r" % header_line)
|
|
1820
1914
|
return (tokens[0], tokens[1], int(tokens[2]))
|
|
1821
1915
|
|
|
1822
|
-
def _prepare_ref(self, ref:
|
|
1916
|
+
def _prepare_ref(self, ref: object) -> bytes:
|
|
1823
1917
|
# Required for command to separate refs on stdin, as bytes.
|
|
1824
1918
|
if isinstance(ref, bytes):
|
|
1825
1919
|
# Assume 40 bytes hexsha - bin-to-ascii for some reason returns bytes, not text.
|
|
@@ -1846,7 +1940,7 @@ class Git(metaclass=_GitMeta):
|
|
|
1846
1940
|
cmd = cast("Git.AutoInterrupt", cmd)
|
|
1847
1941
|
return cmd
|
|
1848
1942
|
|
|
1849
|
-
def __get_object_header(self, cmd: "Git.AutoInterrupt", ref:
|
|
1943
|
+
def __get_object_header(self, cmd: "Git.AutoInterrupt", ref: Union[str, bytes]) -> Tuple[str, str, int]:
|
|
1850
1944
|
if cmd.stdin and cmd.stdout:
|
|
1851
1945
|
cmd.stdin.write(self._prepare_ref(ref))
|
|
1852
1946
|
cmd.stdin.flush()
|
|
@@ -1854,7 +1948,7 @@ class Git(metaclass=_GitMeta):
|
|
|
1854
1948
|
else:
|
|
1855
1949
|
raise ValueError("cmd stdin was empty")
|
|
1856
1950
|
|
|
1857
|
-
def get_object_header(self, ref: str) -> Tuple[str, str, int]:
|
|
1951
|
+
def get_object_header(self, ref: Union[str, bytes]) -> Tuple[str, str, int]:
|
|
1858
1952
|
"""Use this method to quickly examine the type and size of the object behind the
|
|
1859
1953
|
given ref.
|
|
1860
1954
|
|
|
@@ -1868,7 +1962,7 @@ class Git(metaclass=_GitMeta):
|
|
|
1868
1962
|
cmd = self._get_persistent_cmd("cat_file_header", "cat_file", batch_check=True)
|
|
1869
1963
|
return self.__get_object_header(cmd, ref)
|
|
1870
1964
|
|
|
1871
|
-
def get_object_data(self, ref: str) -> Tuple[str, str, int, bytes]:
|
|
1965
|
+
def get_object_data(self, ref: Union[str, bytes]) -> Tuple[str, str, int, bytes]:
|
|
1872
1966
|
"""Similar to :meth:`get_object_header`, but returns object data as well.
|
|
1873
1967
|
|
|
1874
1968
|
:return:
|
|
@@ -1882,7 +1976,7 @@ class Git(metaclass=_GitMeta):
|
|
|
1882
1976
|
del stream
|
|
1883
1977
|
return (hexsha, typename, size, data)
|
|
1884
1978
|
|
|
1885
|
-
def stream_object_data(self, ref: str) -> Tuple[str, str, int, "Git.CatFileContentStream"]:
|
|
1979
|
+
def stream_object_data(self, ref: Union[str, bytes]) -> Tuple[str, str, int, "Git.CatFileContentStream"]:
|
|
1886
1980
|
"""Similar to :meth:`get_object_data`, but returns the data as a stream.
|
|
1887
1981
|
|
|
1888
1982
|
:return:
|