Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 6 additions & 2 deletions CLIENT-CLI.md
Original file line number Diff line number Diff line change
Expand Up @@ -72,8 +72,12 @@ given targets directory. Client must ensure that metadata is up-to-date before d
Client must use exit code 0 if the download succeeded fully and exit code 1 if any part of
the download failed.

Client may use any filename or directory structure it wants within `TARGET_DIR`: The expectation is that if a
targetpath is downloaded twice it is stored with the same filename (even if the content changed).
Client should support artifact caching: if client is requested to download an artifact that has
already been downloaded (with matching hashes), it should not download the artifact again.

Client may use any filename or directory structure it wants within `TARGET_DIR`: The expectation
is that if an artifact is downloaded twice (because the artifact content changed) it is stored in
`TARGET_DIR` with the same filename.

This command may be called multiple times in a test.

Expand Down
3 changes: 2 additions & 1 deletion clients/python-tuf/python_tuf.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,8 @@ def download_target(
target_info = updater.get_targetinfo(target_name)
if not target_info:
raise RuntimeError(f"{target_name} not found in repository")
updater.download_target(target_info)
if not updater.find_cached_target(target_info):
updater.download_target(target_info)


def main() -> int:
Expand Down
25 changes: 25 additions & 0 deletions tuf_conformance/test_file_download.py
Original file line number Diff line number Diff line change
Expand Up @@ -238,3 +238,28 @@ def test_download_with_unknown_hash_algorithm(
# and only then realize hash cannot be verified
assert client.download_target(init_data, target_path) == 1
assert client.get_downloaded_target_bytes() == []


def test_artifact_cache(client: ClientRunner, server: SimulatorServer) -> None:
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we include the test where the artifact should be downloaded again because the contents changed?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

test_multiple_changes_to_target should handle that along with other cases...

I can see some advantage from having a simple test that would only test what you suggest (instead of a long test that tests multiple things), but it does not seem strictly necessary 🤷

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh no I'm just not aware of what was in there and it was too much work from my phone to go looking. Lgtm.

"""In this test client is asked to download the same artifact twice.
The client is expected return the cached content on the second time.

Artifact caching is not required in the specification: clients
that do not support it can mark this test as expected to fail
"""

init_data, repo = server.new_test(client.test_name)
assert client.init_client(init_data) == 0

# Create a test artifact, add it to the repository
target_path = "target_file.txt"
target_content = b"target file contents"
repo.add_artifact(Targets.type, target_content, target_path)
repo.publish([Targets.type, Snapshot.type, Timestamp.type])

# Client is asked to download artifact twice
assert client.download_target(init_data, target_path) == 0
assert client.download_target(init_data, target_path) == 0

# Expect only one download from repository
assert len(repo.artifact_statistics) == 1
Loading