Skip to content

Commit 35ba6fd

Browse files
committed
Merge remote-tracking branch 'BenediktSeidl/typing-3'
2 parents dc1c22c + 41a76dd commit 35ba6fd

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

65 files changed

+695
-239
lines changed

.github/workflows/lint.yml

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,11 @@ jobs:
2222
- name: Install ruff
2323
run: pip install ruff
2424

25-
- name: Check code style with ruff
25+
- name: Format code with ruff
2626
run: ruff format --diff
2727

28+
- name: Check code style with ruff
29+
run: ruff check
30+
2831
- name: Check typing with mypy
2932
run: LIBSSH2_VERSION=1.11.1 LIBGIT2_VERSION=1.9.1 /bin/sh build.sh mypy

build.sh

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -269,7 +269,7 @@ if [ "$1" = "mypy" ]; then
269269
$PREFIX/bin/pip install $WHEELDIR/pygit2*-$PYTHON_TAG-*.whl
270270
fi
271271
$PREFIX/bin/pip install -r requirements-test.txt
272-
$PREFIX/bin/mypy pygit2
272+
$PREFIX/bin/mypy pygit2 test
273273
fi
274274

275275
# Test .pyi stub file

pygit2/__init__.py

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -30,26 +30,29 @@
3030
import os
3131
import typing
3232

33-
# Low level API
34-
from ._pygit2 import *
35-
from ._pygit2 import _cache_enums
36-
3733
# High level API
3834
from . import enums
3935
from ._build import __version__
36+
37+
# Low level API
38+
from ._pygit2 import *
39+
from ._pygit2 import _cache_enums
4040
from .blame import Blame, BlameHunk
4141
from .blob import BlobIO
42-
from .callbacks import Payload, RemoteCallbacks, CheckoutCallbacks, StashApplyCallbacks
4342
from .callbacks import (
43+
CheckoutCallbacks,
44+
Payload,
45+
RemoteCallbacks,
46+
StashApplyCallbacks,
47+
get_credentials,
4448
git_clone_options,
4549
git_fetch_options,
4650
git_proxy_options,
47-
get_credentials,
4851
)
4952
from .config import Config
5053
from .credentials import *
51-
from .errors import check_error, Passthrough
52-
from .ffi import ffi, C
54+
from .errors import Passthrough, check_error
55+
from .ffi import C, ffi
5356
from .filter import Filter
5457
from .index import Index, IndexEntry
5558
from .legacyenums import *
@@ -60,7 +63,6 @@
6063
from .submodules import Submodule
6164
from .utils import to_bytes, to_str
6265

63-
6466
# Features
6567
features = enums.Feature(C.git_libgit2_features())
6668

@@ -164,7 +166,7 @@ def clone_repository(
164166
callbacks: RemoteCallbacks | None = None,
165167
depth: int = 0,
166168
proxy: None | bool | str = None,
167-
):
169+
) -> Repository:
168170
"""
169171
Clones a new Git repository from *url* in the given *path*.
170172

pygit2/_libgit2/ffi.pyi

Lines changed: 273 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,273 @@
1+
# Copyright 2010-2025 The pygit2 contributors
2+
#
3+
# This file is free software; you can redistribute it and/or modify
4+
# it under the terms of the GNU General Public License, version 2,
5+
# as published by the Free Software Foundation.
6+
#
7+
# In addition to the permissions in the GNU General Public License,
8+
# the authors give you unlimited permission to link the compiled
9+
# version of this file into combinations with other programs,
10+
# and to distribute those combinations without any restriction
11+
# coming from the use of this file. (The General Public License
12+
# restrictions do apply in other respects; for example, they cover
13+
# modification of the file, and distribution when not linked into
14+
# a combined executable.)
15+
#
16+
# This file is distributed in the hope that it will be useful, but
17+
# WITHOUT ANY WARRANTY; without even the implied warranty of
18+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19+
# General Public License for more details.
20+
#
21+
# You should have received a copy of the GNU General Public License
22+
# along with this program; see the file COPYING. If not, write to
23+
# the Free Software Foundation, 51 Franklin Street, Fifth Floor,
24+
# Boston, MA 02110-1301, USA.
25+
26+
from typing import Any, Generic, Literal, NewType, SupportsIndex, TypeVar, overload
27+
28+
from pygit2._pygit2 import Repository
29+
30+
T = TypeVar('T')
31+
32+
NULL_TYPE = NewType('NULL_TYPE', object)
33+
NULL: NULL_TYPE = ...
34+
35+
char = NewType('char', object)
36+
char_pointer = NewType('char_pointer', object)
37+
38+
class _Pointer(Generic[T]):
39+
def __setitem__(self, item: Literal[0], a: T) -> None: ...
40+
@overload
41+
def __getitem__(self, item: Literal[0]) -> T: ...
42+
@overload
43+
def __getitem__(self, item: slice[None, None, None]) -> bytes: ...
44+
45+
class GitTimeC:
46+
# incomplete
47+
time: int
48+
offset: int
49+
50+
class GitSignatureC:
51+
name: char_pointer
52+
email: char_pointer
53+
when: GitTimeC
54+
55+
class GitHunkC:
56+
# incomplete
57+
boundary: char
58+
final_start_line_number: int
59+
final_signature: GitSignatureC
60+
orig_signature: GitSignatureC
61+
orig_start_line_number: int
62+
orig_path: char_pointer
63+
lines_in_hunk: int
64+
65+
class GitRepositoryC:
66+
# incomplete
67+
# TODO: this has to be unified with pygit2._pygit2(pyi).Repository
68+
def _from_c(cls, ptr: 'GitRepositoryC', owned: bool) -> 'Repository': ...
69+
70+
class GitFetchOptionsC:
71+
# TODO: FetchOptions exist in _pygit2.pyi
72+
# incomplete
73+
depth: int
74+
75+
class GitSubmoduleC:
76+
pass
77+
78+
class GitSubmoduleUpdateOptionsC:
79+
fetch_opts: GitFetchOptionsC
80+
81+
class UnsignedIntC:
82+
def __getitem__(self, item: Literal[0]) -> int: ...
83+
84+
class GitOidC:
85+
id: _Pointer[bytes]
86+
87+
class GitBlameOptionsC:
88+
flags: int
89+
min_match_characters: int
90+
newest_commit: object
91+
oldest_commit: object
92+
min_line: int
93+
max_line: int
94+
95+
class GitBlameC:
96+
# incomplete
97+
pass
98+
99+
class GitMergeOptionsC:
100+
file_favor: int
101+
flags: int
102+
file_flags: int
103+
104+
class GitAnnotatedCommitC:
105+
pass
106+
107+
class GitAttrOptionsC:
108+
# incomplete
109+
version: int
110+
flags: int
111+
112+
class GitBufC:
113+
ptr: char_pointer
114+
115+
class GitCheckoutOptionsC:
116+
# incomplete
117+
checkout_strategy: int
118+
119+
class GitCommitC:
120+
pass
121+
122+
class GitConfigC:
123+
pass
124+
125+
class GitDescribeFormatOptionsC:
126+
version: int
127+
abbreviated_size: int
128+
always_use_long_format: int
129+
dirty_suffix: char_pointer
130+
131+
class GitDescribeOptionsC:
132+
version: int
133+
max_candidates_tags: int
134+
describe_strategy: int
135+
pattern: char_pointer
136+
only_follow_first_parent: int
137+
show_commit_oid_as_fallback: int
138+
139+
class GitDescribeResultC:
140+
pass
141+
142+
class GitIndexC:
143+
pass
144+
145+
class GitMergeFileResultC:
146+
pass
147+
148+
class GitObjectC:
149+
pass
150+
151+
class GitStashSaveOptionsC:
152+
version: int
153+
flags: int
154+
stasher: GitSignatureC
155+
message: char_pointer
156+
paths: GitStrrayC
157+
158+
class GitStrrayC:
159+
pass
160+
161+
class GitTreeC:
162+
pass
163+
164+
class GitRepositoryInitOptionsC:
165+
version: int
166+
flags: int
167+
mode: int
168+
workdir_path: char_pointer
169+
description: char_pointer
170+
template_path: char_pointer
171+
initial_head: char_pointer
172+
origin_url: char_pointer
173+
174+
class GitCloneOptionsC:
175+
pass
176+
177+
class GitProxyTC:
178+
pass
179+
180+
class GitProxyOptionsC:
181+
version: int
182+
type: GitProxyTC
183+
url: char_pointer
184+
# credentials
185+
# certificate_check
186+
# payload
187+
188+
class GitRemoteC:
189+
pass
190+
191+
class GitReferenceC:
192+
pass
193+
194+
def string(a: char_pointer) -> bytes: ...
195+
@overload
196+
def new(a: Literal['git_repository **']) -> _Pointer[GitRepositoryC]: ...
197+
@overload
198+
def new(a: Literal['git_remote **']) -> _Pointer[GitRemoteC]: ...
199+
@overload
200+
def new(a: Literal['git_repository_init_options *']) -> GitRepositoryInitOptionsC: ...
201+
@overload
202+
def new(a: Literal['git_submodule_update_options *']) -> GitSubmoduleUpdateOptionsC: ...
203+
@overload
204+
def new(a: Literal['git_submodule **']) -> _Pointer[GitSubmoduleC]: ...
205+
@overload
206+
def new(a: Literal['unsigned int *']) -> UnsignedIntC: ...
207+
@overload
208+
def new(a: Literal['git_proxy_options *']) -> GitProxyOptionsC: ...
209+
@overload
210+
def new(a: Literal['git_oid *']) -> GitOidC: ...
211+
@overload
212+
def new(a: Literal['git_blame **']) -> _Pointer[GitBlameC]: ...
213+
@overload
214+
def new(a: Literal['git_clone_options *']) -> GitCloneOptionsC: ...
215+
@overload
216+
def new(a: Literal['git_merge_options *']) -> GitMergeOptionsC: ...
217+
@overload
218+
def new(a: Literal['git_blame_options *']) -> GitBlameOptionsC: ...
219+
@overload
220+
def new(a: Literal['git_annotated_commit **']) -> _Pointer[GitAnnotatedCommitC]: ...
221+
@overload
222+
def new(a: Literal['git_attr_options *']) -> GitAttrOptionsC: ...
223+
@overload
224+
def new(a: Literal['git_buf *']) -> GitBufC: ...
225+
@overload
226+
def new(a: Literal['git_checkout_options *']) -> GitCheckoutOptionsC: ...
227+
@overload
228+
def new(a: Literal['git_commit **']) -> _Pointer[GitCommitC]: ...
229+
@overload
230+
def new(a: Literal['git_config *']) -> GitConfigC: ...
231+
@overload
232+
def new(a: Literal['git_describe_format_options *']) -> GitDescribeFormatOptionsC: ...
233+
@overload
234+
def new(a: Literal['git_describe_options *']) -> GitDescribeOptionsC: ...
235+
@overload
236+
def new(a: Literal['git_describe_result *']) -> GitDescribeResultC: ...
237+
@overload
238+
def new(a: Literal['git_describe_result **']) -> _Pointer[GitDescribeResultC]: ...
239+
@overload
240+
def new(a: Literal['struct git_reference **']) -> _Pointer[GitReferenceC]: ...
241+
@overload
242+
def new(a: Literal['git_index **']) -> _Pointer[GitIndexC]: ...
243+
@overload
244+
def new(a: Literal['git_merge_file_result *']) -> GitMergeFileResultC: ...
245+
@overload
246+
def new(a: Literal['git_object *']) -> GitObjectC: ...
247+
@overload
248+
def new(a: Literal['git_object **']) -> _Pointer[GitObjectC]: ...
249+
@overload
250+
def new(a: Literal['git_signature *']) -> GitSignatureC: ...
251+
@overload
252+
def new(a: Literal['git_signature **']) -> _Pointer[GitSignatureC]: ...
253+
@overload
254+
def new(a: Literal['git_stash_save_options *']) -> GitStashSaveOptionsC: ...
255+
@overload
256+
def new(a: Literal['git_tree **']) -> _Pointer[GitTreeC]: ...
257+
@overload
258+
def new(a: Literal['git_buf *'], b: tuple[NULL_TYPE, Literal[0]]) -> GitBufC: ...
259+
@overload
260+
def new(a: Literal['char **']) -> _Pointer[char_pointer]: ...
261+
@overload
262+
def new(a: Literal['char[]', 'char []'], b: bytes | NULL_TYPE) -> char_pointer: ...
263+
def addressof(a: object, attribute: str) -> _Pointer[object]: ...
264+
265+
class buffer(bytes):
266+
def __init__(self, a: object) -> None: ...
267+
def __setitem__(self, item: slice[None, None, None], value: bytes) -> None: ...
268+
@overload
269+
def __getitem__(self, item: SupportsIndex) -> int: ...
270+
@overload
271+
def __getitem__(self, item: slice[Any, Any, Any]) -> bytes: ...
272+
273+
def cast(a: Literal['int'], b: object) -> int: ...

0 commit comments

Comments
 (0)