Skip to content

Commit 2d2e401

Browse files
authored
Merge pull request #842 from theupdateframework/improve_spec_version_handling
Improve the way specification version is checked in metadata
2 parents a4cf9c9 + 18ef3b4 commit 2d2e401

File tree

4 files changed

+43
-12
lines changed

4 files changed

+43
-12
lines changed

tests/test_updater.py

Lines changed: 23 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -739,8 +739,13 @@ def test_3__update_metadata(self):
739739

740740
def test_3__get_metadata_file(self):
741741

742+
'''
743+
This test focuses on making sure that the updater rejects unknown or
744+
badly-formatted TUF specification version numbers....
745+
'''
746+
742747
valid_tuf_version = tuf.formats.TUF_VERSION_NUMBER
743-
tuf.formats.TUF_VERSION_NUMBER = '2'
748+
tuf.formats.TUF_VERSION_NUMBER = '9.0'
744749

745750
repository = repo_tool.load_repository(self.repository_directory)
746751
repository.timestamp.load_signing_key(self.role_keys['timestamp']['private'])
@@ -757,8 +762,18 @@ def test_3__get_metadata_file(self):
757762
upperbound_filelength, 1)
758763

759764
except tuf.exceptions.NoWorkingMirrorError as e:
765+
# Note that this test provides a piece of metadata which would fail to
766+
# be accepted -- with a different error -- if the specification version
767+
# number were not a problem.
760768
for mirror_error in six.itervalues(e.mirror_errors):
761-
assert isinstance(mirror_error, securesystemslib.exceptions.BadVersionNumberError)
769+
assert isinstance(
770+
mirror_error, tuf.exceptions.UnsupportedSpecificationError)
771+
772+
else:
773+
self.fail(
774+
'Expected a failure to verify metadata when the metadata had a '
775+
'specification version number that was unexpected. '
776+
'No error was raised.')
762777

763778
# Test for an improperly formatted TUF version number.
764779
tuf.formats.TUF_VERSION_NUMBER = 'BAD'
@@ -779,6 +794,12 @@ def test_3__get_metadata_file(self):
779794
for mirror_error in six.itervalues(e.mirror_errors):
780795
assert isinstance(mirror_error, securesystemslib.exceptions.FormatError)
781796

797+
else:
798+
self.fail(
799+
'Expected a failure to verify metadata when the metadata had a '
800+
'specification version number that was not in the correct format. '
801+
'No error was raised.')
802+
782803
# Reset the TUF_VERSION_NUMBER so that subsequent unit tests use the
783804
# expected value.
784805
tuf.formats.TUF_VERSION_NUMBER = valid_tuf_version

tuf/client/updater.py

Lines changed: 9 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -166,11 +166,6 @@
166166
iso8601_logger = logging.getLogger('iso8601')
167167
iso8601_logger.disabled = True
168168

169-
# Metadata includes the specification version number that it follows.
170-
# All downloaded metadata must be equal to our supported major version of 1.
171-
# For example, "1.4.3" and "1.0.0" are supported. "2.0.0" is not supported.
172-
SUPPORTED_MAJOR_VERSION = 1
173-
174169

175170
class MultiRepoUpdater(object):
176171
"""
@@ -1497,11 +1492,15 @@ def _get_metadata_file(self, metadata_role, remote_filename,
14971492
# version number of new metadata equals our expected major version
14981493
# number, the new metadata is safe to parse.
14991494
try:
1500-
spec_version_parsed = metadata_signable['signed']['spec_version'].split('.')
1501-
if int(spec_version_parsed[0]) != SUPPORTED_MAJOR_VERSION:
1502-
raise securesystemslib.exceptions.BadVersionNumberError('Downloaded'
1503-
' metadata that specifies an unsupported spec_version. Supported'
1504-
' major version number: ' + repr(SUPPORTED_MAJOR_VERSION))
1495+
metadata_spec_version = metadata_signable['signed']['spec_version']
1496+
spec_major_version = int(metadata_spec_version.split('.')[0])
1497+
if spec_major_version != tuf.formats.SUPPORTED_MAJOR_VERSION:
1498+
raise tuf.exceptions.UnsupportedSpecificationError(
1499+
'Downloaded metadata that specifies an unsupported '
1500+
'spec_version. This code supports major version number: ' +
1501+
repr(tuf.formats.SUPPORTED_MAJOR_VERSION) + '; however, the '
1502+
'obtained metadata lists version number: ' +
1503+
str(metadata_spec_version))
15051504

15061505
except (ValueError, TypeError):
15071506
raise securesystemslib.exceptions.FormatError('Improperly'

tuf/exceptions.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,12 @@ class Error(Exception):
4040
"""Indicate a generic error."""
4141

4242

43+
class UnsupportedSpecificationError(Error):
44+
"""
45+
Metadata received claims to conform to a version of the specification that is
46+
not supported by this client.
47+
"""
48+
4349
class FormatError(Error):
4450
"""Indicate an error while validating an object's format."""
4551

tuf/formats.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -90,7 +90,12 @@
9090
# TUF specification version. The constant should be updated when the version
9191
# number of the specification changes. All metadata should list this version
9292
# number.
93+
# Metadata includes the specification version number that it follows.
94+
# All downloaded metadata must be equal to our supported major version of 1.
95+
# For example, "1.4.3" and "1.0.0" are supported. "2.0.0" is not supported.
9396
TUF_VERSION_NUMBER = '1.0'
97+
SUPPORTED_MAJOR_VERSION = int(TUF_VERSION_NUMBER.split('.')[0])
98+
9499
SPECIFICATION_VERSION_SCHEMA = SCHEMA.AnyString()
95100

96101
# A datetime in 'YYYY-MM-DDTHH:MM:SSZ' ISO 8601 format. The "Z" zone designator

0 commit comments

Comments
 (0)