Skip to content

Commit ccb74d0

Browse files
committed
More fixes
1 parent 839caa1 commit ccb74d0

File tree

2 files changed

+36
-48
lines changed

2 files changed

+36
-48
lines changed

pygmt/clib/session.py

+5-4
Original file line numberDiff line numberDiff line change
@@ -1765,7 +1765,7 @@ def virtualfile_from_stringio(
17651765
seg.header = None
17661766
seg.text = None
17671767

1768-
def virtualfile_in(
1768+
def virtualfile_in( # noqa: PLR0912
17691769
self,
17701770
check_kind=None,
17711771
data=None,
@@ -1829,7 +1829,7 @@ def virtualfile_in(
18291829
... print(fout.read().strip())
18301830
<vector memory>: N = 3 <7/9> <4/6> <1/3>
18311831
"""
1832-
# Check if the combination of data, and x/y/z is valid.
1832+
# Specify either data or x/y/z.
18331833
if data is not None and any(v is not None for v in (x, y, z)):
18341834
msg = "Too much data. Use either data or x/y/z."
18351835
raise GMTInvalidInput(msg)
@@ -1846,7 +1846,7 @@ def virtualfile_in(
18461846
case "vector":
18471847
valid_kinds += ("empty", "matrix", "vectors", "geojson")
18481848
case _:
1849-
msg = f"Unrecognized check_kind: {check_kind}."
1849+
msg = f"Invalid value for check_kind: '{check_kind}'."
18501850
raise GMTInvalidInput(msg)
18511851
if kind not in valid_kinds:
18521852
msg = f"Unrecognized data type for {check_kind}: {type(data)}."
@@ -1900,7 +1900,8 @@ def virtualfile_in(
19001900
_virtualfile_from = self.virtualfile_from_vectors
19011901
_data = data.T
19021902

1903-
_validate_data_input(data=_data, required_z=required_z, kind=kind)
1903+
# Check if _data to be passed to the virtualfile_from_ function is valid.
1904+
_validate_data_input(data=_data, kind=kind, required_z=required_z)
19041905

19051906
# Finally create the virtualfile from the data, to be passed into GMT
19061907
file_context = _virtualfile_from(_data)

pygmt/helpers/utils.py

+31-44
Original file line numberDiff line numberDiff line change
@@ -47,70 +47,61 @@
4747

4848
def _validate_data_input(data: Any, kind: Kind, required_z: bool = False) -> None:
4949
"""
50-
Check if the combination of data/x/y/z is valid.
50+
Check if the data to be passed to the virtualfile_from_ functions is valid.
5151
5252
Examples
5353
--------
54-
>>> _validate_data_input(data="infile")
55-
>>> _validate_data_input(x=[1, 2, 3], y=[4, 5, 6])
56-
>>> _validate_data_input(x=[1, 2, 3], y=[4, 5, 6], z=[7, 8, 9])
57-
>>> _validate_data_input(data=None, required_data=False)
58-
>>> _validate_data_input()
54+
The "empty" kind means the data is given via a series of vectors like x/y/z.
55+
56+
>>> _validate_data_input(data=[[1, 2, 3], [4, 5, 6]], kind="empty")
57+
>>> _validate_data_input(data=[[1, 2, 3], [4, 5, 6], [7, 8, 9]], kind="empty")
58+
>>> _validate_data_input(data=[None, [4, 5, 6]], kind="empty")
5959
Traceback (most recent call last):
6060
...
61-
pygmt.exceptions.GMTInvalidInput: No input data provided.
62-
>>> _validate_data_input(x=[1, 2, 3])
61+
pygmt.exceptions.GMTInvalidInput: Must provide both x and y.
62+
>>> _validate_data_input(data=[[1, 2, 3], None], kind="empty")
6363
Traceback (most recent call last):
6464
...
6565
pygmt.exceptions.GMTInvalidInput: Must provide both x and y.
66-
>>> _validate_data_input(y=[4, 5, 6])
66+
>>> _validate_data_input(data=[None, None], kind="empty")
6767
Traceback (most recent call last):
6868
...
6969
pygmt.exceptions.GMTInvalidInput: Must provide both x and y.
70-
>>> _validate_data_input(x=[1, 2, 3], y=[4, 5, 6], required_z=True)
70+
>>> _validate_data_input(data=[[1, 2, 3], [4, 5, 6]], kind="empty", required_z=True)
7171
Traceback (most recent call last):
7272
...
7373
pygmt.exceptions.GMTInvalidInput: Must provide x, y, and z.
74+
75+
The "matrix" kind means the data is given via a 2-D numpy.ndarray.
76+
7477
>>> import numpy as np
7578
>>> import pandas as pd
7679
>>> import xarray as xr
7780
>>> data = np.arange(8).reshape((4, 2))
78-
>>> _validate_data_input(data=data, required_z=True, kind="matrix")
81+
>>> _validate_data_input(data=data, kind="matrix", required_z=True)
7982
Traceback (most recent call last):
8083
...
8184
pygmt.exceptions.GMTInvalidInput: Need at least 3 columns but 2 column(s) are given.
85+
86+
The "vectors" kind means the original data is either dictionary, list, tuple,
87+
pandas.DataFrame, pandas.Series, xarray.Dataset, or xarray.DataArray.
88+
8289
>>> _validate_data_input(
8390
... data=pd.DataFrame(data, columns=["x", "y"]),
84-
... required_z=True,
8591
... kind="vectors",
92+
... required_z=True,
8693
... )
8794
Traceback (most recent call last):
8895
...
8996
pygmt.exceptions.GMTInvalidInput: Need at least 3 columns but 2 column(s) are given.
9097
>>> _validate_data_input(
9198
... data=xr.Dataset(pd.DataFrame(data, columns=["x", "y"])),
92-
... required_z=True,
9399
... kind="vectors",
100+
... required_z=True,
94101
... )
95102
Traceback (most recent call last):
96103
...
97104
pygmt.exceptions.GMTInvalidInput: Need at least 3 columns but 2 column(s) are given.
98-
>>> _validate_data_input(data="infile", x=[1, 2, 3])
99-
Traceback (most recent call last):
100-
...
101-
pygmt.exceptions.GMTInvalidInput: Too much data. Use either data or x/y/z.
102-
>>> _validate_data_input(data="infile", y=[4, 5, 6])
103-
Traceback (most recent call last):
104-
...
105-
pygmt.exceptions.GMTInvalidInput: Too much data. Use either data or x/y/z.
106-
>>> _validate_data_input(data="infile", x=[1, 2, 3], y=[4, 5, 6])
107-
Traceback (most recent call last):
108-
...
109-
pygmt.exceptions.GMTInvalidInput: Too much data. Use either data or x/y/z.
110-
>>> _validate_data_input(data="infile", z=[7, 8, 9])
111-
Traceback (most recent call last):
112-
...
113-
pygmt.exceptions.GMTInvalidInput: Too much data. Use either data or x/y/z.
114105
115106
Raises
116107
------
@@ -120,29 +111,25 @@ def _validate_data_input(data: Any, kind: Kind, required_z: bool = False) -> Non
120111
# Determine the required number of columns based on the required_z flag.
121112
required_cols = 3 if required_z else 1
122113

123-
# Check based on the data kind.
124114
match kind:
125-
case "empty": # data = [x, y, z]
126-
if required_z and len(data) < 3:
127-
msg = "Must provide x, y, and z."
128-
raise GMTInvalidInput(msg)
129-
if any(v is None for v in data):
115+
case "empty": # data = [x, y], [x, y, z], [x, y, z, ...]
116+
if len(data) < 2 or any(v is None for v in data[:2]):
130117
msg = "Must provide both x and y."
131118
raise GMTInvalidInput(msg)
119+
if required_z and (len(data) < 3 or data[:3] is None):
120+
msg = "Must provide x, y, and z."
121+
raise GMTInvalidInput(msg)
132122
case "matrix": # 2-D numpy.ndarray
133123
if (actual_cols := data.shape[1]) < required_cols:
134-
msg = (
135-
f"Need at least {required_cols} columns but {actual_cols} column(s) "
136-
"are given."
137-
)
124+
msg = f"Need at least {required_cols} columns but {actual_cols} column(s) are given."
138125
raise GMTInvalidInput(msg)
139126
case "vectors":
140-
# Check if the number of columns is sufficient.
127+
# "vectors" means the original data is either dictionary, list, tuple,
128+
# pandas.DataFrame, pandas.Series, xarray.Dataset, or xarray.DataArray.
129+
# The original data is converted to a list of vectors or a 2-D numpy.ndarray
130+
# in the virtualfile_in function.
141131
if (actual_cols := len(data)) < required_cols:
142-
msg = (
143-
f"Need at least {required_cols} columns but {actual_cols} "
144-
"column(s) are given."
145-
)
132+
msg = f"Need at least {required_cols} columns but {actual_cols} column(s) are given."
146133
raise GMTInvalidInput(msg)
147134

148135

0 commit comments

Comments
 (0)