Merge branch 'master' into devel

This commit is contained in:
John Evans 2013-07-12 08:32:05 -04:00
commit 03bdd3bf9b
23 changed files with 313 additions and 194 deletions

View file

@ -1,3 +1,7 @@
Jul 11, 2013 - v0.2.2 Fixed mistakes with trove classifier, pypi releases.
Jul 11, 2013 - v0.2.0 Support for Python 2.7 on windows, OpenJPEG 1.5.1.
Jun 27, 2013 - v0.1.10 Can wrap codestreams in custom JP2 jackets. Exposing
parameter to specify multi component transform. Added a raw codestream
file.

View file

@ -78,7 +78,7 @@ copyright = u'2013, John Evans'
# The short X.Y version.
version = '0.1'
# The full version, including alpha/beta/rc tags.
release = '0.1.10'
release = '0.2.2'
# The language for content autogenerated by Sphinx. Refer to documentation
# for a list of supported languages.

View file

@ -7,15 +7,15 @@ Glymur Configuration
''''''''''''''''''''''
The default glymur installation process relies upon OpenJPEG version
1.5.1 being properly installed on your system. This will, however,
only give you you basic read capabilities, so if you wish to take
advantage of more of glymur's features, you should compile OpenJPEG as
a shared library from the developmental source that you can retrieve
via subversion. As of this time of writing, svn revision 2345 works.
You should also download the test data for the purpose of configuring
and running OpenJPEG's test suite, check their instructions for all this.
You should set the **OPJ_DATA_ROOT** environment variable for the purpose
of running Glymur's test suite. ::
1.5.1 being properly installed on your system. This will, however, only
give you you basic read capabilities, so if you wish to take advantage
of more of glymur's features, you should compile OpenJPEG as a shared
library (named *openjp2* instead of *openjpeg*) from the developmental
source that you can retrieve via subversion. As of this time of writing,
svn revision 2345 works. You should also download the test data for
the purpose of configuring and running OpenJPEG's test suite, check
their instructions for all this. You should set the **OPJ_DATA_ROOT**
environment variable for the purpose of running Glymur's test suite. ::
$ svn co http://openjpeg.googlecode.com/svn/data
$ export OPJ_DATA_ROOT=`pwd`/data
@ -32,13 +32,16 @@ the openjp2 library. You may create the configuration file as follows::
> openjp2: /opt/openjp2-svn/lib/libopenjp2.so
> EOF
That assumes, of course, that you've installed OpenJPEG into
This assumes, of course, that you've installed OpenJPEG into
/opt/openjp2-svn on a linux system. You may also substitute
**$XDG_CONFIG_HOME** for **$HOME/.config**.
Again, though, the configuration file is not required if you only wish to
read JPEG 2000 files using OpenJPEG version 1.5.1.
You may also include a line for the version 1.5.1 library if you have it installed
in a non-standard place, i.e. ::
[library]
openjp2: /opt/openjp2-svn/lib/libopenjp2.so
openjpeg: /not/the/usual/location/lib/libopenjpeg.so
'''''''''''''''''''''''''''''''''''''''''''
Package Management Suggestions for Testing
@ -65,13 +68,29 @@ additionally be installed:
* py33-scikit-image and either py33-Pillow or freeimage
* py33-matplotlib and py33-Pillow
MacPorts supplies both OpenJPEG 1.5.0 and OpenJPEG 2.0.0. As previously
mentioned, the 2.0.0 official release is not supported (although the 2.0+
development version via SVN *is* supported).
Linux
-----
Fedora 19
'''''''''
Fedora 18 ships with Python 3.3 and all the necessary RPMs are available to
run the maximum number of tests.
* python3
* python3-numpy
* python3-setuptools
* python3-matplotlib (for running tests)
* python3-matplotlib-tk (or whichever matplotlib backend you prefer)
* python3-pillow (for running tests)
Fedora 18
'''''''''
Fedora 18 ships with Python 3.3, so all the necessary RPMs are available to
meet the minimal set of requirements.
Fedora 18 ships with Python 3.3 and the following RPMs are available to
meet the minimal set of requirements for running glymur.
* python3
* python3-numpy
@ -94,28 +113,6 @@ repositories::
$ pip-python3 install Pillow --user
$ export PYTHONPATH=$HOME/.local/lib/python3.3/site-packages:$PYTHONPATH
Raspbian
''''''''
Yeah, this was the first thing I tried after getting my new Raspberry
Pi hooked up (couldn't help myself :-) Raspbian ships with Python
3.2 and 2.7, so these steps detail working with 2.7.
Additional required OS packages include::
* python-pip
* python-pkg-resources
* python-mock
You must install contextlib2 via pip, and then you can run at least
a minimal number of tests. To attempt to run more of the tests,
install the following debs::
* python-dev
* python-matplotlib
and then install Pillow via pip. The tests take about 30 minutes to run, with
one unexpected failure as of the time of writing.
Fedora 17
'''''''''
Fedora 17 ships with Python 3.2 and 2.7, but OpenJPEG is only at version 1.4,
@ -152,20 +149,21 @@ Windows
-------
The only configuration I've tested is Python(xy), which uses Python 2.7.
Python(xy) already comes with numpy, but you will have to install pip and then
contextlib2 as well. This configuration assumes you've installed OpenJPEG
1.5.1.
contextlib2 and mock as well. Both 1.5.1 and the svn development versions of
openjpeg work.
'''''''
Testing
'''''''
If you wish to run the tests (strongly suggested :-), you can either run them
If you wish to run the tests (strongly recommended :-), you can either run them
from within python as follows ... ::
>>> import glymur
>>> glymur.runtests()
or from the unix command line. ::
or from the command line. ::
$ cd /to/where/you/unpacked/glymur
$ python -m unittest discover

View file

@ -27,8 +27,8 @@ about OpenJPEG, please consult http://www.openjpeg.org.
If you use MacPorts on the mac or if you have a sufficiently recent version of
Linux, your package manager should already provide you with at least version
1.5.1 of OpenJPEG, which means that glymur can be installed ready to read JPEG
2000 images. If you use windows, I suggest using the 1.5.1 windows installer provided
to you by the OpenJPEG folks at
2000 images. If you use windows, I suggest using the 1.5.1 windows installer
provided to you by the OpenJPEG folks at
https://code.google.com/p/openjpeg/downloads/list .
Glymur Installation
@ -56,5 +56,5 @@ You can run the tests from within python as follows::
>>> glymur.runtests()
Many tests are currently skipped; in fact most of them are skipped if you
are relying on OpenJPEG 1.5.1. But the important thing is whether or not any
tests fail.
are relying on OpenJPEG 1.5.1. But the important thing, though, is whether or
not any tests fail.

View file

@ -17,8 +17,8 @@ def nemo():
file : str
Platform-independent path to nemo.jp2.
"""
file = pkg_resources.resource_filename(__name__, "nemo.jp2")
return file
filename = pkg_resources.resource_filename(__name__, "nemo.jp2")
return filename
def goodstuff():
@ -29,5 +29,5 @@ def goodstuff():
file : str
Platform-independent path to goodstuff.j2k.
"""
file = pkg_resources.resource_filename(__name__, "goodstuff.j2k")
return file
filename = pkg_resources.resource_filename(__name__, "goodstuff.j2k")
return filename

View file

@ -38,11 +38,13 @@ _METHOD_DISPLAY = {
ANY_ICC_PROFILE: 'any ICC profile',
VENDOR_COLOR_METHOD: 'vendor color method'}
_ = {1: 'accurately represents correct colorspace definition',
2: 'approximates correct colorspace definition, exceptional quality',
3: 'approximates correct colorspace definition, reasonable quality',
4: 'approximates correct colorspace definition, poor quality'}
_approximation_display = _
_APPROX_DISPLAY = {1: 'accurately represents correct colorspace definition',
2: 'approximates correct colorspace definition, '
+ 'exceptional quality',
3: 'approximates correct colorspace definition, '
+ 'reasonable quality',
4: 'approximates correct colorspace definition, '
+ 'poor quality'}
class Jp2kBox(object):
@ -66,12 +68,15 @@ class Jp2kBox(object):
self.offset = offset
self.longname = longname
# should never be used except for last box in file.
self._file_size = -1
def __str__(self):
msg = "{0} Box ({1})".format(self.longname, self.box_id)
msg += " @ ({0}, {1})".format(self.offset, self.length)
return msg
def write(self, fptr):
def write(self, _):
"""Must be implemented in a subclass.
"""
msg = "Not supported for {0} box.".format(self.longname)
@ -120,7 +125,7 @@ class Jp2kBox(object):
# Call the proper parser for the given box with ID "T".
try:
box = _BOX_WITH_ID[box_id]._parse(fptr, start, num_bytes)
box = _BOX_WITH_ID[box_id].parse(fptr, start, num_bytes)
except KeyError:
msg = 'Unrecognized box ({0}) encountered.'.format(box_id)
warnings.warn(msg)
@ -177,6 +182,7 @@ class ColourSpecificationBox(Jp2kBox):
ICC profile header according to ICC profile specification. If
colorspace is not None, then icc_profile must be empty.
"""
def __init__(self, method=ENUMERATED_COLORSPACE, precedence=0,
approximation=0, colorspace=None, icc_profile=None,
length=0, offset=-1):
@ -203,8 +209,9 @@ class ColourSpecificationBox(Jp2kBox):
msg += '\n Precedence: {0}'.format(self.precedence)
if self.approximation is not 0:
dispvalue = _approximation_display[self.approximation]
dispvalue = _APPROX_DISPLAY[self.approximation]
msg += '\n Approximation: {0}'.format(dispvalue)
if self.colorspace is not None:
dispvalue = _COLORSPACE_MAP_DISPLAY[self.colorspace]
msg += '\n Colorspace: {0}'.format(dispvalue)
@ -240,7 +247,7 @@ class ColourSpecificationBox(Jp2kBox):
fptr.write(read_buffer)
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse JPEG 2000 color specification box.
Parameters
@ -468,7 +475,7 @@ class ChannelDefinitionBox(Jp2kBox):
self.association[j]))
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse component definition box.
Parameters
@ -542,7 +549,7 @@ class ComponentMappingBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse component mapping box.
Parameters
@ -607,7 +614,7 @@ class ContiguousCodestreamBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset=0, length=0):
def parse(fptr, offset=0, length=0):
"""Parse a codestream box.
Parameters
@ -685,7 +692,7 @@ class FileTypeBox(Jp2kBox):
fptr.write(item.encode())
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse JPEG 2000 file type box.
Parameters
@ -812,7 +819,7 @@ class ImageHeaderBox(Jp2kBox):
fptr.write(read_buffer)
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse JPEG 2000 image header box.
Parameters
@ -883,7 +890,7 @@ class AssociationBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse association box.
Parameters
@ -956,7 +963,7 @@ class JP2HeaderBox(Jp2kBox):
fptr.seek(end_pos)
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse JPEG 2000 header box.
Parameters
@ -1017,7 +1024,7 @@ class JPEG2000SignatureBox(Jp2kBox):
fptr.write(struct.pack('>BBBB', *self.signature))
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse JPEG 2000 signature box.
Parameters
@ -1073,7 +1080,7 @@ class PaletteBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse palette box.
Parameters
@ -1220,6 +1227,8 @@ _READER_REQUIREMENTS_DISPLAY = {
+ 'requirements in M.9.2.3',
73: 'YPbPr(1125/60) enumerated colourspace',
74: 'YPbPr(1250/50) enumerated colourspace'}
class ReaderRequirementsBox(Jp2kBox):
"""Container for reader requirements box information.
@ -1276,7 +1285,7 @@ class ReaderRequirementsBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse reader requirements box.
Parameters
@ -1380,7 +1389,7 @@ class ResolutionBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse Resolution box.
Parameters
@ -1436,7 +1445,7 @@ class CaptureResolutionBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse Resolution box.
Parameters
@ -1493,7 +1502,7 @@ class DisplayResolutionBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse Resolution box.
Parameters
@ -1548,7 +1557,7 @@ class LabelBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse Label box.
Parameters
@ -1633,7 +1642,7 @@ class XMLBox(Jp2kBox):
fptr.write(read_buffer)
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse XML box.
Parameters
@ -1697,7 +1706,7 @@ class UUIDListBox(Jp2kBox):
return(msg)
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse UUIDList box.
Parameters
@ -1760,7 +1769,7 @@ class UUIDInfoBox(Jp2kBox):
return(msg)
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse UUIDInfo super box.
Parameters
@ -1828,7 +1837,7 @@ class DataEntryURLBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse Data Entry URL box.
Parameters
@ -1949,7 +1958,7 @@ class UUIDBox(Jp2kBox):
return msg
@staticmethod
def _parse(fptr, offset, length):
def parse(fptr, offset, length):
"""Parse UUID box.
Parameters

View file

@ -98,7 +98,7 @@ class Jp2k(Jp2kBox):
# Parse the file for JP2/JPX contents only if we are reading it.
if mode == 'rb':
self._parse()
self.parse()
def __str__(self):
metadata = ['File: ' + os.path.basename(self.filename)]
@ -110,7 +110,7 @@ class Jp2k(Jp2kBox):
metadata.append(str(codestream))
return '\n'.join(metadata)
def _parse(self):
def parse(self):
"""Parses the JPEG 2000 file.
Raises
@ -425,7 +425,7 @@ class Jp2k(Jp2kBox):
_opj2.destroy_codec(codec)
_opj2.image_destroy(image)
self._parse()
self.parse()
def wrap(self, filename, boxes=None):
"""Write the codestream back out to file, wrapped in new JP2 jacket.

View file

@ -10,8 +10,10 @@ import warnings
import sys
if sys.hexversion <= 0x03000000:
from ConfigParser import SafeConfigParser as ConfigParser
from ConfigParser import NoOptionError
else:
from configparser import ConfigParser
from configparser import NoOptionError
def glymurrc_fname():
@ -28,7 +30,6 @@ def glymurrc_fname():
if os.path.exists(fname):
return fname
# Either GLYMURCONFIGDIR/glymurrc or $HOME/.glymur/glymurrc
confdir = get_configdir()
if confdir is not None:
fname = os.path.join(confdir, 'glymurrc')
@ -39,10 +40,12 @@ def glymurrc_fname():
return None
def get_openjpeg_config():
""" Try to find openjpeg library on the system path first.
def load_openjpeg(libopenjpeg_path):
"""Load the openjpeg library, falling back on defaults if necessary.
"""
libopenjpeg_path = find_library('openjpeg')
if libopenjpeg_path is None:
# Let ctypes try to find it.
libopenjpeg_path = find_library('openjpeg')
# If we could not find it, then look in some likely locations.
if libopenjpeg_path is None:
@ -74,19 +77,34 @@ def get_openjpeg_config():
return openjpeg_lib
def get_openjp2_config():
def read_config_file():
"""
We expect to not find openjp2 on the system path since the only version
that we currently care about is still in the svn trunk at openjpeg.org.
We must use a configuration file that the user must write.
"""
lib = {'openjp2': None, 'openjpeg': None}
filename = glymurrc_fname()
if filename is not None:
# Read the configuration file for the library location.
parser = ConfigParser()
parser.read(filename)
libopenjp2_path = parser.get('library', 'openjp2')
else:
try:
lib['openjp2'] = parser.get('library', 'openjp2')
except NoOptionError:
pass
try:
lib['openjpeg'] = parser.get('library', 'openjpeg')
except NoOptionError:
pass
return lib
def load_openjp2(libopenjp2_path):
"""Load the openjp2 library, falling back on defaults if necessary.
"""
if libopenjp2_path is None:
# No help from the config file, try to find it ourselves.
libopenjp2_path = find_library('openjp2')
@ -98,20 +116,22 @@ def get_openjp2_config():
openjp2_lib = ctypes.windll.LoadLibrary(libopenjp2_path)
else:
openjp2_lib = ctypes.CDLL(libopenjp2_path)
except OSError:
except (TypeError, OSError):
msg = '"Library {0}" could not be loaded. Operating in degraded mode.'
msg = msg.format(libopenjp2_path)
warnings.warn(msg, UserWarning)
openjp2_lib = None
return openjp2_lib
def glymur_config():
"""Try to ascertain locations of openjp2, openjpeg libraries.
"""
openjp2_lib = get_openjp2_config()
openjpeg_lib = get_openjpeg_config()
return openjp2_lib, openjpeg_lib
libs = read_config_file()
libopenjp2_handle = load_openjp2(libs['openjp2'])
libopenjpeg_handle = load_openjpeg(libs['openjpeg'])
return libopenjp2_handle, libopenjpeg_handle
def get_configdir():

View file

@ -1,3 +1,4 @@
#pylint: disable-all
import doctest
import os
import pkg_resources
@ -12,6 +13,7 @@ import numpy as np
import glymur
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
@unittest.skipIf(glymur.lib._openjp2.OPENJP2 is None,
"Missing openjp2 library.")
class TestOpenJP2(unittest.TestCase):

View file

@ -1,8 +1,10 @@
#pylint: disable-all
import ctypes
import unittest
import glymur
@unittest.skipIf(glymur.lib._openjpeg.OPENJPEG is None,
"Missing openjpeg library.")
class TestOpenJPEG(unittest.TestCase):
@ -35,4 +37,3 @@ class TestOpenJPEG(unittest.TestCase):
self.assertEqual(dp.jpwl_max_tiles, 0)
self.assertEqual(dp.cp_limit_decoding, 0)
self.assertEqual(dp.flags, 0)

View file

@ -3,19 +3,19 @@ import sys
import numpy as np
def mse(A, B):
def mse(amat, bmat):
"""Mean Square Error"""
diff = A.astype(np.double) - B.astype(np.double)
#e = np.sqrt(np.mean(diff**2))
e = np.mean(diff**2)
return e
diff = amat.astype(np.double) - bmat.astype(np.double)
err = np.mean(diff**2)
return err
def peak_tolerance(A, B):
def peak_tolerance(amat, bmat):
"""Peak Tolerance"""
diff = np.abs(A.astype(np.double) - B.astype(np.double))
p = diff.max()
return p
diff = np.abs(amat.astype(np.double) - bmat.astype(np.double))
ptol = diff.max()
return ptol
def read_pgx(pgx_file):
@ -28,42 +28,42 @@ def read_pgx(pgx_file):
PG%[ \t]%c%c%[ \t+-]%d%[ \t]%d%[ \t]%d"
"""
header = ''
with open(pgx_file, 'rb') as fp:
with open(pgx_file, 'rb') as fptr:
while True:
x = fp.read(1)
if x[0] == 10 or x == '\n':
pos = fp.tell()
char = fptr.read(1)
if char[0] == 10 or char == '\n':
pos = fptr.tell()
break
else:
if sys.hexversion < 0x03000000:
header += x
header += char
else:
header += chr(x[0])
header += chr(char[0])
header = header.rstrip()
n = re.split('\s', header)
tokens = re.split('\s', header)
if (n[1][0] == 'M') and (sys.byteorder == 'little'):
if (tokens[1][0] == 'M') and (sys.byteorder == 'little'):
swapbytes = True
elif (n[1][0] == 'L') and (sys.byteorder == 'big'):
elif (tokens[1][0] == 'L') and (sys.byteorder == 'big'):
swapbytes = True
else:
swapbytes = False
if (len(n) == 6):
bitdepth = int(n[3])
if (len(tokens) == 6):
bitdepth = int(tokens[3])
signed = bitdepth < 0
if signed:
bitdepth = -1 * bitdepth
nrows = int(n[5])
ncols = int(n[4])
nrows = int(tokens[5])
ncols = int(tokens[4])
else:
bitdepth = int(n[2])
bitdepth = int(tokens[2])
signed = bitdepth < 0
if signed:
bitdepth = -1 * bitdepth
nrows = int(n[4])
ncols = int(n[3])
nrows = int(tokens[4])
ncols = int(tokens[3])
if signed:
if bitdepth <= 8:
@ -84,10 +84,8 @@ def read_pgx(pgx_file):
# Reopen the file in binary mode and seek to the start of the binary
# data
with open(pgx_file, 'rb') as fp:
fp.seek(pos)
data = np.fromfile(file=fp, dtype=dtype).reshape(shape)
with open(pgx_file, 'rb') as fptr:
fptr.seek(pos)
data = np.fromfile(file=fptr, dtype=dtype).reshape(shape)
return(data.byteswap(swapbytes))

View file

@ -1,3 +1,4 @@
#pylint: disable-all
import os
import pkg_resources
import re
@ -29,6 +30,7 @@ class TestCallbacks(unittest.TestCase):
# Restore stdout.
sys.stdout = self.stdout
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_info_callback_on_write(self):
# Verify the messages printed when writing an image in verbose mode.
j = glymur.Jp2k(self.jp2file)
@ -96,9 +98,12 @@ class TestCallbacks15(unittest.TestCase):
actual = sys.stdout.getvalue().strip()
regex = re.compile(r"""\[INFO\]\stile\s1\sof\s1\s+
\[INFO\]\s-\stiers-1\stook\s[0-9]+\.[0-9]+\ss\s+
\[INFO\]\s-\sdwt\stook\s[0-9]+\.[0-9]+\ss\s+
\[INFO\]\s-\stile\sdecoded\sin\s[0-9]+\.[0-9]+\ss""",
\[INFO\]\s-\stiers-1\stook\s
[0-9]+\.[0-9]+\ss\s+
\[INFO\]\s-\sdwt\stook\s
(-){0,1}[0-9]+\.[0-9]+\ss\s+
\[INFO\]\s-\stile\sdecoded\sin\s
[0-9]+\.[0-9]+\ss""",
re.VERBOSE)
if sys.hexversion <= 0x03020000:
self.assertRegexpMatches(actual, regex)
@ -106,6 +111,5 @@ class TestCallbacks15(unittest.TestCase):
self.assertRegex(actual, regex)
if __name__ == "__main__":
unittest.main()

View file

@ -1,3 +1,4 @@
#pylint: disable-all
import os
import struct
import sys
@ -29,6 +30,7 @@ class TestCodestream(unittest.TestCase):
def tearDown(self):
pass
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_reserved_marker_segment(self):
# Some marker segments were reserved in FCD15444-1. Since that
# standard is old, some of them may have come into use.
@ -58,6 +60,7 @@ class TestCodestream(unittest.TestCase):
self.assertEqual(c.segment[2].length, 3)
self.assertEqual(c.segment[2]._data, b'\x00')
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
@unittest.skipIf(sys.hexversion < 0x03020000,
"Uses features introduced in 3.2.")
def test_unknown_marker_segment(self):

View file

@ -1,6 +1,7 @@
"""These tests are for edge cases where OPENJPEG does not exist, but
"""These tests are for edge cases where OPENJPEG does not exist, but
OPENJP2 may be present in some form or other.
"""
#pylint: disable-all
import imp
import os

View file

@ -1,3 +1,4 @@
#pylint: disable-all
import datetime
import os
import struct

View file

@ -1,3 +1,4 @@
#pylint: disable-all
import doctest
import os
import tempfile
@ -14,10 +15,14 @@ from glymur.jp2box import *
# Doc tests should be run as well.
def load_tests(loader, tests, ignore):
if os.name == "nt":
# Can't do it on windows, temporary file issue.
return tests
tests.addTests(doctest.DocTestSuite('glymur.jp2box'))
return tests
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
@unittest.skipIf(glymur.lib.openjp2.OPENJP2 is None,
"Missing openjp2 library.")
class TestChannelDefinition(unittest.TestCase):
@ -232,6 +237,7 @@ class TestChannelDefinition(unittest.TestCase):
association=[1, 2, 3])
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
class TestXML(unittest.TestCase):
def setUp(self):
@ -291,7 +297,7 @@ class TestXML(unittest.TestCase):
with self.assertRaises((IOError, OSError)) as ce:
xmlb = glymur.jp2box.XMLBox(filename=self.xmlfile, xml=xml_object)
@unittest.skipIf(os.name == "nt",
@unittest.skipIf(os.name == "nt",
"Problems using NamedTemporaryFile on windows.")
def test_basic_xml(self):
# Should be able to write an XMLBox.
@ -313,7 +319,7 @@ class TestXML(unittest.TestCase):
self.assertEqual(ET.tostring(jp2.box[3].xml),
b'<data>0</data>')
@unittest.skipIf(os.name == "nt",
@unittest.skipIf(os.name == "nt",
"Problems using NamedTemporaryFile on windows.")
def test_xml_from_file(self):
j2k = Jp2k(self.j2kfile)
@ -359,7 +365,7 @@ class TestColourSpecificationBox(unittest.TestCase):
def tearDown(self):
pass
@unittest.skipIf(os.name == "nt",
@unittest.skipIf(os.name == "nt",
"Problems using NamedTemporaryFile on windows.")
def test_color_specification_box_with_out_enumerated_colorspace(self):
j2k = Jp2k(self.j2kfile)
@ -370,6 +376,7 @@ class TestColourSpecificationBox(unittest.TestCase):
with self.assertRaises(NotImplementedError):
j2k.wrap(tfile.name, boxes=boxes)
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_missing_colr_box(self):
j2k = Jp2k(self.j2kfile)
boxes = [self.jP, self.ftyp, self.jp2h, self.jp2c]
@ -501,12 +508,14 @@ class TestJp2Boxes(unittest.TestCase):
self.assertEqual(jp2.box[2].box[1].colorspace, glymur.core.SRGB)
self.assertIsNone(jp2.box[2].box[1].icc_profile)
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_wrap(self):
j2k = Jp2k(self.j2kfile)
with tempfile.NamedTemporaryFile(suffix=".jp2") as tfile:
j2k.wrap(tfile.name)
self.verify_wrapped_raw(tfile.name)
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_wrap_jp2(self):
j2k = Jp2k(self.j2kfile)
with tempfile.NamedTemporaryFile(suffix=".jp2") as tfile:
@ -514,6 +523,7 @@ class TestJp2Boxes(unittest.TestCase):
boxes = [box.box_id for box in jp2.box]
self.assertEqual(boxes, ['jP ', 'ftyp', 'jp2h', 'jp2c'])
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_default_layout_but_with_specified_boxes(self):
j2k = Jp2k(self.j2kfile)
boxes = [JPEG2000SignatureBox(),
@ -532,6 +542,7 @@ class TestJp2Boxes(unittest.TestCase):
j2k.wrap(tfile.name, boxes=boxes)
self.verify_wrapped_raw(tfile.name)
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_image_header_box_not_first_in_jp2_header(self):
# The specification says that ihdr must be the first box in jp2h.
j2k = Jp2k(self.j2kfile)
@ -551,6 +562,7 @@ class TestJp2Boxes(unittest.TestCase):
with self.assertRaises(IOError):
j2k.wrap(tfile.name, boxes=boxes)
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_first_2_boxes_not_jP_and_ftyp(self):
j2k = Jp2k(self.j2kfile)
c = j2k.get_codestream()
@ -571,6 +583,7 @@ class TestJp2Boxes(unittest.TestCase):
with self.assertRaises(IOError):
j2k.wrap(tfile.name, boxes=boxes)
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_jp2h_not_preceeding_jp2c(self):
j2k = Jp2k(self.j2kfile)
c = j2k.get_codestream()
@ -591,6 +604,7 @@ class TestJp2Boxes(unittest.TestCase):
with self.assertRaises(IOError):
j2k.wrap(tfile.name, boxes=boxes)
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_missing_codestream(self):
j2k = Jp2k(self.j2kfile)
c = j2k.get_codestream()

View file

@ -1,7 +1,5 @@
import contextlib
import ctypes
# pylint: disable-all
import doctest
import imp
import os
import re
import shutil
@ -33,14 +31,18 @@ except:
# Doc tests should be run as well.
def load_tests(loader, tests, ignore):
if os.name == "nt":
# Can't do it on windows, temporary file issue.
return tests
if glymur.lib.openjp2.OPENJP2 is not None:
tests.addTests(doctest.DocTestSuite('glymur.jp2k'))
return tests
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
@unittest.skipIf(glymur.lib.openjp2.OPENJP2 is None,
"Missing openjp2 library.")
class TestJp2k(unittest.TestCase):
class TestJp2kBadXmlFile(unittest.TestCase):
@classmethod
def setUpClass(cls):
@ -88,14 +90,6 @@ class TestJp2k(unittest.TestCase):
with self.assertWarns(UserWarning) as cw:
jp2k = Jp2k(self._bad_xml_file)
def test_rlevel_max(self):
# Verify that rlevel=-1 gets us the lowest resolution image
j = Jp2k(self.j2kfile)
thumbnail1 = j.read(rlevel=-1)
thumbnail2 = j.read(rlevel=5)
np.testing.assert_array_equal(thumbnail1, thumbnail2)
self.assertEqual(thumbnail1.shape, (25, 15, 3))
def test_invalid_xml_box(self):
# Should be able to recover from xml box with bad xml.
with warnings.catch_warnings():
@ -107,6 +101,26 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(jp2k.box[3].length, 28)
self.assertIsNone(jp2k.box[3].xml)
@unittest.skipIf(glymur.lib.openjp2.OPENJP2 is None,
"Missing openjp2 library.")
class TestJp2k(unittest.TestCase):
def setUp(self):
self.jp2file = glymur.data.nemo()
self.j2kfile = glymur.data.goodstuff()
def tearDown(self):
pass
def test_rlevel_max(self):
# Verify that rlevel=-1 gets us the lowest resolution image
j = Jp2k(self.j2kfile)
thumbnail1 = j.read(rlevel=-1)
thumbnail2 = j.read(rlevel=5)
np.testing.assert_array_equal(thumbnail1, thumbnail2)
self.assertEqual(thumbnail1.shape, (25, 15, 3))
def test_bad_area_parameter(self):
# Verify that we error out appropriately if given a bad area parameter.
j = Jp2k(self.jp2file)
@ -143,6 +157,7 @@ class TestJp2k(unittest.TestCase):
filename = 'this file does not actually exist on the file system.'
jp2k = Jp2k(filename)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_write_srgb_without_mct(self):
j2k = Jp2k(self.j2kfile)
expdata = j2k.read()
@ -155,6 +170,7 @@ class TestJp2k(unittest.TestCase):
c = ofile.get_codestream()
self.assertEqual(c.segment[2].spcod[3], 0) # no mct
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_write_grayscale_with_mct(self):
# MCT usage makes no sense for grayscale images.
j2k = Jp2k(self.j2kfile)
@ -164,6 +180,7 @@ class TestJp2k(unittest.TestCase):
with self.assertRaises(IOError):
ofile.write(expdata[:, :, 0], mct=True)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_write_cprl(self):
# Issue 17
j = Jp2k(self.jp2file)
@ -244,6 +261,7 @@ class TestJp2k(unittest.TestCase):
jp2k = Jp2k(filename)
self.assertEqual(len(jp2k.box), 0)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_64bit_XL_field(self):
# Verify that boxes with the XL field are properly read.
# Don't have such a file on hand, so we create one. Copy our example
@ -276,6 +294,7 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(jp2k.box[5].offset, 3127)
self.assertEqual(jp2k.box[5].length, 1133427 + 8)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_L_is_zero(self):
# Verify that boxes with the L field as zero are correctly read.
# This should only happen in the last box of a JPEG 2000 file.
@ -331,6 +350,7 @@ class TestJp2k(unittest.TestCase):
j = Jp2k(filename)
self.assertEqual(j.box, [])
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_code_block_height_different_than_width(self):
# Verify that we can set a code block size where height does not equal
# width.
@ -346,6 +366,7 @@ class TestJp2k(unittest.TestCase):
# Code block size is reported as XY in the codestream.
self.assertEqual(tuple(c.segment[2].spcod[5:7]), (3, 2))
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_negative_too_many_dimensions(self):
# OpenJP2 only allows 2D or 3D images.
with tempfile.NamedTemporaryFile(suffix='.j2k') as tfile:
@ -354,6 +375,7 @@ class TestJp2k(unittest.TestCase):
data = np.zeros((128, 128, 2, 2), dtype=np.uint8)
j.write(data)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_unrecognized_jp2_colorspace(self):
# We only allow RGB and GRAYSCALE.
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
@ -362,6 +384,7 @@ class TestJp2k(unittest.TestCase):
data = np.zeros((128, 128, 3), dtype=np.uint8)
j.write(data, colorspace='cmyk')
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_2D_rgb(self):
# RGB must have at least 3 components.
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
@ -370,6 +393,7 @@ class TestJp2k(unittest.TestCase):
data = np.zeros((128, 128, 2), dtype=np.uint8)
j.write(data, colorspace='rgb')
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_colorspace_with_j2k(self):
# Specifying a colorspace with J2K does not make sense.
with tempfile.NamedTemporaryFile(suffix='.j2k') as tfile:
@ -378,6 +402,7 @@ class TestJp2k(unittest.TestCase):
data = np.zeros((128, 128, 3), dtype=np.uint8)
j.write(data, colorspace='rgb')
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_specify_rgb(self):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
j = Jp2k(tfile.name, 'wb')
@ -385,6 +410,7 @@ class TestJp2k(unittest.TestCase):
j.write(data, colorspace='rgb')
self.assertEqual(j.box[2].box[1].colorspace, glymur.core.SRGB)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_specify_gray(self):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
j = Jp2k(tfile.name, 'wb')
@ -393,6 +419,7 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(j.box[2].box[1].colorspace,
glymur.core.GREYSCALE)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_specify_grey(self):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
j = Jp2k(tfile.name, 'wb')
@ -401,6 +428,7 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(j.box[2].box[1].colorspace,
glymur.core.GREYSCALE)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_grey_with_extra_component(self):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
j = Jp2k(tfile.name, 'wb')
@ -412,6 +440,7 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(j.box[2].box[1].colorspace,
glymur.core.GREYSCALE)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_grey_with_two_extra_components(self):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
j = Jp2k(tfile.name, 'wb')
@ -423,6 +452,7 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(j.box[2].box[1].colorspace,
glymur.core.GREYSCALE)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_rgb_with_extra_component(self):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
j = Jp2k(tfile.name, 'wb')
@ -441,6 +471,7 @@ class TestJp2k(unittest.TestCase):
data = np.zeros((128, 128, 3), dtype=np.uint8)
j.write(data, colorspace='ycc')
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_uinf_ulst_url_boxes(self):
# Verify that we can read UINF, ULST, and URL boxes. I don't have
# easy access to such a file, and there's no such file in the
@ -497,6 +528,7 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(jp2k.box[3].box[1].flag, (0, 0, 0))
self.assertEqual(jp2k.box[3].box[1].url, 'abcd')
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_xml_box_with_trailing_nulls(self):
# ElementTree does not like trailing null chars after valid XML
# text.
@ -526,6 +558,7 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(jp2k.box[3].offset, 77)
self.assertEqual(jp2k.box[3].length, 36)
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_asoc_label_box(self):
# Construct a fake file with an asoc and a label box, as
# OpenJPEG doesn't have such a file.
@ -572,6 +605,7 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(jasoc.box[3].box[0].label, 'label')
self.assertEqual(jasoc.box[3].box[1].box_id, 'xml ')
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_openjpeg_library_message(self):
# Verify the error message produced by the openjpeg library.
# This will confirm that the error callback mechanism is working.
@ -599,10 +633,10 @@ class TestJp2k(unittest.TestCase):
Invalid\svalues\sfor\scomp\s=\s0\s+
:\sdx=1\sdy=0''', re.VERBOSE)
if sys.hexversion < 0x03020000:
with self.assertRaisesRegexp((IOError, OSError), regexp) as ce:
with self.assertRaisesRegexp((IOError, OSError), regexp):
d = j.read(rlevel=1)
else:
with self.assertRaisesRegex((IOError, OSError), regexp) as ce:
with self.assertRaisesRegex((IOError, OSError), regexp):
d = j.read(rlevel=1)
def test_xmp_attribute(self):
@ -616,6 +650,7 @@ class TestJp2k(unittest.TestCase):
attr_value = elt.attrib['{0}CreatorTool'.format(ns1)]
self.assertEqual(attr_value, 'glymur')
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_unrecognized_exif_tag(self):
# An unrecognized exif tag should be handled gracefully.
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
@ -671,42 +706,48 @@ class TestJp2k15(unittest.TestCase):
pass
def test_bands(self):
# Reading individual bands is an advanced maneuver.
"""Reading individual bands is an advanced maneuver.
"""
jp2k = Jp2k(self.j2kfile)
with self.assertRaises(NotImplementedError) as ce:
jpdata = jp2k.read_bands()
with self.assertRaises(NotImplementedError):
jp2k.read_bands()
def test_area(self):
# Area option not allowed for 1.5.1.
"""Area option not allowed for 1.5.1.
"""
j2k = Jp2k(self.j2kfile)
with self.assertRaises(TypeError) as ce:
d = j2k.read(area=(0, 0, 100, 100))
with self.assertRaises(TypeError):
j2k.read(area=(0, 0, 100, 100))
def test_tile(self):
# tile option not allowed for 1.5.1.
"""tile option not allowed for 1.5.1.
"""
j2k = Jp2k(self.j2kfile)
with self.assertRaises(TypeError) as ce:
d = j2k.read(tile=0)
with self.assertRaises(TypeError):
j2k.read(tile=0)
def test_layer(self):
# layer option not allowed for 1.5.1.
"""layer option not allowed for 1.5.1.
"""
j2k = Jp2k(self.j2kfile)
with self.assertRaises(TypeError) as ce:
d = j2k.read(layer=1)
with self.assertRaises(TypeError):
j2k.read(layer=1)
def test_basic_jp2(self):
# This test is only useful when openjp2 is not available
# and OPJ_DATA_ROOT is not set. We need at least one
# working JP2 test.
"""This test is only useful when openjp2 is not available
and OPJ_DATA_ROOT is not set. We need at least one
working JP2 test.
"""
j2k = Jp2k(self.jp2file)
d = j2k.read(rlevel=1)
j2k.read(rlevel=1)
def test_basic_j2k(self):
# This test is only useful when openjp2 is not available
# and OPJ_DATA_ROOT is not set. We need at least one
# working J2K test.
"""This test is only useful when openjp2 is not available
and OPJ_DATA_ROOT is not set. We need at least one
working J2K test.
"""
j2k = Jp2k(self.j2kfile)
d = j2k.read()
j2k.read()
if __name__ == "__main__":

View file

@ -2,6 +2,7 @@
The tests defined here roughly correspond to what is in the OpenJPEG test
suite.
"""
#pylint: disable-all
from contextlib import contextmanager
import os
@ -4215,7 +4216,8 @@ class TestSuiteDump(unittest.TestCase):
# Jp2 Header
# Colour specification
self.assertEqual(jp2.box[3].box[1].method, glymur.core.RESTRICTED_ICC_PROFILE) # enumerated
self.assertEqual(jp2.box[3].box[1].method,
glymur.core.RESTRICTED_ICC_PROFILE) # enumerated
self.assertEqual(jp2.box[3].box[1].precedence, 0)
self.assertEqual(jp2.box[3].box[1].approximation, 1) # JPX exact
self.assertEqual(jp2.box[3].box[1].icc_profile['Size'], 546)
@ -4312,7 +4314,8 @@ class TestSuiteDump(unittest.TestCase):
# Jp2 Header
# Colour specification
self.assertEqual(jp2.box[3].box[1].method, glymur.core.RESTRICTED_ICC_PROFILE)
self.assertEqual(jp2.box[3].box[1].method,
glymur.core.RESTRICTED_ICC_PROFILE)
self.assertEqual(jp2.box[3].box[1].precedence, 0)
self.assertEqual(jp2.box[3].box[1].approximation, 1) # JPX exact
self.assertEqual(jp2.box[3].box[1].icc_profile['Size'], 13332)
@ -4362,7 +4365,8 @@ class TestSuiteDump(unittest.TestCase):
# Jp2 Header
# Colour specification
self.assertEqual(jp2.box[2].box[1].method, glymur.core.RESTRICTED_ICC_PROFILE) # enumerated
self.assertEqual(jp2.box[2].box[1].method,
glymur.core.RESTRICTED_ICC_PROFILE) # enumerated
self.assertEqual(jp2.box[2].box[1].precedence, 0)
self.assertEqual(jp2.box[2].box[1].approximation, 1) # JPX exact
self.assertEqual(jp2.box[2].box[1].icc_profile['Size'], 414)
@ -7079,7 +7083,8 @@ class TestSuiteDump(unittest.TestCase):
# Jp2 Header
# Colour specification
self.assertEqual(jp2.box[2].box[1].method, glymur.core.RESTRICTED_ICC_PROFILE) # res icc
self.assertEqual(jp2.box[2].box[1].method,
glymur.core.RESTRICTED_ICC_PROFILE)
self.assertEqual(jp2.box[2].box[1].precedence, 0)
self.assertEqual(jp2.box[2].box[1].approximation, 0) # JP2
self.assertIsNone(jp2.box[2].box[1].icc_profile)

View file

@ -2,6 +2,7 @@
The tests here do not correspond directly to the OpenJPEG test suite, but
seem like logical negative tests to add.
"""
#pylint: disable-all
import os
import sys
import tempfile
@ -71,6 +72,7 @@ class TestSuiteNegative(unittest.TestCase):
def tearDown(self):
pass
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_negative_psnr_with_cratios(self):
# Using psnr with cratios options is not allowed.
# Not an OpenJPEG test, but close.
@ -126,6 +128,7 @@ class TestSuiteNegative(unittest.TestCase):
# the end of SOT.
self.assertEqual(c.segment[-1].marker_id, 'SOD')
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_code_block_dimensions(self):
# opj_compress doesn't allow the dimensions of a codeblock
# to be too small or too big, so neither will we.
@ -154,6 +157,7 @@ class TestSuiteNegative(unittest.TestCase):
with self.assertWarns(UserWarning) as cw:
j = Jp2k(infile)
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_precinct_size_not_multiple_of_two(self):
# Seems like precinct sizes should be powers of two.
ifile = Jp2k(self.j2kfile)
@ -163,6 +167,7 @@ class TestSuiteNegative(unittest.TestCase):
with self.assertRaises(IOError) as ce:
ofile.write(data, psizes=[(13, 13)])
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_codeblock_size_not_multiple_of_two(self):
# Seems like code block sizes should be powers of two.
ifile = Jp2k(self.j2kfile)
@ -172,6 +177,7 @@ class TestSuiteNegative(unittest.TestCase):
with self.assertRaises(IOError) as ce:
ofile.write(data, cbsize=(13, 12))
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_codeblock_size_with_precinct_size(self):
# Seems like code block sizes should never exceed half that of
# precinct size.

View file

@ -2,6 +2,7 @@
The tests defined here roughly correspond to what is in the OpenJPEG test
suite.
"""
#pylint: disable-all
import os
import platform
import sys
@ -57,6 +58,7 @@ def read_image(infile):
return data
@unittest.skipIf(os.name == "nt", "no write support on windows, period")
@unittest.skipIf(glymur.lib.openjp2.OPENJP2 is None,
"Missing openjp2 library.")
@unittest.skipIf(no_read_backend, no_read_backend_msg)

View file

@ -1,3 +1,4 @@
#pylint: disable-all
import os
import pkg_resources
import struct
@ -21,6 +22,7 @@ except:
raise
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
@unittest.skipIf(glymur.lib.openjp2.OPENJP2 is None,
"Missing openjp2 library.")
class TestPrintingNeedsLib(unittest.TestCase):
@ -782,8 +784,7 @@ class TestPrinting(unittest.TestCase):
expected = '\n'.join(lines)
self.assertEqual(actual, expected)
@unittest.skipIf(os.name == "nt",
"Problems using NamedTemporaryFile on windows.")
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
def test_less_common_boxes(self):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
with open(self.jp2file, 'rb') as ifile:

View file

@ -1,22 +1,30 @@
| OS | Python 2.7 | Python 3.3 | Notes |
+------------+------------+------------+----------------------------------+
| Windows | X | | Python(xy) with OpenJPEG 1.5.1. |
| | | | At least 25 tests should pass |
+------------+------------+------------+----------------------------------+
| Mac | X | | MacPorts with both OpenJPEG 1.5.1|
| | | | and OpenJPEG svn. Maximum number|
| | | | of tests should pass. |
+------------+------------+------------+----------------------------------+
| Mac | | X | MacPorts with both OpenJPEG 1.5.1|
| | | | and OpenJPEG svn. Maximum number|
| | | | of tests should pass. |
+------------+------------+------------+----------------------------------+
| Raspberry | X | | Ships with only 1.3. Should |
| | | | error out gracefully. |
+------------+------------+------------+----------------------------------+
| Fedora 17 | X | | Ships with 1.4. Should error out|
| | | | gracefully. |
+------------+------------+------------+----------------------------------+
| Fedora 18 | | X | Ships with 1.5.1. Some tests |
| | | | should pass. |
+------------+------------+------------+----------------------------------+
| OS | Python 2.7 | Python 3.3 | Notes |
+------------+------------+------------+--------------------------------------+
| Windows | X | | Python(xy) with OpenJPEG 1.5.1. At |
| | | | least 155 of 444 tests should pass. |
+------------+------------+------------+--------------------------------------+
| Windows | X | | Python(xy) with OpenJPEG 1.5.1 and |
| | | | OpenJPEG svn. At least 282 of 444 |
| | | | tests should pass. |
+------------+------------+------------+--------------------------------------+
| Mac | X | | MacPorts with both OpenJPEG 1.5.1 |
| | | | and OpenJPEG svn. 370 of 450 tests |
| | | | should pass. |
+------------+------------+------------+--------------------------------------+
| Mac | | X | MacPorts with both OpenJPEG 1.5.1 |
| | | | and OpenJPEG svn. 390 of 450 |
| | | | tests should pass. |
+------------+------------+------------+--------------------------------------+
| Fedora 19 | | X | Ships with 1.5.1. 390 of 450 tests |
| | | | should pass. |
+------------+------------+------------+--------------------------------------+
| Fedora 18 | | X | Ships with 1.5.1. 167 of 445 tests |
| | | | should pass. |
+------------+------------+------------+--------------------------------------+
| Fedora 17 | X | | Ships with 1.4. Should error out |
| | | | gracefully. |
+------------+------------+------------+--------------------------------------+
Pylint on entire package should be at least 0.95.
pep8 should be pass cleanly.
Coverage should exceed 95%.

View file

@ -2,7 +2,7 @@ from setuptools import setup, find_packages
import sys
kwargs = {'name': 'Glymur',
'version': '0.1.10',
'version': '0.2.2',
'description': 'Tools for accessing JPEG2000 files',
'long_description': open('README.md').read(),
'author': 'John Evans',
@ -26,9 +26,10 @@ clssfrs = ["Programming Language :: Python",
"Programming Language :: Python :: 3.3",
"Programming Language :: Python :: Implementation :: CPython",
"License :: OSI Approved :: MIT License",
"Development Status :: 3 - Alpha",
"Development Status :: 5 - Production/Stable",
"Operating System :: MacOS",
"Operating System :: POSIX :: Linux",
"Operating System :: Microsoft :: Windows :: Windows XP",
"Intended Audience :: Science/Research",
"Intended Audience :: Information Technology",
"Topic :: Software Development :: Libraries :: Python Modules"]