Currently the subpaths are redistributed in create_append_path,
but even though that sets path.parallel_safe=false, it's too late
for set_append_rel_pathlist() to realize that.
It simply grabs the first path from childrel->partial_pathlist and
builds an AppendPath on top of that, assuming the resulting Append
is also parallel_safe.
But if the child relations had to be redistributed by adding a
RemoteSubplan on each of them, then the Append is parallel unsafe
and the attempt to add Gather on top of that fails because of
tripping on Assert(subpath->parallel_safe).
Make sure the result of create_append_path is also parallel safe
before adding it as a partial path.
I'd be surprised if there were no other places relying on the same
assumption. Ultimately, we probably want to build the redistributed
paths before calling create_append_path().
/* Generate a partial append path. */
appendpath = create_append_path(rel, partial_subpaths, NULL,
parallel_workers);
- add_partial_path(rel, (Path *) appendpath);
+
+ /*
+ * XL: In case we had to re-distribute the child relations, don't
+ * do anything. Otherwise create_gather_path hits an Assert etc.
+ */
+ if (appendpath->path.parallel_safe)
+ add_partial_path(rel, (Path *) appendpath);
}
/*