Skip to content

Commit b8f2205

Browse files
authored
Add tests for hash algorithm support (#175)
* Spec does not clearly state what algorithms should be supported * Test for sha256, sha512 and finally both of them * Test a unknown hash algo as well * Avoid testing unknown + known algo: the expected results is not clear, see #174 If we had a good "optional feature" selection we could use that for the supported algorithms but for now I think xfail works for this case. Signed-off-by: Jussi Kukkonen <[email protected]>
1 parent 2f10292 commit b8f2205

File tree

1 file changed

+65
-1
lines changed

1 file changed

+65
-1
lines changed

tuf_conformance/test_file_download.py

Lines changed: 65 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
1-
from tuf.api.metadata import Targets
1+
import pytest
2+
from tuf.api.metadata import TargetFile, Targets
23

34
from tuf_conformance.client_runner import ClientRunner
5+
from tuf_conformance.repository_simulator import Artifact
46
from tuf_conformance.simulator_server import SimulatorServer
57

68

@@ -169,3 +171,65 @@ def test_multiple_changes_to_target(
169171

170172
# Check that the client did not download the malicious file
171173
assert client.get_downloaded_target_bytes() == expected_downloads
174+
175+
176+
hash_algos = [
177+
["sha256"],
178+
["sha512"],
179+
["sha256", "sha512"],
180+
]
181+
182+
183+
@pytest.mark.parametrize("hashes", hash_algos)
184+
def test_download_with_hash_algorithms(
185+
client: ClientRunner, server: SimulatorServer, hashes: list[str]
186+
) -> None:
187+
"""Test support of hash algorithms. The specification does not require any
188+
specific algorithms, and only mentions sha256.
189+
190+
Clients can use --expected-failures to mark tests that fail because of algorithms
191+
they do not intend to support."""
192+
init_data, repo = server.new_test(client.test_name)
193+
194+
# Create a legitimate test artifact
195+
target_path = "target_file.txt"
196+
target_content = b"target file contents"
197+
198+
# Add target manually and not with repo.add_artifact() so we can choose hashes
199+
target = TargetFile.from_data(target_path, target_content, hashes)
200+
repo.targets.targets[target_path] = target
201+
repo.artifacts[target_path] = Artifact(target_content, target)
202+
203+
assert client.init_client(init_data) == 0
204+
assert client.download_target(init_data, target_path) == 0
205+
206+
# downloading using any of the hashes repository advertized is accepted:
207+
possible_dls = [(target_path, h) for h in target.hashes.values()]
208+
assert len(repo.artifact_statistics) == 1
209+
assert repo.artifact_statistics[0] in possible_dls
210+
assert client.get_downloaded_target_bytes() == [target_content]
211+
212+
213+
def test_download_with_unknown_hash_algorithm(
214+
client: ClientRunner, server: SimulatorServer
215+
) -> None:
216+
"""Use an unknown hash algorithm: client should not accept the artifact"""
217+
init_data, repo = server.new_test(client.test_name)
218+
219+
# Create a legitimate test artifact
220+
target_path = "target_file.txt"
221+
target_content = b"target file contents"
222+
223+
# Add target manually, use a hash algorithm that does not exist
224+
# Use repo.add_artifact() so we can modify hashes
225+
target = TargetFile.from_data(target_path, target_content, ["sha512"])
226+
target.hashes["unknown-hash"] = target.hashes["sha512"]
227+
del target.hashes["sha512"]
228+
repo.targets.targets[target_path] = target
229+
repo.artifacts[target_path] = Artifact(target_content, target)
230+
231+
assert client.init_client(init_data) == 0
232+
# Note that we allow the client to actually download the artifact from repo
233+
# and only then realize hash cannot be verified
234+
assert client.download_target(init_data, target_path) == 1
235+
assert client.get_downloaded_target_bytes() == []

0 commit comments

Comments
 (0)