Skip to content

Commit 3302d87

Browse files
committed
Issue #720/#402/#725 eliminate _ensure_save_result
1 parent 923f4d9 commit 3302d87

File tree

3 files changed

+37
-97
lines changed

3 files changed

+37
-97
lines changed

openeo/rest/_datacube.py

Lines changed: 0 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -324,42 +324,3 @@ def build_child_callback(
324324
raise ValueError(process)
325325

326326
return PGNode.to_process_graph_argument(pg)
327-
328-
329-
def _ensure_save_result(
330-
cube: _ProcessGraphAbstraction,
331-
*,
332-
format: Optional[str] = None,
333-
options: Optional[dict] = None,
334-
weak_format: Optional[str] = None,
335-
default_format: str,
336-
method: str,
337-
) -> Union[SaveResult, StacResource]:
338-
"""
339-
Make sure there is a`save_result` node in the process graph.
340-
341-
:param format: (optional) desired `save_result` file format
342-
:param options: (optional) desired `save_result` file format parameters
343-
:param weak_format: (optional) weak format indicator guessed from file name
344-
:param default_format: default format for data type to use when no format is specified by user
345-
:return:
346-
"""
347-
# TODO #278 instead of standalone helper function, move this to common base class for raster cubes, vector cubes, ...
348-
save_result_nodes = [n for n in cube.result_node().walk_nodes() if n.process_id == "save_result"]
349-
350-
if not save_result_nodes:
351-
# No `save_result` node yet: automatically add it.
352-
if isinstance(cube, (openeo.DataCube, openeo.VectorCube)):
353-
pg_with_save_result = cube.save_result(format=format or weak_format or default_format, options=options)
354-
else:
355-
raise OpenEoClientException(f"No support to add `save_result` on {cube!r}.")
356-
else:
357-
if format or options:
358-
raise OpenEoClientException(
359-
f"{method} with explicit output {'format' if format else 'options'} {format or options!r},"
360-
f" but the process graph already has `save_result` node(s)"
361-
f" which is ambiguous and should not be combined."
362-
)
363-
pg_with_save_result = cube
364-
365-
return pg_with_save_result

openeo/rest/datacube.py

Lines changed: 17 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,6 @@
5656
from openeo.rest._datacube import (
5757
THIS,
5858
UDF,
59-
_ensure_save_result,
6059
_ProcessGraphAbstraction,
6160
build_child_callback,
6261
)
@@ -65,7 +64,6 @@
6564
from openeo.rest.mlmodel import MlModel
6665
from openeo.rest.result import SaveResult
6766
from openeo.rest.service import Service
68-
from openeo.rest.stac_resource import StacResource
6967
from openeo.rest.udp import RESTUserDefinedProcess
7068
from openeo.rest.vectorcube import VectorCube
7169
from openeo.util import dict_no_none, guess_format, load_json, normalize_crs, rfc3339
@@ -2352,6 +2350,17 @@ def save_result(
23522350
)
23532351
return SaveResult(pg, connection=self._connection)
23542352

2353+
def _auto_save_result(
2354+
self,
2355+
format: Optional[str] = None,
2356+
outputfile: Optional[Union[str, pathlib.Path]] = None,
2357+
options: Optional[dict] = None,
2358+
) -> SaveResult:
2359+
return self.save_result(
2360+
format=format or (guess_format(outputfile) if outputfile else None) or self._DEFAULT_RASTER_FORMAT,
2361+
options=options,
2362+
)
2363+
23552364
def download(
23562365
self,
23572366
outputfile: Optional[Union[str, pathlib.Path]] = None,
@@ -2374,7 +2383,7 @@ def download(
23742383
:param options: Optional, file format options
23752384
:param validate: Optional toggle to enable/prevent validation of the process graphs before execution
23762385
(overruling the connection's ``auto_validate`` setting).
2377-
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph if there is none yet.
2386+
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph.
23782387
:param additional: additional (top-level) properties to set in the request body
23792388
:param job_options: dictionary of job options to pass to the backend
23802389
(under top-level property "job_options")
@@ -2389,14 +2398,7 @@ def download(
23892398
"""
23902399
# TODO #278 centralize download/create_job/execute_job logic in DataCube, VectorCube, MlModel, ...
23912400
if auto_add_save_result:
2392-
res = _ensure_save_result(
2393-
cube=self,
2394-
format=format,
2395-
options=options,
2396-
weak_format=guess_format(outputfile) if outputfile else None,
2397-
default_format=self._DEFAULT_RASTER_FORMAT,
2398-
method="DataCube.download()",
2399-
)
2401+
res = self._auto_save_result(format=format, outputfile=outputfile, options=options)
24002402
else:
24012403
res = self
24022404
return self._connection.download(
@@ -2543,7 +2545,7 @@ def execute_batch(
25432545
(under top-level property "job_options")
25442546
:param validate: Optional toggle to enable/prevent validation of the process graphs before execution
25452547
(overruling the connection's ``auto_validate`` setting).
2546-
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph if there is none yet.
2548+
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph.
25472549
:param show_error_logs: whether to automatically print error logs when the batch job failed.
25482550
:param log_level: Optional minimum severity level for log entries that the back-end should keep track of.
25492551
One of "error" (highest severity), "warning", "info", and "debug" (lowest severity).
@@ -2568,14 +2570,7 @@ def execute_batch(
25682570

25692571
# TODO #278 centralize download/create_job/execute_job logic in DataCube, VectorCube, MlModel, ...
25702572
if auto_add_save_result:
2571-
res = _ensure_save_result(
2572-
cube=self,
2573-
format=out_format,
2574-
options=format_options,
2575-
weak_format=guess_format(outputfile) if outputfile else None,
2576-
default_format=self._DEFAULT_RASTER_FORMAT,
2577-
method="DataCube.execute_batch()",
2578-
)
2573+
res = self._auto_save_result(format=out_format, outputfile=outputfile, options=format_options)
25792574
create_kwargs = {}
25802575
else:
25812576
res = self
@@ -2637,7 +2632,7 @@ def create_job(
26372632
(under top-level property "job_options")
26382633
:param validate: Optional toggle to enable/prevent validation of the process graphs before execution
26392634
(overruling the connection's ``auto_validate`` setting).
2640-
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph if there is none yet.
2635+
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph.
26412636
:param log_level: Optional minimum severity level for log entries that the back-end should keep track of.
26422637
One of "error" (highest severity), "warning", "info", and "debug" (lowest severity).
26432638
@@ -2656,13 +2651,7 @@ def create_job(
26562651
# TODO: avoid using all kwargs as format_options
26572652
# TODO #278 centralize download/create_job/execute_job logic in DataCube, VectorCube, MlModel, ...
26582653
if auto_add_save_result:
2659-
res = _ensure_save_result(
2660-
cube=self,
2661-
format=out_format,
2662-
options=format_options or None,
2663-
default_format=self._DEFAULT_RASTER_FORMAT,
2664-
method="DataCube.create_job()",
2665-
)
2654+
res = self._auto_save_result(format=out_format, options=format_options)
26662655
else:
26672656
res = self
26682657

openeo/rest/vectorcube.py

Lines changed: 20 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,6 @@
2020
from openeo.rest._datacube import (
2121
THIS,
2222
UDF,
23-
_ensure_save_result,
2423
_ProcessGraphAbstraction,
2524
build_child_callback,
2625
)
@@ -194,7 +193,6 @@ def run_udf(
194193

195194
@openeo_process
196195
def save_result(self, format: Union[str, None] = "GeoJSON", options: dict = None) -> SaveResult:
197-
# TODO #401: guard against duplicate save_result nodes?
198196
pg = self._build_pgnode(
199197
process_id="save_result",
200198
arguments={
@@ -206,6 +204,17 @@ def save_result(self, format: Union[str, None] = "GeoJSON", options: dict = None
206204
)
207205
return SaveResult(pg, connection=self._connection)
208206

207+
def _auto_save_result(
208+
self,
209+
format: Optional[str] = None,
210+
outputfile: Optional[Union[str, pathlib.Path]] = None,
211+
options: Optional[dict] = None,
212+
) -> SaveResult:
213+
return self.save_result(
214+
format=format or (guess_format(outputfile) if outputfile else None) or self._DEFAULT_VECTOR_FORMAT,
215+
options=options,
216+
)
217+
209218
def execute(self, *, validate: Optional[bool] = None) -> dict:
210219
"""Executes the process graph."""
211220
return self._connection.execute(self.flat_graph(), validate=validate)
@@ -230,7 +239,7 @@ def download(
230239
:param options: (optional) additional output format options.
231240
:param validate: Optional toggle to enable/prevent validation of the process graphs before execution
232241
(overruling the connection's ``auto_validate`` setting).
233-
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph if there is none yet.
242+
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph.
234243
235244
.. versionchanged:: 0.21.0
236245
When not specified explicitly, output format is guessed from output file extension.
@@ -240,14 +249,7 @@ def download(
240249
"""
241250
# TODO #278 centralize download/create_job/execute_job logic in DataCube, VectorCube, MlModel, ...
242251
if auto_add_save_result:
243-
res = _ensure_save_result(
244-
cube=self,
245-
format=format,
246-
options=options,
247-
weak_format=guess_format(outputfile) if outputfile else None,
248-
default_format=self._DEFAULT_VECTOR_FORMAT,
249-
method="VectorCube.download()",
250-
)
252+
res = self._auto_save_result(format=format, outputfile=outputfile, options=options)
251253
else:
252254
res = self
253255
return self._connection.download(res.flat_graph(), outputfile=outputfile, validate=validate)
@@ -287,7 +289,7 @@ def execute_batch(
287289
:param format_options: (optional) additional output format options
288290
:param validate: Optional toggle to enable/prevent validation of the process graphs before execution
289291
(overruling the connection's ``auto_validate`` setting).
290-
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph if there is none yet.
292+
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph.
291293
:param show_error_logs: whether to automatically print error logs when the batch job failed.
292294
:param log_level: Optional minimum severity level for log entries that the back-end should keep track of.
293295
One of "error" (highest severity), "warning", "info", and "debug" (lowest severity).
@@ -310,14 +312,7 @@ def execute_batch(
310312
Added argument ``log_level``.
311313
"""
312314
if auto_add_save_result:
313-
res = _ensure_save_result(
314-
cube=self,
315-
format=out_format,
316-
options=format_options,
317-
weak_format=guess_format(outputfile) if outputfile else None,
318-
default_format=self._DEFAULT_VECTOR_FORMAT,
319-
method="VectorCube.execute_batch()",
320-
)
315+
res = self._auto_save_result(format=out_format, outputfile=outputfile, options=format_options)
321316
create_kwargs = {}
322317
else:
323318
res = self
@@ -373,7 +368,7 @@ def create_job(
373368
:param format_options: String Parameters for the job result format
374369
:param validate: Optional toggle to enable/prevent validation of the process graphs before execution
375370
(overruling the connection's ``auto_validate`` setting).
376-
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph if there is none yet.
371+
:param auto_add_save_result: Automatically add a ``save_result`` node to the process graph.
377372
:param log_level: Optional minimum severity level for log entries that the back-end should keep track of.
378373
One of "error" (highest severity), "warning", "info", and "debug" (lowest severity).
379374
@@ -387,17 +382,12 @@ def create_job(
387382
"""
388383
# TODO: avoid using all kwargs as format_options
389384
# TODO #278 centralize download/create_job/execute_job logic in DataCube, VectorCube, MlModel, ...
390-
cube = self
391385
if auto_add_save_result:
392-
cube = _ensure_save_result(
393-
cube=cube,
394-
format=out_format,
395-
options=format_options or None,
396-
default_format=self._DEFAULT_VECTOR_FORMAT,
397-
method="VectorCube.create_job()",
398-
)
386+
res = self._auto_save_result(format=out_format, options=format_options or None)
387+
else:
388+
res = self
399389
return self._connection.create_job(
400-
process_graph=cube.flat_graph(),
390+
process_graph=res.flat_graph(),
401391
title=title,
402392
description=description,
403393
plan=plan,

0 commit comments

Comments
 (0)