Commit 1376293d authored by Paul McCarthy's avatar Paul McCarthy 🚵
Browse files

Merge branch 'rel/2.6.1' into 'v2.6'

Rel/2.6.1

See merge request fsl/fslpy!166
parents 996a52af 514294b3
Pipeline #4504 passed with stages
in 1 minute and 16 seconds
......@@ -21,6 +21,22 @@ set -e
if [[ -f /.dockerenv ]]; then
# We have to use different host names to connect
# to the docker daemon host on mac as opposed
# to on linux.
#
# On linux (assuming the docker job is running
# with --net=host), we can connect via
# username@localhost.
#
# On mac, we have to connect via
# username@host.docker.internal
if [[ "$CI_RUNNER_TAGS" == *"macOS"* ]]; then
if [[ "$FSL_HOST" == *"@localhost" ]]; then
FSL_HOST=${FSL_HOST/localhost/host.docker.internal}
fi
fi
apt-get update -y || yum -y check-update || true;
apt-get install -y openssh-client rsync git || yum install -y openssh-client rsync git || true;
......
......@@ -157,27 +157,27 @@ variables:
- bash ./.ci/test_template.sh
test:3.5:
test:3.6:
stage: test
image: pauldmccarthy/fsleyes-py35-wxpy4-gtk2
image: pauldmccarthy/fsleyes-py36-wxpy4-gtk3
<<: *test_template
test:3.6:
test:3.7:
stage: test
image: pauldmccarthy/fsleyes-py36-wxpy4-gtk2
image: pauldmccarthy/fsleyes-py37-wxpy4-gtk3
<<: *test_template
test:3.7:
test:3.8:
stage: test
image: pauldmccarthy/fsleyes-py37-wxpy4-gtk2
image: pauldmccarthy/fsleyes-py38-wxpy4-gtk3
<<: *test_template
test:build-pypi-dist:
stage: test
image: pauldmccarthy/fsleyes-py35-wxpy4-gtk2
image: pauldmccarthy/fsleyes-py36-wxpy4-gtk3
<<: *except_releases
tags:
......@@ -195,7 +195,7 @@ test:build-pypi-dist:
style:
stage: style
image: pauldmccarthy/fsleyes-py35-wxpy4-gtk2
image: pauldmccarthy/fsleyes-py36-wxpy4-gtk3
<<: *test_template
variables:
TEST_STYLE: "true"
......
......@@ -2,6 +2,18 @@ This document contains the ``fslpy`` release history in reverse chronological
order.
2.6.1 (Thursday 19th September 2019)
------------------------------------
Changed
^^^^^^^
* ``fslpy`` is no longer tested against Python 3.5, and is now tested against
Python 3.6, 3.7, and 3.8.
2.6.0 (Tuesday 10th September 2019)
-----------------------------------
......
......@@ -77,7 +77,7 @@ def read_line(line: str) -> Tuple[int, PurePath, str]:
"""
Parses line from the tree file
:param line: input line from a \*.tree file
:param line: input line from a ``*.tree`` file
:return: Tuple with:
- number of spaces in front of the name
......@@ -105,7 +105,7 @@ def read_subtree_line(line: str, directory: str) -> Tuple[int, "filetree.FileTre
"""
Parses the line defining a sub_tree
:param line: input line from a \*.tree file
:param line: input line from a ``*.tree`` file
:param directory: containing directory
:return: Tuple with
......
......@@ -48,9 +48,8 @@ class FileTreeQuery(object):
short name that are present. The :meth:`query` method can be used to
retrieve files which match a specific template, and variable values.
The :meth:`query` method returns a multi-dimensional ``numpy.array``
which contains :class:`Match` objects, where each dimension one
represents variable for the template in question.
The :meth:`query` method returns a collection of :class:`Match` objects,
each of which represents one file which matches the query.
Example usage::
......
......@@ -98,7 +98,7 @@ def resolve_optionals(text):
else:
return ''
res = [resolve_single_optional(text) for text in re.split('(\[.*?\])', text)]
res = [resolve_single_optional(text) for text in re.split(r'(\[.*?\])', text)]
return ''.join(res)
......@@ -109,7 +109,7 @@ def find_variables(template):
:param template: full template
:return: sequence of variables
"""
return tuple(var.split(':')[0] for var in re.findall("\{(.*?)\}", template))
return tuple(var.split(':')[0] for var in re.findall(r"\{(.*?)\}", template))
def optional_variables(template):
......@@ -121,7 +121,7 @@ def optional_variables(template):
"""
include = set()
exclude = set()
for text in re.split('(\[.*?\])', template):
for text in re.split(r'(\[.*?\])', template):
if len(text) == 0:
continue
variables = find_variables(text)
......@@ -152,13 +152,13 @@ def extract_variables(template, filename, known_vars=None):
sub_re = resolve_optionals(fill_known(
template,
dict(
**{var: '(\S+)' for k, var in zip(keep, optional) if k},
**{var: '(\S+)' for var in remaining.difference(optional)}
**{var: r'(\S+)' for k, var in zip(keep, optional) if k},
**{var: r'(\S+)' for var in remaining.difference(optional)}
)
))
while '//' in sub_re:
sub_re = sub_re.replace('//', '/')
sub_re = sub_re.replace('.', '\.')
sub_re = sub_re.replace('.', r'\.')
if re.match(sub_re, filename) is None:
continue
......
......@@ -86,7 +86,7 @@ import atexit
import logging
import functools
import threading
import collections
from collections import abc
try: import queue
except ImportError: import Queue as queue
......@@ -610,7 +610,7 @@ def wait(threads, task, *args, **kwargs):
direct = kwargs.pop('wait_direct', False)
if not isinstance(threads, collections.Sequence):
if not isinstance(threads, abc.Sequence):
threads = [threads]
haveWX = fslplatform.haveGui
......
......@@ -47,7 +47,7 @@ import re
import string
__version__ = '2.6.0'
__version__ = '2.6.1'
"""Current version number, as a string. """
......
......@@ -5,21 +5,21 @@ test=pytest
universal=1
[tool:pytest]
# Available test markers:
# - fsltest: Requires FSL
# - wxtest: Requires wxPython
# - dicomtest: Requires dcm2niix
# - meshtest: Requires trimesh and rtree
# - igziptest: Requires indexed_gzip
# - piltest: Requires Pillow
# - noroottest: Need to be executed as
# non-root user (will fail
# otherwise)
# - longtest: Takes a long time
#
markers =
fsltest: Requires FSL
wxtest: Requires wxPython
dicomtest: Requires dcm2niix
meshtest: Requires trimesh and rtree
igziptest: Requires indexed_gzip
piltest: Requires Pillow
noroottest: Need to be executed as non-root user (will fail otherwise)
longtest: Takes a long time
unixtest: Only works on *nix systems
testpaths = tests
addopts = -v --niters=50 --cov=fsl -m "not longtest"
[flake8]
ignore = E127,E201,E203,E221,E222,E241,E271,E272,E301,E302,E303,E701,W504
\ No newline at end of file
......@@ -9,13 +9,13 @@ import pytest
import scipy.ndimage as ndimage
import fsl.data.image as fslimage
import fsl.utils.transform as transform
import fsl.transform.affine as affine
import fsl.utils.image.resample as resample
from . import make_random_image
def random_affine():
return transform.compose(
return affine.compose(
0.25 + 4.75 * np.random.random(3),
-50 + 100 * np.random.random(3),
-np.pi + 2 * np.pi * np.random.random(3))
......@@ -61,9 +61,9 @@ def test_resample(seed):
resx, resy, resz = restestcoords.T
resvals = resampled[resx, resy, resz]
res2orig = transform.concat(img.worldToVoxMat, xf)
res2orig = affine.concat(img.worldToVoxMat, xf)
origtestcoords = transform.transform(restestcoords, res2orig)
origtestcoords = affine.transform(restestcoords, res2orig)
# remove any coordinates which are out of
# bounds in the original image space, or
......@@ -130,8 +130,8 @@ def test_resample_origin(seed):
shape = np.random.randint(5, 50, 3)
res = resample.resample(img, shape, origin='corner')
res = fslimage.Image(res[0], xform=res[1])
imgb = transform.axisBounds(img.shape, img.voxToWorldMat)
resb = transform.axisBounds(res.shape, res.voxToWorldMat)
imgb = affine.axisBounds(img.shape, img.voxToWorldMat)
resb = affine.axisBounds(res.shape, res.voxToWorldMat)
assert np.all(np.isclose(imgb, resb, rtol=1e-5, atol=1e-5))
# with origin='centre' image
......@@ -142,8 +142,8 @@ def test_resample_origin(seed):
res = resample.resample(img, shape, origin='centre')
res = fslimage.Image(res[0], xform=res[1])
off = (np.array(img.shape) / np.array(res.shape) - 1) / 2
imgb = np.array(transform.axisBounds(img.shape, img.voxToWorldMat))
resb = np.array(transform.axisBounds(res.shape, res.voxToWorldMat))
imgb = np.array(affine.axisBounds(img.shape, img.voxToWorldMat))
resb = np.array(affine.axisBounds(res.shape, res.voxToWorldMat))
assert np.all(np.isclose(imgb, resb + off, rtol=1e-5, atol=1e-5))
# with origin='corner', using
......@@ -165,7 +165,7 @@ def test_resample_origin(seed):
def test_resampleToPixdims():
img = fslimage.Image(make_random_image(dims=(10, 10, 10)))
imglo, imghi = transform.axisBounds(img.shape, img.voxToWorldMat)
imglo, imghi = affine.axisBounds(img.shape, img.voxToWorldMat)
oldpix = np.array(img.pixdim, dtype=np.float)
oldshape = np.array(img.shape, dtype=np.float)
......@@ -177,7 +177,7 @@ def test_resampleToPixdims():
res = resample.resampleToPixdims(img, newpix, origin=origin)
res = fslimage.Image(res[0], xform=res[1])
reslo, reshi = transform.axisBounds(res.shape, res.voxToWorldMat)
reslo, reshi = affine.axisBounds(res.shape, res.voxToWorldMat)
resfov = reshi - reslo
expfov = newpix * res.shape
......@@ -219,7 +219,7 @@ def test_resampleToReference2():
img[1, 1, 1] = 1
img = fslimage.Image(img)
refv2w = transform.scaleOffsetXform([1, 1, 1], [-1, -1, -1])
refv2w = affine.scaleOffsetXform([1, 1, 1], [-1, -1, -1])
ref = np.zeros((5, 5, 5), dtype=np.float)
ref = fslimage.Image(ref, xform=refv2w)
res = resample.resampleToReference(img, ref, order=0)
......@@ -235,7 +235,7 @@ def test_resampleToReference3():
# Test resampling image to ref
# with mismatched dimensions
imgdata = np.random.randint(0, 65536, (5, 5, 5))
img = fslimage.Image(imgdata, xform=transform.scaleOffsetXform(
img = fslimage.Image(imgdata, xform=affine.scaleOffsetXform(
(2, 2, 2), (0.5, 0.5, 0.5)))
# reference/expected data when
......@@ -270,7 +270,7 @@ def test_resampleToReference4():
# the image and ref are out of
# alignment, but this affine
# will bring them into alignment
img2ref = transform.scaleOffsetXform([2, 2, 2], [10, 10, 10])
img2ref = affine.scaleOffsetXform([2, 2, 2], [10, 10, 10])
imgdata = np.random.randint(0, 65536, (5, 5, 5))
refdata = np.zeros((5, 5, 5))
......
......@@ -286,7 +286,7 @@ def _eval_coord_voxel_query(
else:
exp = [q_type, squery]
_stdout = re.sub('\s+', ' ', stdout).strip()
_stdout = re.sub(r'\s+', ' ', stdout).strip()
assert _stdout == ' '.join(exp)
if isinstance(a_img, fslatlases.LabelAtlas):
......@@ -388,7 +388,7 @@ def _eval_mask_query(
if expprop > 0:
exp.append('{} {:0.4f}'.format(explabel, expprop))
_stdout = re.sub('\s+', ' ', stdout).strip()
_stdout = re.sub(r'\s+', ' ', stdout).strip()
assert _stdout == ' '.join(exp)
if isinstance(aimg, fslatlases.LabelAtlas):
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment