Skip to content

Commit

Permalink
fix(api): Remove crs from scripts in api/resources
Browse files Browse the repository at this point in the history
If a wheel is built on Windows, there's a good chance there will be carriage returns in the scripts
in api/resources, which break the container initialization scripts. To avoid editing the files in
question in the repo, add a step during the wheel build that unzips the wheel, removes carriage
returns, and rezips it.

Closes #2305
  • Loading branch information
sfoster1 committed Sep 18, 2018
1 parent 1e3b27e commit 5e693a5
Show file tree
Hide file tree
Showing 2 changed files with 119 additions and 0 deletions.
1 change: 1 addition & 0 deletions api/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ dev:
.PHONY: wheel
wheel: clean
$(python) setup.py bdist_wheel
$(python) remove_cr_in_zip.py -v dist/
shx rm -rf build
shx ls dist

Expand Down
118 changes: 118 additions & 0 deletions api/remove_cr_in_zip.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
"""
Edit an opentrons wheel to remove any carriage returns from files in resources
If there are crs in the scripts in resources/, the robot will not be able to
boot because those files are sourced directly during the boot process. While
the crs may be rewritten when they are committed and pushed to github, if a
windows dev does a push-api from their local checkout there's a good chance
the crs will still be present.
This script therefore opens the specified wheel, unzips it to a tempdir,
removes any carriage returns found in /resources, and rezips it to the
original filename.
"""

import zipfile
import tempfile
import os
import sys
import re


def _write_files(outzip, contentsdir, verbose=False):
for dirpath, dirnames, filenames in os.walk(contentsdir):
for fn in filenames:
fn_abs = os.path.join(dirpath, fn)
zip_path = os.path.relpath(fn_abs, contentsdir)
outzip.write(fn_abs, zip_path)


def _edit_files(indir, verbose=False):
to_edit = []
print(os.listdir(os.path.join(indir, 'opentrons')))
for root, _2, filenames in os.walk(os.path.join(indir,
'opentrons',
'resources')):
to_edit.extend([os.path.join(root, fn) for fn in filenames])
if verbose:
print("File edit list: {}".format(to_edit))
for fn in to_edit:
# We don’t need to edit python files
if verbose:
sys.stdout.write("Checking {}: ".format(fn))
if fn.endswith('.py') or fn.endswith('.pyc'):
if verbose:
print("Skipped (is python file)")
continue
# Or python files that don’t look like python files
try:
first = open(fn).readline()
except UnicodeDecodeError: # (or binary files)
print("Skipped (is most likely binary)")
continue
else:
if first.startswith('#!') and 'python' in first:
if verbose:
print("Skipped (is shebanged python file)")
continue
contents = open(fn, 'rb').read()
new = re.sub(b'\r\n', b'\n', contents)
if verbose:
if len(contents)-len(new) > 0:
print("Edited (found {} <cr>)"
.format(len(contents)-len(new)))
else:
print("Nothing to do")
open(fn, 'wb').write(new)


def rewrite_egg(infile, outfile, verbose=False):
""" Rewrite any <cr> in the resources/ subdirectory of the specified egg.
filelike should be an open filelike object holding the egg.
"""
with tempfile.TemporaryDirectory() as tempdir:
with zipfile.ZipFile(infile, 'r') as inzip:
if verbose:
print("Extracting {} to {}".format(inzip, tempdir))
inzip.extractall(tempdir)
print("Editing files in {}".format(tempdir))
_edit_files(tempdir, verbose)
with zipfile.ZipFile(outfile, 'w') as outzip:
if verbose:
print("Zipping {} to {}".format(tempdir, outzip))
_write_files(outzip, tempdir, verbose)


if __name__ == '__main__':
import argparse
parser = argparse.ArgumentParser(
description='Create a new opentrons egg without <cr> in shell scripts')
parser.add_argument(
'in_whl', metavar='INWHL', type=str,
help='The wheel file, or directory containing the egg file, to read')
parser.add_argument(
'out_whl', metavar='OUTWHL', type=str,
help='The wheel file to write. If not specified, execute in place',
nargs='?',
default=None)
parser.add_argument('-v', '--verbose', help='Print extra status messages',
action='store_true')
args = parser.parse_args()
if os.path.isdir(args.in_whl):
files = os.listdir(args.in_whl)
for f in files:
if re.match('opentrons-.*.whl', f):
in_whl = os.path.join(args.in_whl, f)
break
else:
raise OSError("Couldn't find anything that looked like a wheel in {}"
.format(args.in_whl))
else:
in_whl = args.in_whl
if None is args.out_whl:
out_whl = in_whl
else:
out_whl = args.out_whl

rewrite_egg(in_whl, out_whl, args.verbose)

0 comments on commit 5e693a5

Please sign in to comment.