Skip to content

Commit 27e6dbc

Browse files
committed
ENH: Add type hints
1 parent 1c40619 commit 27e6dbc

25 files changed

+845
-325
lines changed

.travis.yml

+6
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,12 @@ install:
115115
script:
116116
- python -c "import pyproj; pyproj.Proj('epsg:4269')"
117117
- make test-coverage
118+
- |
119+
if [ "$TRAVIS_PYTHON_VERSION" = "3.5" ]; then
120+
make check-type;
121+
else
122+
make check;
123+
fi
118124
# Building and uploading docs with doctr
119125
- set -e
120126
- |

MANIFEST.in

+1
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ include pyproj/*.pyd
77
include pyproj/*.pyx
88
include pyproj/*.pxd
99
include pyproj/*.pxi
10+
include pyproj/*.pyi
1011
include test/sample.out
1112
include test/conftest.py
1213
recursive-include docs *

Makefile

+4-1
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,10 @@ clean-cython: ## clean the cython files
6363
lint: ## check style with flake8
6464
flake8 --max-line-length 88 setup.py pyproj/ test/ docs/
6565

66-
check: lint ## flake8 black isort check
66+
check-type:
67+
mypy pyproj
68+
69+
check: lint check-type ## flake8 black isort check
6770
black --check setup.py pyproj/ test/ docs/
6871
isort --check --recursive -m 3 -w 88 -tc -p test setup.py pyproj/ test/ docs/
6972

docs/history.rst

+1
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ Change Log
44
2.6.0
55
~~~~~
66
* ENH: Added Proj.get_factors() (issue #503)
7+
* ENH: Added type hints (issue #369)
78

89
2.5.0
910
~~~~~

pyproj/_crs.pxd

+1-1
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ cdef class Base:
3333
cdef readonly object name
3434
cdef readonly object _remarks
3535
cdef readonly object _scope
36-
36+
cdef _set_base_info(self)
3737

3838
cdef class _CRSParts(Base):
3939
pass

pyproj/_crs.pyi

+236
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,236 @@
1+
from typing import Any, Iterable, List, Optional, Tuple, Union
2+
3+
from pyproj.crs.enums import CoordinateOperationType
4+
from pyproj.enums import ProjVersion, WktVersion
5+
6+
class Axis:
7+
name: str
8+
abbrev: str
9+
direction: str
10+
unit_conversion_factor: float
11+
unit_name: str
12+
unit_auth_code: str
13+
unit_code: str
14+
def __str__(self) -> str: ...
15+
def __repr__(self) -> str: ...
16+
17+
class AreaOfUse:
18+
west: float
19+
south: float
20+
east: float
21+
north: float
22+
name: str
23+
def __str__(self) -> str: ...
24+
def __repr__(self) -> str: ...
25+
@property
26+
def bounds(self) -> tuple[float]: ...
27+
28+
class Base:
29+
name: str
30+
@property
31+
def remarks(self) -> str: ...
32+
@property
33+
def scope(self) -> str: ...
34+
def to_wkt(
35+
self,
36+
version: Union[WktVersion, str] = WktVersion.WKT2_2019,
37+
pretty: bool = False,
38+
) -> str: ...
39+
def to_json(self, pretty: bool = False, indentation: int = 2) -> str: ...
40+
def to_json_dict(self) -> dict: ...
41+
def __str__(self) -> str: ...
42+
def __repr__(self) -> str: ...
43+
def __eq__(self, other: Any) -> bool: ...
44+
def is_exact_same(self, other: Any) -> bool: ...
45+
46+
class _CRSParts(Base):
47+
@classmethod
48+
def from_user_input(cls, user_input: Any) -> "_CRSParts": ...
49+
50+
class Ellipsoid(_CRSParts):
51+
semi_major_metre: float
52+
semi_minor_metre: float
53+
is_semi_minor_computed: float
54+
inverse_flattening: float
55+
@staticmethod
56+
def from_authority(auth_name: str, code: Union[int, str]) -> "Ellipsoid": ...
57+
@staticmethod
58+
def from_epsg(code: Union[int, str]) -> "Ellipsoid": ...
59+
@staticmethod
60+
def from_string(ellipsoid_string: str) -> "Ellipsoid": ...
61+
@staticmethod
62+
def from_json_dict(ellipsoid_dict: dict) -> "Ellipsoid": ...
63+
@staticmethod
64+
def from_json(ellipsoid_json_str: str) -> "Ellipsoid": ...
65+
@staticmethod
66+
def from_name(
67+
ellipsoid_name: str, auth_name: Optional[str] = None
68+
) -> "Ellipsoid": ...
69+
70+
class PrimeMeridian(_CRSParts):
71+
longitude: float
72+
unit_conversion_factor: str
73+
unit_name: str
74+
@staticmethod
75+
def from_authority(auth_name: str, code: Union[int, str]) -> "PrimeMeridian": ...
76+
@staticmethod
77+
def from_epsg(code: Union[int, str]) -> "PrimeMeridian": ...
78+
@staticmethod
79+
def from_string(prime_meridian_string: str) -> "PrimeMeridian": ...
80+
@staticmethod
81+
def from_json_dict(prime_meridian_dict: dict) -> "PrimeMeridian": ...
82+
@staticmethod
83+
def from_json(prime_meridian_json_str: str) -> "PrimeMeridian": ...
84+
@staticmethod
85+
def from_name(
86+
prime_meridian_name: str, auth_name: Optional[str] = None
87+
) -> "PrimeMeridian": ...
88+
89+
class Datum(_CRSParts):
90+
type_name: str
91+
@property
92+
def ellipsoid(self) -> Optional[Ellipsoid]: ...
93+
@property
94+
def prime_meridian(self) -> Optional[PrimeMeridian]: ...
95+
@staticmethod
96+
def from_authority(auth_name: str, code: Union[int, str]) -> "Datum": ...
97+
@staticmethod
98+
def from_epsg(code: Union[int, str]) -> "Datum": ...
99+
@staticmethod
100+
def from_string(datum_string: str) -> "Datum": ...
101+
@staticmethod
102+
def from_json_dict(datum_dict: dict) -> "Datum": ...
103+
@staticmethod
104+
def from_json(datum_json_str: str) -> "Datum": ...
105+
@staticmethod
106+
def from_name(datum_name: str, auth_name: Optional[str] = None) -> "Datum": ...
107+
108+
class CoordinateSystem(_CRSParts):
109+
def __init__(self) -> None: ...
110+
@property
111+
def axis_list(self) -> Iterable[Axis]: ...
112+
@staticmethod
113+
def from_string(coordinate_system_string: str) -> "CoordinateSystem": ...
114+
@staticmethod
115+
def from_json_dict(coordinate_system_dict: dict) -> "CoordinateSystem": ...
116+
@staticmethod
117+
def from_json(coordinate_system_json_str: str) -> "CoordinateSystem": ...
118+
119+
class Param:
120+
name: str
121+
auth_name: str
122+
code: str
123+
value: str
124+
unit_conversion_factor: float
125+
unit_name: str
126+
unit_auth_name: str
127+
unit_code: str
128+
unit_category: str
129+
def __str__(self) -> str: ...
130+
def __repr__(self) -> str: ...
131+
132+
class Grid:
133+
short_name: str
134+
full_name: str
135+
package_name: str
136+
url: str
137+
direct_download: str
138+
open_license: str
139+
available: str
140+
def __str__(self) -> str: ...
141+
def __repr__(self) -> str: ...
142+
143+
class CoordinateOperation(_CRSParts):
144+
method_name: str
145+
method_auth_name: str
146+
method_code: str
147+
accuracy: float
148+
is_instantiable: bool
149+
has_ballpark_transformation: bool
150+
type_name: str
151+
@property
152+
def params(self) -> Iterable[Param]: ...
153+
@property
154+
def grids(self) -> Iterable[Grid]: ...
155+
@property
156+
def area_of_use(self) -> Optional[AreaOfUse]: ...
157+
@property
158+
def towgs84(self) -> Iterable[float]: ...
159+
@property
160+
def operations(self) -> Tuple["CoordinateOperation"]: ...
161+
def __init__(self) -> None: ...
162+
def __repr__(self) -> str: ...
163+
@staticmethod
164+
def from_authority(
165+
auth_name: str, code: Union[int, str]
166+
) -> "CoordinateOperation": ...
167+
@staticmethod
168+
def from_epsg(code: Union[int, str]) -> "CoordinateOperation": ...
169+
@staticmethod
170+
def from_string(ellipsoid_string: str) -> "CoordinateOperation": ...
171+
@staticmethod
172+
def from_json_dict(ellipsoid_dict: dict) -> "CoordinateOperation": ...
173+
@staticmethod
174+
def from_json(ellipsoid_json_str: str) -> "CoordinateOperation": ...
175+
def to_proj4(
176+
self, version: Union[ProjVersion, int] = ProjVersion.PROJ_5
177+
) -> str: ...
178+
@staticmethod
179+
def from_name(
180+
coordinate_operation_name: str,
181+
auth_name: Optional[str] = None,
182+
coordinate_operation_type: Union[
183+
CoordinateOperationType, str
184+
] = CoordinateOperationType.CONVERSION,
185+
) -> "CoordinateOperation": ...
186+
187+
class _CRS(Base):
188+
srs: str
189+
type_name: str
190+
def __init__(self, proj_string: str) -> None: ...
191+
@property
192+
def ellipsoid(self) -> Optional[Ellipsoid]: ...
193+
@property
194+
def area_of_use(self) -> Optional[AreaOfUse]: ...
195+
@property
196+
def axis_info(self) -> List[Axis]: ...
197+
@property
198+
def prime_meridian(self) -> Optional[PrimeMeridian]: ...
199+
@property
200+
def datum(self) -> Optional[Datum]: ...
201+
@property
202+
def sub_crs_list(self) -> Iterable["_CRS"]: ...
203+
@property
204+
def source_crs(self) -> Optional["_CRS"]: ...
205+
@property
206+
def target_crs(self) -> Optional["_CRS"]: ...
207+
@property
208+
def geodetic_crs(self) -> Optional["_CRS"]: ...
209+
@property
210+
def coordinate_system(self) -> Optional[CoordinateSystem]: ...
211+
@property
212+
def coordinate_operation(self) -> Optional[CoordinateOperation]: ...
213+
def to_proj4(
214+
self, version: Union[ProjVersion, int] = ProjVersion.PROJ_5
215+
) -> str: ...
216+
def to_epsg(self, min_confidence: int = 70) -> Optional[int]: ...
217+
def to_authority(
218+
self, auth_name: Optional[str] = None, min_confidence: int = 70
219+
): ...
220+
@property
221+
def is_geographic(self) -> bool: ...
222+
@property
223+
def is_projected(self) -> bool: ...
224+
@property
225+
def is_vertical(self) -> bool: ...
226+
@property
227+
def is_bound(self) -> bool: ...
228+
@property
229+
def is_engineering(self) -> bool: ...
230+
@property
231+
def is_geocentric(self) -> bool: ...
232+
def equals(self, other: Any, ignore_axis_order: bool) -> bool: ...
233+
234+
def is_proj(proj_string: str) -> bool: ...
235+
def is_wkt(proj_string: str) -> bool: ...
236+
def _load_proj_json(in_proj_json: str) -> dict: ...

pyproj/_crs.pyx

+2-2
Original file line numberDiff line numberDiff line change
@@ -389,7 +389,7 @@ cdef class Base:
389389
if self.context != NULL:
390390
proj_context_destroy(self.context)
391391

392-
def _set_base_info(self):
392+
cdef _set_base_info(self):
393393
"""
394394
Set the name of the PJ
395395
"""
@@ -2327,7 +2327,7 @@ cdef class _CRS(Base):
23272327
"""
23282328
Returns
23292329
-------
2330-
list[Axis]: The list of axis information.
2330+
List[Axis]: The list of axis information.
23312331
"""
23322332
return self.coordinate_system.axis_list if self.coordinate_system else []
23332333

pyproj/_datadir.pyi

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
def pyproj_global_context_initialize() -> None: ...

pyproj/_geod.pxd

+5-5
Original file line numberDiff line numberDiff line change
@@ -28,8 +28,8 @@ cdef extern from "geodesic.h":
2828
cdef class Geod:
2929
cdef geod_geodesic _geod_geodesic
3030
cdef readonly object initstring
31-
cdef readonly object a
32-
cdef readonly object b
33-
cdef readonly object f
34-
cdef readonly object es
35-
cdef readonly object sphere
31+
cdef readonly double a
32+
cdef readonly double b
33+
cdef readonly double f
34+
cdef readonly double es
35+
cdef readonly bint sphere

pyproj/_geod.pyi

+35
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
from typing import Any, Tuple, Type
2+
3+
geodesic_version_str: str
4+
5+
class Geod:
6+
initstring: str
7+
a: float
8+
b: float
9+
f: float
10+
es: float
11+
sphere: bool
12+
def __init__(
13+
self, a: float, f: float, sphere: bool, b: float, es: float
14+
) -> None: ...
15+
def __reduce__(self) -> Tuple[Type["Geod"], str]: ...
16+
def __repr__(self) -> str: ...
17+
def _fwd(
18+
self, lons: Any, lats: Any, az: Any, dist: Any, radians: bool = False
19+
) -> None: ...
20+
def _inv(
21+
self, lons1: Any, lats1: Any, lons2: Any, lats2: Any, radians: bool = False
22+
) -> None: ...
23+
def _npts(
24+
self,
25+
lon1: float,
26+
lat1: float,
27+
lon2: float,
28+
lat2: float,
29+
npts: int,
30+
radians: bool = False,
31+
) -> Tuple[Tuple[float], Tuple[float]]: ...
32+
def _line_length(self, lons: Any, lats: Any, radians: bool = False) -> float: ...
33+
def _polygon_area_perimeter(
34+
self, lons: Any, lats: Any, radians: bool = False
35+
) -> Tuple[float, float]: ...

pyproj/_geod.pyx

+5-7
Original file line numberDiff line numberDiff line change
@@ -12,16 +12,14 @@ geodesic_version_str = "{0}.{1}.{2}".format(
1212
)
1313

1414
cdef class Geod:
15-
def __init__(self, a, f, sphere, b, es):
15+
def __init__(self, double a, double f, bint sphere, double b, double es):
1616
geod_init(&self._geod_geodesic, <double> a, <double> f)
1717
self.a = a
1818
self.f = f
19-
if isinstance(a, float) and a.is_integer():
20-
# convert 'a' only for initstring
21-
a = int(a)
22-
if f == 0.0:
23-
f = 0
24-
self.initstring = pystrdecode(cstrencode("+a=%s +f=%s" % (a, f)))
19+
# convert 'a' only for initstring
20+
a_str = int(a) if a.is_integer() else a
21+
f_str = int(f) if f.is_integer() else f
22+
self.initstring = pystrdecode(cstrencode("+a=%s +f=%s" % (a_str, f_str)))
2523
self.sphere = sphere
2624
self.b = b
2725
self.es = es

pyproj/_list.pyi

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
from typing import Dict, List, NamedTuple, Union
2+
3+
from pyproj.enums import PJType
4+
5+
def get_proj_operations_map() -> Dict[str, str]: ...
6+
def get_ellps_map() -> Dict[str, Dict[str, float]]: ...
7+
def get_prime_meridians_map() -> Dict[str, str]: ...
8+
9+
class Unit(NamedTuple):
10+
id: str
11+
to_meter: str
12+
name: str
13+
factor: float
14+
15+
def get_units_map() -> Dict[str, Unit]: ...
16+
def get_angular_units_map() -> Dict[str, Unit]: ...
17+
def get_authorities() -> List[str]: ...
18+
def get_codes(
19+
auth_name: str, pj_type: Union[PJType, str], allow_deprecated: bool = False
20+
) -> List[str]: ...

0 commit comments

Comments
 (0)