Skip to content

Commit 950ae9b

Browse files
authored
Two fixes for the execution related to pytask-latex. (#7)
1 parent d1abd63 commit 950ae9b

File tree

7 files changed

+39
-13
lines changed

7 files changed

+39
-13
lines changed

docs/changes.rst

+8
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,14 @@ chronological order. Releases follow `semantic versioning <https://semver.org/>`
66
all releases are available on `Anaconda.org <https://anaconda.org/pytask/pytask>`_.
77

88

9+
0.0.3 - 2020-07-19
10+
------------------
11+
12+
- :gh:`7` makes pytask exit with code 1 if a task failed and the
13+
``skip_ancestor_failed`` decorator is only applied to descendant tasks not the task
14+
itself.
15+
16+
917
0.0.2 - 2020-07-17
1018
------------------
1119

src/pytask/dag.py

+6-2
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,16 @@ def sort_tasks_topologically(dag):
99
yield node
1010

1111

12-
def task_and_descending_tasks(task_name, dag):
13-
yield task_name
12+
def descending_tasks(task_name, dag):
1413
for descendant in nx.descendants(dag, task_name):
1514
if "task" in dag.nodes[descendant]:
1615
yield descendant
1716

1817

18+
def task_and_descending_tasks(task_name, dag):
19+
yield task_name
20+
yield from descending_tasks(task_name, dag)
21+
22+
1923
def node_and_neigbors(dag, node):
2024
return itertools.chain([node], dag.neighbors(node))

src/pytask/exceptions.py

+4
Original file line numberDiff line numberDiff line change
@@ -18,5 +18,9 @@ class ResolvingDependenciesError(PytaskError):
1818
"""Exception during resolving dependencies."""
1919

2020

21+
class ExecutionError(PytaskError):
22+
"""Exception during execution."""
23+
24+
2125
class TaskDuplicatedError(PytaskError):
2226
"""Exception for duplicated task during collection."""

src/pytask/execute.py

+6-3
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,11 @@
66
import click
77
import pytask
88
from pytask import hookimpl
9+
from pytask.dag import descending_tasks
910
from pytask.dag import node_and_neigbors
1011
from pytask.dag import sort_tasks_topologically
11-
from pytask.dag import task_and_descending_tasks
1212
from pytask.database import create_or_update_state
13+
from pytask.exceptions import ExecutionError
1314
from pytask.exceptions import NodeNotFoundError
1415
from pytask.mark import Mark
1516
from pytask.nodes import FilePathNode
@@ -116,7 +117,7 @@ def pytask_execute_task_process_report(session, report):
116117
if report.success:
117118
_update_states_in_database(session.dag, task.name)
118119
else:
119-
for descending_task_name in task_and_descending_tasks(task.name, session.dag):
120+
for descending_task_name in descending_tasks(task.name, session.dag):
120121
descending_task = session.dag.nodes[descending_task_name]["task"]
121122
descending_task.markers.append(
122123
Mark(
@@ -125,7 +126,6 @@ def pytask_execute_task_process_report(session, report):
125126
{"reason": f"Previous task '{task.name}' failed."},
126127
)
127128
)
128-
129129
return True
130130

131131

@@ -161,6 +161,9 @@ def pytask_execute_log_end(session, reports):
161161
format_execute_footer(n_successful, n_failed, duration, tm_width), nl=True
162162
)
163163

164+
if n_failed:
165+
raise ExecutionError
166+
164167
return True
165168

166169

src/pytask/main.py

+4-1
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
from pytask.database import create_database
77
from pytask.enums import ExitCode
88
from pytask.exceptions import CollectionError
9+
from pytask.exceptions import ExecutionError
910
from pytask.exceptions import ResolvingDependenciesError
1011
from pytask.pluginmanager import get_plugin_manager
1112

@@ -63,8 +64,10 @@ def main(config_from_cli):
6364
except ResolvingDependenciesError:
6465
session.exit_code = ExitCode.RESOLVING_DEPENDENCIES_FAILED
6566

66-
except Exception as e:
67+
except ExecutionError:
6768
session.exit_code = ExitCode.FAILED
69+
70+
except Exception as e:
6871
if config["pdb"]:
6972
pdb.post_mortem()
7073
else:

src/pytask/parametrize.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -164,7 +164,7 @@ def _generate_product_of_names_and_functions(
164164
)
165165

166166
# Convert parametrized dependencies and products to decorator.
167-
func = copy.deepcopy(_copy_func(obj))
167+
func = _copy_func(obj)
168168
func.pytestmark = copy.deepcopy(obj.pytestmark)
169169

170170
for marker_name in ["depends_on", "produces"]:
@@ -188,7 +188,7 @@ def _to_tuple(x):
188188

189189

190190
def _copy_func(f):
191-
"""Based on http://stackoverflow.com/a/6528148/190597 (Glenn Maynard)"""
191+
"""Based on https://stackoverflow.com/a/13503277/7523785."""
192192
g = types.FunctionType(
193193
f.__code__,
194194
f.__globals__,

src/pytask/skipping.py

+9-5
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import click
22
import pytask
3-
from pytask.dag import task_and_descending_tasks
3+
from pytask.dag import descending_tasks
44
from pytask.mark import get_markers_from_task
55
from pytask.mark import Mark
66
from pytask.outcomes import Skipped
@@ -26,16 +26,20 @@ def pytask_execute_task_setup(task):
2626

2727
@pytask.hookimpl
2828
def pytask_execute_task_process_report(session, report):
29+
task = report.task
30+
2931
if report.exc_info and isinstance(report.exc_info[1], SkippedUnchanged):
3032
report.success = True
3133

3234
elif report.exc_info and isinstance(report.exc_info[1], Skipped):
3335
report.success = True
34-
for descending_task_name in task_and_descending_tasks(
35-
report.task.name, session.dag
36-
):
36+
for descending_task_name in descending_tasks(report.task.name, session.dag):
3737
descending_task = session.dag.nodes[descending_task_name]["task"]
38-
descending_task.markers.append(Mark("skip", (), {},))
38+
descending_task.markers.append(
39+
Mark(
40+
"skip", (), {"reason": f"Previous task '{task.name}' was skipped."},
41+
)
42+
)
3943

4044
elif report.exc_info and isinstance(report.exc_info[1], SkippedAncestorFailed):
4145
report.success = False

0 commit comments

Comments
 (0)