Skip to content

Commit 0397939

Browse files
committed
Merge remote-tracking branch 'origin/master' into stagefiles
2 parents 6f9c2f8 + 81ff56f commit 0397939

File tree

7 files changed

+78
-20
lines changed

7 files changed

+78
-20
lines changed

cwltool/cwltest.py

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -25,15 +25,15 @@ class CompareFail(Exception):
2525

2626

2727
def compare(a, b): # type: (Any, Any) -> bool
28+
if a == "Any" or b == "Any":
29+
return True
2830
try:
2931
if isinstance(a, dict):
3032
if a.get("class") == "File":
31-
if "path" in a:
32-
comp = "path"
33-
else:
34-
comp = "location"
35-
if a[comp] and (not (b[comp].endswith("/" + a[comp]) or ("/" not in b[comp] and a[comp] == b[comp]))):
36-
raise CompareFail(u"%s does not end with %s" %(b[comp], a[comp]))
33+
if a["path"] == "Any" or b["path"] == "Any":
34+
return True
35+
if not (b["path"].endswith("/" + a["path"]) or ("/" not in b["path"] and a["path"] == b["path"])):
36+
raise CompareFail(u"%s does not end with %s" %(b["path"], a["path"]))
3737
# ignore empty collections
3838
b = {k: v for k, v in b.iteritems()
3939
if not isinstance(v, (list, dict)) or len(v) > 0}

cwltool/main.py

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -182,6 +182,16 @@ def output_callback(out, processStatus):
182182
kwargs["outdir"] = tempfile.mkdtemp()
183183
output_dirs.add(kwargs["outdir"])
184184

185+
jobReqs = None
186+
if "cwl:requirements" in job_order_object:
187+
jobReqs = job_order_object["cwl:requirements"]
188+
elif ("cwl:defaults" in t.metadata and "cwl:requirements" in
189+
t.metadata["cwl:defaults"]):
190+
jobReqs = t.metadata["cwl:defaults"]["cwl:requirements"]
191+
if jobReqs:
192+
for req in jobReqs:
193+
t.requirements.append(req)
194+
185195
jobiter = t.job(job_order_object,
186196
output_callback,
187197
**kwargs)
@@ -297,7 +307,8 @@ def generate_parser(toolparser, tool, namemap):
297307
action = cast(argparse.Action, FileAppendAction)
298308
else:
299309
action = "append"
300-
310+
elif isinstance(inptype, dict) and inptype["type"] == "enum":
311+
atype = str
301312
if inptype == "string":
302313
atype = str
303314
elif inptype == "int":

cwltool/process.py

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -286,6 +286,22 @@ def fillInDefaults(inputs, job):
286286
else:
287287
raise validate.ValidationException("Missing input parameter `%s`" % shortname(inp["id"]))
288288

289+
290+
def avroize_type(field_type, name_prefix=""):
291+
"""
292+
adds missing information to a type so that CWL types are valid in schema_salad.
293+
"""
294+
if type(field_type) == list:
295+
field_type_result = []
296+
for idx, field_type_item in enumerate(field_type):
297+
field_type_result.append(avroize_type(field_type_item, name_prefix+"_"+str(idx)))
298+
return field_type_result
299+
elif type(field_type) == dict and "type" in field_type and field_type["type"] == "enum":
300+
if "name" not in field_type:
301+
field_type["name"] = name_prefix+"_type_enum"
302+
return field_type
303+
304+
289305
class Process(object):
290306
__metaclass__ = abc.ABCMeta
291307

@@ -328,7 +344,7 @@ def __init__(self, toolpath_object, **kwargs):
328344

329345
if sd:
330346
sdtypes = sd["types"]
331-
av = schema_salad.schema.make_valid_avro(sdtypes, {t["name"]: t for t in sdtypes}, set())
347+
av = schema_salad.schema.make_valid_avro(sdtypes, {t["name"]: t for t in avroize_type(sdtypes)}, set())
332348
for i in av:
333349
self.schemaDefs[i["name"]] = i
334350
avro.schema.make_avsc_object(av, self.names)
@@ -354,7 +370,7 @@ def __init__(self, toolpath_object, **kwargs):
354370
c["type"] = ["null"] + aslist(c["type"])
355371
else:
356372
c["type"] = c["type"]
357-
373+
c["type"] = avroize_type(c["type"],c["name"])
358374
if key == "inputs":
359375
self.inputs_record_schema["fields"].append(c) # type: ignore
360376
elif key == "outputs":

cwltool/workflow.py

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -82,27 +82,29 @@ def match_types(sinktype, src, iid, inputobj, linkMerge, valueFrom):
8282
else:
8383
raise WorkflowException(u"Unrecognized linkMerge enum '%s'" % linkMerge)
8484
return True
85-
elif valueFrom is not None or are_same_type(src.parameter["type"], sinktype) or sinktype == "Any":
85+
elif valueFrom is not None or can_assign_src_to_sink(src.parameter["type"], sinktype) or sinktype == "Any":
8686
# simply assign the value from state to input
8787
inputobj[iid] = copy.deepcopy(src.value)
8888
return True
8989
return False
9090

91-
def are_same_type(src, sink): # type: (Any, Any) -> bool
91+
def can_assign_src_to_sink(src, sink): # type: (Any, Any) -> bool
9292
"""Check for identical type specifications, ignoring extra keys like inputBinding.
9393
"""
9494
if isinstance(src, dict) and isinstance(sink, dict):
9595
if src["type"] == "array" and sink["type"] == "array":
96-
if 'null' in sink["items"]:
97-
return are_same_type([src["items"]], [it for it in sink["items"] if it != 'null'])
98-
return are_same_type(src["items"], sink["items"])
99-
elif src["type"] == sink["type"]:
100-
return True
101-
else:
102-
return False
96+
return can_assign_src_to_sink(src["items"], sink["items"])
97+
elif isinstance(src, list):
98+
for t in src:
99+
if can_assign_src_to_sink(t, sink):
100+
return True
101+
elif isinstance(sink, list):
102+
for t in sink:
103+
if can_assign_src_to_sink(src, t):
104+
return True
103105
else:
104106
return src == sink
105-
107+
return False
106108

107109
def object_from_state(state, parms, frag_only, supportsMultipleInput, sourceField):
108110
# type: (Dict[unicode, WorkflowStateItem], List[Dict[unicode, Any]], bool, bool, unicode) -> Dict[unicode, Any]

tests/echo-cwlrun-job.yaml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
cwl:tool: echo.cwl
2+
cwl:requirements:
3+
- class: DockerRequirement
4+
dockerPull: debian
5+
6+
inp: "Hoopla!"

tests/echo-job.yaml

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
cwl:requirements:
2+
- class: DockerRequirement
3+
dockerPull: debian
4+
5+
inp: "Howdy!"

tests/test_examples.py

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
import cwltool.expression as expr
55
import cwltool.factory
66
import cwltool.process
7-
7+
import cwltool.workflow
88

99
class TestParamMatching(unittest.TestCase):
1010

@@ -150,6 +150,24 @@ def loadref(base, p):
150150
set(("$include", "$schemas", "path")),
151151
loadref), indent=4)
152152

153+
class TestTypeCompare(unittest.TestCase):
154+
def test_typecompare(self):
155+
self.assertTrue(cwltool.workflow.can_assign_src_to_sink(
156+
{'items': ['string', 'null'], 'type': 'array'},
157+
{'items': ['string', 'null'], 'type': 'array'}))
158+
159+
self.assertTrue(cwltool.workflow.can_assign_src_to_sink(
160+
{'items': ['string'], 'type': 'array'},
161+
{'items': ['string', 'null'], 'type': 'array'}))
162+
163+
self.assertTrue(cwltool.workflow.can_assign_src_to_sink(
164+
{'items': ['string', 'null'], 'type': 'array'},
165+
{'items': ['string'], 'type': 'array'}))
166+
167+
self.assertFalse(cwltool.workflow.can_assign_src_to_sink(
168+
{'items': ['string'], 'type': 'array'},
169+
{'items': ['int'], 'type': 'array'}))
170+
153171

154172
if __name__ == '__main__':
155173
unittest.main()

0 commit comments

Comments
 (0)