diff --git a/glymur/jp2box.py b/glymur/jp2box.py
index bf88e4d..6f628df 100644
--- a/glymur/jp2box.py
+++ b/glymur/jp2box.py
@@ -2122,6 +2122,7 @@ class UUIDBox(Jp2kBox):
text = raw_data.decode('utf-8')
elt = ET.fromstring(text)
self.data = ET.ElementTree(elt)
+ self._type = 'XMP'
elif the_uuid.bytes == b'JpgTiffExif->JP2':
exif_obj = Exif(raw_data)
ifds = OrderedDict()
@@ -2130,8 +2131,16 @@ class UUIDBox(Jp2kBox):
ifds['GPSInfo'] = exif_obj.exif_gpsinfo
ifds['Iop'] = exif_obj.exif_iop
self.data = ifds
+ self._type = 'Exif'
else:
self.data = raw_data
+ self._type = 'unknown'
+
+ if length == 0:
+ # Need to compute the length.
+ # The length is 8 (L and T fields) + 16 (length of UUID identifier)
+ # + length of uuid data.
+ length = 24 + len(self.data)
self.length = length
self.offset = offset
@@ -2164,6 +2173,16 @@ class UUIDBox(Jp2kBox):
return msg
+ def write(self, fptr):
+ """Write a UUID box box to file.
+ """
+ if self._type != 'XMP':
+ msg = "Only XMP UUID boxes can currently be written."
+ raise NotImplementedError(msg)
+ read_buffer = struct.pack('>I4s', self.length, 'uuid')
+ fptr.write(read_buffer)
+ fptr.write(self.data)
+
@staticmethod
def parse(fptr, offset, length):
"""Parse UUID box.
diff --git a/glymur/jp2k.py b/glymur/jp2k.py
index 1bd36a4..45eaf39 100644
--- a/glymur/jp2k.py
+++ b/glymur/jp2k.py
@@ -514,14 +514,17 @@ class Jp2k(Jp2kBox):
Parameters
----------
box : Jp2Box
- Instance of a JP2 box. Currently only XML boxes are allowed.
+ Instance of a JP2 box. Only UUID and XML boxes can currently be
+ appended.
"""
if self._codec_format == opj2.CODEC_J2K:
msg = "Only JP2 files can currently have boxes appended to them."
raise IOError(msg)
- if box.box_id != 'xml ':
- raise IOError("Only XML boxes can currently be appended.")
+ if not ((box.box_id == 'xml ') or
+ (box.box_id == 'uuid' and box._type == 'XMP')):
+ msg = "Only XML boxes and XMP UUID boxes can currently be appended."
+ raise IOError(msg)
# Check the last box. If the length field is zero, then rewrite
# the length field to reflect the true length of the box.
diff --git a/glymur/test/test_jp2box.py b/glymur/test/test_jp2box.py
index ef62460..ff61bc5 100644
--- a/glymur/test/test_jp2box.py
+++ b/glymur/test/test_jp2box.py
@@ -429,14 +429,14 @@ class TestAppend(unittest.TestCase):
with tempfile.NamedTemporaryFile(suffix=".j2k") as tfile:
shutil.copyfile(self.j2kfile, tfile.name)
- jp2 = Jp2k(tfile.name)
+ j2k = Jp2k(tfile.name)
- # Make a UUID box.
- uuid_instance = uuid.UUID('00000000-0000-0000-0000-000000000000')
- data = b'0123456789'
- uuidbox = glymur.jp2box.UUIDBox(uuid_instance, data)
+ # Make an XML box. XML boxes should always be appendable to jp2
+ # files.
+ the_xml = ET.fromstring('0')
+ xmlbox = glymur.jp2box.XMLBox(xml=the_xml)
with self.assertRaises(IOError):
- jp2.append(uuidbox)
+ j2k.append(xmlbox)
def test_length_field_is_zero(self):
"""L=0 (length field in box header) is handled.
@@ -473,14 +473,14 @@ class TestAppend(unittest.TestCase):
self.assertEqual(ET.tostring(jp2.box[-1].xml.getroot()),
b'0')
- def test_only_xml_allowed_to_append(self):
+ def test_append_allowable_boxes(self):
"""Only XML boxes are allowed to be appended."""
with tempfile.NamedTemporaryFile(suffix=".jp2") as tfile:
shutil.copyfile(self.jp2file, tfile.name)
jp2 = Jp2k(tfile.name)
- # Make a UUID box.
+ # Make a UUID box. Only XMP UUID boxes can currently be appended.
uuid_instance = uuid.UUID('00000000-0000-0000-0000-000000000000')
data = b'0123456789'
uuidbox = glymur.jp2box.UUIDBox(uuid_instance, data)
diff --git a/setup.py b/setup.py
index 89e69f7..b780e4d 100644
--- a/setup.py
+++ b/setup.py
@@ -42,7 +42,7 @@ kwargs['classifiers'] = clssfrs
# Get the version string. Cannot do this by importing glymur!
version_file = os.path.join('glymur', 'version.py')
-with open('glymur/version.py', 'rt') as fptr:
+with open(version_file, 'rt') as fptr:
contents = fptr.read()
match = re.search('version\s*=\s*"(?P\d*.\d*.\d*.*)"\n', contents)
kwargs['version'] = match.group('version')