Skip to content

Commit 181bba2

Browse files
authored
Merge pull request #166 from common-workflow-language/flake-mypy-auto
add auto flake8 & mypy tests for pull requests
2 parents 491af41 + cfc568b commit 181bba2

21 files changed

+176
-102
lines changed

.travis.yml

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
sudo: false
2+
language: python
3+
python:
4+
- 2.7
5+
- 3.5
6+
os:
7+
- linux
8+
9+
install:
10+
- pip install tox-travis
11+
script: tox
12+
notifications:
13+
email: false

Makefile

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,8 @@ MODULE=cwltool
2626
# `SHELL=bash` doesn't work for some, so don't use BASH-isms like
2727
# `[[` conditional expressions.
2828
PYSOURCES=$(wildcard ${MODULE}/**.py tests/*.py) setup.py
29-
DEVPKGS=pep8 diff_cover autopep8 pylint coverage pep257
30-
DEBDEVPKGS=pep8 python-autopep8 pylint python-coverage pep257 sloccount
29+
DEVPKGS=pep8 diff_cover autopep8 pylint coverage pep257 flake8
30+
DEBDEVPKGS=pep8 python-autopep8 pylint python-coverage pep257 sloccount python-flake8
3131
VERSION=1.0.$(shell date +%Y%m%d%H%M%S --date=`git log --first-parent \
3232
--max-count=1 --format=format:%cI`)
3333
mkfile_dir := $(dir $(abspath $(lastword $(MAKEFILE_LIST))))
@@ -149,10 +149,10 @@ list-author-emails:
149149

150150
mypy: ${PYSOURCES}
151151
rm -Rf typeshed/2.7/ruamel/yaml
152-
ln -s $(shell python -c 'import ruamel.yaml; import os.path; print os.path.dirname(ruamel.yaml.__file__)') \
152+
ln -s $(shell python -c 'from __future__ import print_function; import ruamel.yaml; import os.path; print(os.path.dirname(ruamel.yaml.__file__))') \
153153
typeshed/2.7/ruamel/yaml
154154
rm -Rf typeshed/2.7/schema_salad
155-
ln -s $(shell python -c 'import schema_salad; import os.path; print os.path.dirname(schema_salad.__file__)') \
155+
ln -s $(shell python -c 'from __future__ import print_function; import schema_salad; import os.path; print(os.path.dirname(schema_salad.__file__))') \
156156
typeshed/2.7/schema_salad
157157
MYPYPATH=typeshed/2.7 mypy --py2 --disallow-untyped-calls \
158158
--warn-redundant-casts --warn-unused-ignores cwltool

cwltool/builder.py

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -86,10 +86,9 @@ def bind_input(self, schema, datum, lead_pos=[], tail_pos=[]):
8686
b2 = copy.deepcopy(binding)
8787
b2["datum"] = item
8888
bindings.extend(
89-
self.bind_input(
90-
{"type": schema["items"],
91-
"inputBinding": b2},
92-
item, lead_pos=n, tail_pos=tail_pos))
89+
self.bind_input(
90+
{"type": schema["items"], "inputBinding": b2},
91+
item, lead_pos=n, tail_pos=tail_pos))
9392
binding = None
9493

9594
if schema["type"] == "File":

cwltool/cwltest.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,7 @@ def compare(a, b): # type: (Any, Any) -> bool
4343
raise CompareFail(u"%s does not end with %s" %(b[comp], a[comp]))
4444
# ignore empty collections
4545
b = {k: v for k, v in b.iteritems()
46-
if not isinstance(v, (list, dict)) or len(v) > 0}
46+
if not isinstance(v, (list, dict)) or len(v) > 0}
4747
elif a.get("class") == "Directory":
4848
if len(a["listing"]) != len(b["listing"]):
4949
return False
@@ -215,8 +215,8 @@ def main(): # type: () -> int
215215
_logger.error("Tests interrupted")
216216

217217
if failures == 0 and unsupported == 0:
218-
_logger.info("All tests passed")
219-
return 0
218+
_logger.info("All tests passed")
219+
return 0
220220
elif failures == 0 and unsupported > 0:
221221
_logger.warn("%i tests passed, %i unsupported features", total - unsupported, unsupported)
222222
return 0

cwltool/draft2tool.py

Lines changed: 18 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -109,11 +109,11 @@ def __init__(self, job, output_callback, cachebuilder, jobcache):
109109

110110
def run(self, **kwargs):
111111
# type: (**Any) -> None
112-
self.output_callback(self.job.collect_output_ports(self.job.tool["outputs"],
113-
self.cachebuilder,
114-
self.outdir,
115-
kwargs.get("compute_checksum", True)),
116-
"success")
112+
self.output_callback(self.job.collect_output_ports(
113+
self.job.tool["outputs"],
114+
self.cachebuilder,
115+
self.outdir,
116+
kwargs.get("compute_checksum", True)), "success")
117117

118118
# map files to assigned path inside a container. We need to also explicitly
119119
# walk over input as implicit reassignment doesn't reach everything in builder.bindings
@@ -221,16 +221,17 @@ def job(self, joborder, output_callback, **kwargs):
221221
os.makedirs(jobcache)
222222
kwargs["outdir"] = jobcache
223223
open(jobcachepending, "w").close()
224+
224225
def rm_pending_output_callback(output_callback, jobcachepending,
225226
outputs, processStatus):
226227
if processStatus == "success":
227228
os.remove(jobcachepending)
228229
output_callback(outputs, processStatus)
229230
output_callback = cast(
230-
Callable[..., Any], # known bug in mypy
231-
# https://github.com/python/mypy/issues/797
232-
partial(rm_pending_output_callback, output_callback,
233-
jobcachepending))
231+
Callable[..., Any], # known bug in mypy
232+
# https://github.com/python/mypy/issues/797
233+
partial(rm_pending_output_callback, output_callback,
234+
jobcachepending))
234235

235236
builder = self._init_job(joborder, **kwargs)
236237

@@ -358,7 +359,8 @@ def rm_pending_output_callback(output_callback, jobcachepending,
358359

359360
j.pathmapper = builder.pathmapper
360361
j.collect_outputs = partial(
361-
self.collect_output_ports, self.tool["outputs"], builder, compute_checksum=kwargs.get("compute_checksum", True))
362+
self.collect_output_ports, self.tool["outputs"], builder,
363+
compute_checksum=kwargs.get("compute_checksum", True))
362364
j.output_callback = output_callback
363365

364366
yield j
@@ -380,12 +382,11 @@ def collect_output_ports(self, ports, builder, outdir, compute_checksum=True):
380382
ret[fragment] = self.collect_output(port, builder, outdir, fs_access, compute_checksum=compute_checksum)
381383
except Exception as e:
382384
_logger.debug(
383-
u"Error collecting output for parameter '%s'"
384-
% shortname(port["id"]), exc_info=True)
385+
u"Error collecting output for parameter '%s'"
386+
% shortname(port["id"]), exc_info=True)
385387
raise WorkflowException(
386-
u"Error collecting output for " \
387-
"parameter '%s': %s" %
388-
(shortname(port["id"]), e))
388+
u"Error collecting output for parameter '%s': %s"
389+
% (shortname(port["id"]), e))
389390

390391
if ret:
391392
adjustFileObjs(ret,
@@ -507,6 +508,7 @@ def collect_output(self, schema, builder, outdir, fs_access, compute_checksum=Tr
507508
out = {}
508509
for f in schema["type"]["fields"]:
509510
out[shortname(f["name"])] = self.collect_output( # type: ignore
510-
f, builder, outdir, fs_access, compute_checksum=compute_checksum)
511+
f, builder, outdir, fs_access,
512+
compute_checksum=compute_checksum)
511513
return out
512514
return r

cwltool/expression.py

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,7 @@ def exeval(ex, jobinput, requirements, outdir, tmpdir, context, pull_image):
3131
"self": context,
3232
"runtime": {
3333
"tmpdir": tmpdir,
34-
"outdir": outdir
35-
}
34+
"outdir": outdir }
3635
}
3736
return sandboxjs.execjs(ex["script"], jshead(engineConfig, rootvars))
3837

@@ -66,7 +65,7 @@ def __init__(self): # type: ()->None
6665

6766
_logger.debug(u"Invoking expression engine %s with %s",
6867
runtime + aslist(r["engineCommand"]),
69-
json.dumps(inp, indent=4))
68+
json.dumps(inp, indent=4))
7069

7170
sp = subprocess.Popen(runtime + aslist(r["engineCommand"]),
7271
shell=False,
@@ -85,7 +84,7 @@ def __init__(self): # type: ()->None
8584
seg_symbol = r"""\w+"""
8685
seg_single = r"""\['([^']|\\')+'\]"""
8786
seg_double = r"""\["([^"]|\\")+"\]"""
88-
seg_index = r"""\[[0-9]+\]"""
87+
seg_index = r"""\[[0-9]+\]"""
8988
segments = r"(\.%s|%s|%s|%s)" % (seg_symbol, seg_single, seg_double, seg_index)
9089
segment_re = re.compile(segments, flags=re.UNICODE)
9190
param_re = re.compile(r"\$\((%s)%s*\)" % (seg_symbol, segments), flags=re.UNICODE)
@@ -132,10 +131,9 @@ def do_eval(ex, jobinput, requirements, outdir, tmpdir, resources,
132131
runtime["outdir"] = outdir
133132

134133
rootvars = {
135-
"inputs": jobinput,
136-
"self": context,
137-
"runtime": runtime
138-
}
134+
"inputs": jobinput,
135+
"self": context,
136+
"runtime": runtime }
139137

140138
if isinstance(ex, dict) and "engine" in ex and "script" in ex:
141139
return exeval(ex, jobinput, requirements, outdir, tmpdir, context, pull_image)

cwltool/job.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -79,8 +79,8 @@ def run(self, dry_run=False, pull_image=True, rm_container=True,
7979
p = self.pathmapper.mapper(knownfile)
8080
if p.type == "File" and not os.path.isfile(p[0]):
8181
raise WorkflowException(
82-
u"Input file %s (at %s) not found or is not a regular file."
83-
% (knownfile, self.pathmapper.mapper(knownfile)[0]))
82+
u"Input file %s (at %s) not found or is not a regular "
83+
"file." % (knownfile, self.pathmapper.mapper(knownfile)[0]))
8484

8585
img_id = None
8686
env = None # type: MutableMapping[str, str]
@@ -176,6 +176,7 @@ def run(self, dry_run=False, pull_image=True, rm_container=True,
176176
self.outdir, separateDirs=False)
177177
_logger.debug(u"[job %s] initial work dir %s", self.name,
178178
json.dumps({p: generatemapper.mapper(p) for p in generatemapper.files()}, indent=4))
179+
179180
def linkoutdir(src, tgt):
180181
# Need to make the link to the staged file (may be inside
181182
# the container)

cwltool/load_tool.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -54,8 +54,8 @@ def _convert_stdstreams_to_files(workflowobj):
5454
if out['type'] == streamtype:
5555
if 'outputBinding' in out:
5656
raise ValidationException(
57-
"Not allowed to specify outputBinding when"
58-
" using %s shortcut." % streamtype)
57+
"Not allowed to specify outputBinding when"
58+
" using %s shortcut." % streamtype)
5959
if streamtype in workflowobj:
6060
filename = workflowobj[streamtype]
6161
else:
@@ -104,7 +104,7 @@ def validate_document(document_loader, workflowobj, uri,
104104
del workflowobj["@graph"]
105105

106106
(document_loader, avsc_names) = \
107-
process.get_schema(workflowobj["cwlVersion"])[:2]
107+
process.get_schema(workflowobj["cwlVersion"])[:2]
108108

109109
if isinstance(avsc_names, Exception):
110110
raise avsc_names

cwltool/main.py

Lines changed: 16 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -140,8 +140,9 @@ def arg_parser(): # type: () -> argparse.ArgumentParser
140140

141141
parser.add_argument("--tool-help", action="store_true", help="Print command line help for tool")
142142

143-
parser.add_argument("--relative-deps", choices=['primary', 'cwd'], default="primary",
144-
help="When using --print-deps, print paths relative to primary file or current working directory.")
143+
parser.add_argument("--relative-deps", choices=['primary', 'cwd'],
144+
default="primary", help="When using --print-deps, print paths "
145+
"relative to primary file or current working directory.")
145146

146147
parser.add_argument("--enable-dev", action="store_true",
147148
help="Allow loading and running development versions "
@@ -306,8 +307,8 @@ def generate_parser(toolparser, tool, namemap):
306307

307308
ahelp = inp.get("description", "").replace("%", "%%")
308309
action = None # type: Union[argparse.Action,str]
309-
atype = None # type: Any
310-
default = None # type: Any
310+
atype = None # type: Any
311+
default = None # type: Any
311312

312313
if inptype == "File":
313314
action = cast(argparse.Action, FileAction)
@@ -345,8 +346,8 @@ def generate_parser(toolparser, tool, namemap):
345346
typekw = {}
346347

347348
toolparser.add_argument( # type: ignore
348-
flag + name, required=required, help=ahelp, action=action,
349-
default=default, **typekw)
349+
flag + name, required=required, help=ahelp, action=action,
350+
default=default, **typekw)
350351

351352
return toolparser
352353

@@ -361,10 +362,10 @@ def load_job_order(args, t, stdin, print_input_deps=False, relative_deps=False,
361362
loader = Loader({})
362363
else:
363364
jobloaderctx = {
364-
u"path": {u"@type": u"@id"},
365-
u"location": {u"@type": u"@id"},
366-
u"format": {u"@type": u"@id"},
367-
u"id": u"@id"}
365+
u"path": {u"@type": u"@id"},
366+
u"location": {u"@type": u"@id"},
367+
u"format": {u"@type": u"@id"},
368+
u"id": u"@id"}
368369
jobloaderctx.update(t.metadata.get("$namespaces", {}))
369370
loader = Loader(jobloaderctx)
370371

@@ -458,9 +459,9 @@ def printdeps(obj, document_loader, stdout, relative_deps, uri, basedir=None):
458459
def loadref(b, u):
459460
return document_loader.fetch(urlparse.urljoin(b, u))
460461

461-
sf = scandeps(basedir if basedir else uri, obj,
462-
set(("$import", "run")),
463-
set(("$include", "$schemas", "path", "location")), loadref)
462+
sf = scandeps(
463+
basedir if basedir else uri, obj, set(("$import", "run")),
464+
set(("$include", "$schemas", "path", "location")), loadref)
464465
if sf:
465466
deps["secondaryFiles"] = sf
466467

@@ -471,6 +472,7 @@ def loadref(b, u):
471472
base = "file://" + os.getcwd()
472473
else:
473474
raise Exception(u"Unknown relative_deps %s" % relative_deps)
475+
474476
def makeRelative(ob):
475477
u = ob.get("location", ob.get("path"))
476478
if ":" in u.split("/")[0] and not u.startswith("file://"):
@@ -521,8 +523,7 @@ def print_pack(document_loader, processobj, uri, metadata):
521523
def loadref(b, u):
522524
# type: (unicode, unicode) -> Union[Dict, List, unicode]
523525
return document_loader.resolve_ref(u, base_url=b)[0]
524-
deps = scandeps(uri, processobj,
525-
set(("run",)), set(), loadref)
526+
deps = scandeps(uri, processobj, set(("run",)), set(), loadref)
526527

527528
fdeps = set((uri,))
528529
flatten_deps(deps, fdeps)

cwltool/pathmapper.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -161,14 +161,14 @@ def setup(self, referenced_files, basedir):
161161

162162
# Dereference symbolic links
163163
for path, (ab, tgt, type) in self._pathmap.items():
164-
if type != "File": # or not os.path.exists(ab):
164+
if type != "File": # or not os.path.exists(ab):
165165
continue
166166
deref = ab
167167
st = os.lstat(deref)
168168
while stat.S_ISLNK(st.st_mode):
169169
rl = os.readlink(deref)
170170
deref = rl if os.path.isabs(rl) else os.path.join(
171-
os.path.dirname(deref), rl)
171+
os.path.dirname(deref), rl)
172172
st = os.lstat(deref)
173173

174174
self._pathmap[path] = MapperEnt(deref, tgt, "File")

0 commit comments

Comments
 (0)