Commit graph

4049 commits

Author SHA1 Message Date
Lukas Puehringer
f8fc5e263b Reduce JSON-bias in metadata class model
Clarify that the TUF metadata class model is not bound to a JSON
wireline format by:

- re-wording module, class and method docstrings and code comments
  to add details about custom and default serialization and the
  purpose of from/to_dict methods, and

- removing the 'JsonDict' type annotation -- instead we use
  generic Mapping[str, Any] for method arguments and strict
  Dict[str, Any] as return value as suggested in
  https://docs.python.org/3/library/typing.html#typing.Dict

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-10 09:44:38 +01:00
Lukas Puehringer
aba6ba3f30 Use named argument instead of clarifying comment
Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-10 09:44:38 +01:00
Lukas Puehringer
d823c8fc01 Rename a few variables in tuf.api
- Rename _dict to json_dict to avoid wrong semantics of leading
  underscore. (leading underscore was initially chosen to avoid name
  shadowing)

- Rename 'serializer' argument of type 'SignedSerializer' to
  'signed_serializer', to distinguish from 'serializer' argument of
  type 'MetadataSerializer'.

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-10 09:44:30 +01:00
Lukas Puehringer
aa8225cb07 Mark kwargs in metadata API methods as Optional
Use typing.Optional for optional kwargs that default to None.

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-10 09:44:09 +01:00
Lukas Puehringer
2b4085718b Re-word serialization cyclic import code comments
- Try to clarify purpose and remove unimportant TODO note
- Use pylint block-level control for shorter lines, see
  http://pylint.pycqa.org/en/latest/user_guide/message-control.html#block-disables

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-10 09:44:03 +01:00
Lukas Puehringer
2f57eb8ed7 Add SPDX style license and copyright boilerplate
Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-04 16:26:34 +01:00
Lukas Puehringer
8e9afc96f9 Revert "Move to/from_dict metadata API methods..."
Revert an earlier commit that moved to/from_dict metadata class
model methods to a util module of the serialization sub-package.

We keep to/from_dict methods on the metadata classes because:
- It seems **idiomatic** (see e.g. 3rd-party libaries such as attrs,
pydantic, marshmallow, or built-ins that provide default or
customizable dict representation for higher-level objects).
The idiomatic choice should make usage more intuitive.
- It feels better **structured** when each method is encapsulated
within the corresponding class, which in turn should make
maintaining/modifying/extending the class model easier.
- It allows us to remove function-scope imports (see subsequent
commit).

Caveat:
Now that "the meat" of the sub-packaged JSON serializer is
implemented on the class, it might make it harder to create a
non-dict based serializer by copy-paste-amending the JSON
serializer.

However, the benefits from above seem to outweigh the disadvantage.

See option 5 of ADR0006 for further details (#1270).

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-04 12:46:16 +01:00
Lukas Puehringer
e1be085c3c Move to/from_dict metadata API methods to util
Add tuf.api.serialization.util module with functions to
convert between TUF metadata class model and the corresponding
dictionary representation. These functions replace the
corresponding to/from_dict classmethods.

Configure api/pylintrc to exempt '_type' from protected member
access warning, because the underscore prefix here is only used to
avoid name shadowing.

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-04 12:33:28 +01:00
Lukas Puehringer
240fb547af Use custom errors in serializer.json sub-package
Re-raise all errors that happen during de/serialization as custom
De/SerializationError.

Whilelist 'e', which is idiomatic for error, in api/pylintrc, and
inline exempt broad-except, which are okay if re-raised.

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-04 12:33:28 +01:00
Lukas Puehringer
499f1c858e Adopt serialization sub-package in metadata API
- Rename Metadata methods:
  - to_json_file -> to_file
  - from_json_file -> from_file
- Remove Metadata.from_json/to_json
- Remove Signed.to_canonical_bytes
- Accept optional de/serializer arguments:
  - from_file (default: JSONDeserializer)
  - to_file (default: JSONSerializer)
  - sign, verify (default: CanonicalJSONSerializer)
- inline disable pylint cyclic-import checks

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-04 12:33:18 +01:00
Lukas Puehringer
4a22b4a578 Add concrete de/serializer implementations
Add serializer.json module with implementations to serialize and
deserialize TUF role metadata to and from the JSON wireline format
for transportation, and to serialize the 'signed' part of TUF role
metadata to the OLPC Canonical JSON format for signature generation
and verification.

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-04 10:51:37 +01:00
Lukas Puehringer
3d8cade471 Add metadata serialization sub-package
Add sub-package with 3 abstract base classes to:
- serialize Metadata objects to bytes (transport)
- deserialize Metadata objects from bytes (transport)
- serialize Signed objects to bytes (signatures)

pylint notes:
- configure tox to use api/pylintrc
- configure api/pylintrc to allow classes without public methods
  (default was 2)

Design considerations
---------------------
- Why not implement de/serialization on metadata classes?
  -> See ADR0006.

- Why use separate classes for serialization and deserialization?
  -> Some users might only need either one, e.g. client only needs
     Deserializer. Maybe there are use cases where different
     implementations are used to serialize and deserialize.

- Why use separate classes for Metadata- and Signed-Serialization?
  -> They require different concrete types, i.e. Metadata and
     Signed as parameters, and using these specific types seems to
     make the interface stronger.

- Why are de/serialize methods not class/staticmethods?
  -> In reality we only use classes to namespace and define a
     type annotated interface, thus it would be enough to make the
     methods classmethods. However, to keep the de/serialize
     interface minimal, we move any custom format configuration to
     the constructor. (See e.g. "compact" for JSONSerializer in
     subsequent commit).

Naming considerations
---------------------
- Why de/serialize?
  -> Implies byte stream as input or output to the function, which
     is what our interface needs.
- Why not marshaling?
  -> Synonym for serialize but implies transport, would be okay.
- Why not encoding?
  -> Too abstract and too many connotations (character, a/v).
- Why not parse?
  -> Too abstract and no good opposite terms (unparse, write,
     dump?)

Signed-off-by: Lukas Puehringer <lukas.puehringer@nyu.edu>
2021-03-03 15:09:48 +01:00
Joshua Lock
313511ac62
Merge pull request #1293 from joshuagl/joshuagl/python-three
Begin dropping support for Python 2.7
2021-03-03 10:41:57 +00:00
Joshua Lock
d144141ec7 tests: remove check for python >= 3.6 in test_api
Signed-off-by: Joshua Lock <jlock@vmware.com>
2021-03-03 09:38:39 +00:00
Joshua Lock
13b085712f tests: remove some Python 2 specific tests
Signed-off-by: Joshua Lock <jlock@vmware.com>
2021-03-03 09:38:36 +00:00
Joshua Lock
8ee8e862af updater: remove magic number
Remove the magic number, a whence value of 2 for file.seek(), and instead
use the io.SEEK_END constant from the io module.

Signed-off-by: Joshua Lock <jlock@vmware.com>
2021-03-03 09:37:21 +00:00
Joshua Lock
16bd3c2358 Remove Python 2.7 from GitHub CI configuration
- Drop Python 2.7 from GitHub Actions workflows. Note: There is likely
  additional cleanup that can be done to the workflow now we no longer
  care about supporting Python 2.7.
- No longer tell dependabot to ignore idna updates.

Signed-off-by: Joshua Lock <jlock@vmware.com>
2021-03-03 09:37:21 +00:00
Joshua Lock
58aac6ee12 Update supported Python versions
Remove references to, and handling of, Python 2.7 in our project scaffolding:
- updated python_requires in setup.py to state our intent to support
  Python 3.6 and above (but not Python 4, yet)
- Drop no longer required dependencies in setup.py, and requirements-*.txt
  (further refinement of requirements files will be handled in #1161)
- Remove Python 2.7 from our tox environments

Signed-off-by: Joshua Lock <jlock@vmware.com>
2021-03-03 09:37:21 +00:00
Jussi Kukkonen
ab1520e2a7
Merge pull request #1250 from sechkova/fetcher
Abstract out the network IO
2021-03-03 09:39:25 +02:00
lukpueh
8308f85652
Merge pull request #1292 from MVrachev/patch-1
Bump securesystemslib to 0.20.0
2021-02-26 16:59:00 +01:00
Martin Vrachev
be2eba8329 Bump securesystemslib to 0.20.0
https://github.com/secure-systems-lab/securesystemslib/releases/tag/v0.20.0
https://pypi.org/project/securesystemslib/0.20.0/

Signed-off-by: Martin Vrachev <mvrachev@vmware.com>
2021-02-26 17:48:05 +02:00
Joshua Lock
60875f912b
Merge pull request #1284 from joshuagl/joshuagl/release-v0.17.0
Prepare v0.17.0 release
2021-02-25 11:35:07 +00:00
Joshua Lock
76c0a54e75 Prepare v0.17.0 release
Signed-off-by: Joshua Lock <jlock@vmware.com>
2021-02-25 10:49:12 +00:00
Teodora Sechkova
93c6573008
Apply the new code style to fetcher docstrings
Ensure that the newly added files' docstrings adhere to the
recently adopted code style guideline (#1232).

Small code style improvements in comments and imports.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-24 11:41:35 +02:00
Teodora Sechkova
2af63cfd8d
Add host address as a test level constant
Use a common test level constant for defining
the host address forming the download URL on
the client side.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-24 11:41:34 +02:00
Jussi Kukkonen
1677ce0bf8
Move fetcher components to make API boundary clearer
* Move FetcherInterface to tuf/client/ directory: This way everything
  inside that directory is clearly part of client API, and everything
  outside _may_ be more of an implementation detail (settings is still
  an unfortunate exception)
* Keep RequestsFetcher in tuf/ for same reasons: it's just the default
  implementation, not explicitly part of client API

An even clearer division would be if we moved all the client specific
implementation details (download.py, mirrors.py, requests_fetcher.py)
to tuf/client/_internal/ but that's a larger change...

Signed-off-by: Jussi Kukkonen <jkukkonen@vmware.com>
2021-02-24 11:41:34 +02:00
Jussi Kukkonen
e9b294b57c
Add an HTTP error for Fetcher interface
A custom error is required so that updater is able to special case
403 & 404 status codes.

Rewrite the test case a bit to be more readable.

Signed-off-by: Jussi Kukkonen <jkukkonen@vmware.com>
2021-02-24 11:41:34 +02:00
Teodora Sechkova
055280b2af
Close temp file in test_proxy_use.py
Calls to safe_download and unsafe_download leave
a temporary file unclosed.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-24 11:41:33 +02:00
Teodora Sechkova
50b3b19392
Test downloading data in more than one chunk
Add test cases to test_fetcher and test_download that
decrease default chunk size and download data in more
than one chunk.

Small code-style improvements.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-24 11:41:22 +02:00
Teodora Sechkova
29e3419c7a
Apply a defensive data length check in fetch()
Use '>=' as the defensive version of the equality check.

Add a comment describing the need of a chunks() generator.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-23 17:58:42 +02:00
Teodora Sechkova
4f02e1ee4c
Avoid 'localhost' lookup in tests
On Windows (Github Actions) the lookup for 'localhost' takes 1 second.
This is because:
- Windows retries connect() with a timeout
- the machine has IPv6 and IPv4 but Testserver only binds the port on IPv4
- the test clients connect to 'localhost'

Since socketserver.TCPServer does not seem to support IPv6 before 3.8,
just replace 'localhost' with '127.0.0.1' in client-side URLs.

See #1257

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-23 17:58:41 +02:00
Teodora Sechkova
aaddbd3f64
Take out connection time from download speed calculation
- Update RequestsFetcher.fetch to return a generator object.
- Update _download_file to skip connection time when calculating
average download speed.
- Write chunk to temp file before exiting the fetcher loop
on error.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-23 17:58:41 +02:00
Teodora Sechkova
7dc5ef6e1c
Add test_fetcher
Add unit test for requests_fetcher.py

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-23 17:58:40 +02:00
Teodora Sechkova
6c49792776
Update tests importing tuf.download
Pass RequestsFetcher object to tuf.download functions.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-23 17:58:40 +02:00
Teodora Sechkova
33b89a8b99
Add fetcher as parameter to Updater class
Initialize Updater with an external implementation of
FetcherInterface. If not provided, tuf.fetcher.RequestsFetcher
is used.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-23 17:58:40 +02:00
Teodora Sechkova
815fe24f00
Move network IO logic to RequestsFetcher
Abstract the network IO. Move the network operations from
tuf.download to the RequestsFercher class which is TUF's
implementation of the abstract FetcherInterface.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-23 17:58:39 +02:00
Teodora Sechkova
41ffe7aab1
Implement RequestsFetcher class
A concrete implementation of FetcherInterface based on
the Requests library.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-23 17:58:39 +02:00
Teodora Sechkova
84957c87b2
Add FetcherInterface class
The new class FetcherInterface defines an interface for
abstract network download which can be implemented for a
variety of network libraries and configurations.

Signed-off-by: Teodora Sechkova <tsechkova@vmware.com>
2021-02-23 17:58:38 +02:00
lukpueh
74b1549c00
Merge pull request #1288 from CrossStream/sandbox/rzr/review/master
git: Ignore generated files
2021-02-18 13:14:54 +01:00
Philippe Coval
99f12aba90 git: Ignore generated files
This will help packaging effort

Relate-to: https://github.com/theupdateframework/tuf/issues/263
Signed-off-by: Philippe Coval <rzr@users.sf.net>
Change-Id: I60cf8c5fdbe6aa4b44aebadb7f4bc13c546ad159
2021-02-18 11:38:58 +01:00
lukpueh
768f9d8b20
Merge pull request #1286 from theupdateframework/dependabot/pip/cryptography-3.4.6
Bump cryptography from 3.4.5 to 3.4.6
2021-02-17 13:26:19 +01:00
dependabot[bot]
b6fbbef903
Bump cryptography from 3.4.5 to 3.4.6
Bumps [cryptography](https://github.com/pyca/cryptography) from 3.4.5 to 3.4.6.
- [Release notes](https://github.com/pyca/cryptography/releases)
- [Changelog](https://github.com/pyca/cryptography/blob/main/CHANGELOG.rst)
- [Commits](https://github.com/pyca/cryptography/compare/3.4.5...3.4.6)

Signed-off-by: dependabot[bot] <support@github.com>
2021-02-17 10:04:12 +00:00
lukpueh
8101c9e3f4
Merge pull request #1285 from joshuagl/joshuagl/sslib-bump
Bump securesystemslib to 0.19.0
2021-02-17 10:14:26 +01:00
Joshua Lock
9dd2ef6cb1 Bump securesystemslib to 0.19.0
Bump securesystemslib to the recently released 0.19.0
https://pypi.org/project/securesystemslib/0.19.0/
https://github.com/secure-systems-lab/securesystemslib/releases/tag/v0.19.0

Signed-off-by: Joshua Lock <jlock@vmware.com>
2021-02-17 09:05:54 +00:00
Joshua Lock
021803e020
Merge pull request #1283 from jku/build-on-push-to-develop-only
CI: Limit build-on-push to develop branch only
2021-02-16 14:01:58 +00:00
Jussi Kukkonen
7c5416d5c3 CI: Limit build-on-push to develop branch only
Dependabot pushes to main repository and ends up triggering two builds
every time (one for PR, one for push): limit the rule for build-on-push
to apply to develop branch only.

If release branches are used later on they should be added to list here.

Signed-off-by: Jussi Kukkonen <jkukkonen@vmware.com>
2021-02-16 15:40:35 +02:00
Joshua Lock
ac8525a72a
Merge pull request #1280 from theupdateframework/dependabot/pip/cffi-1.14.5
Bump cffi from 1.14.4 to 1.14.5
2021-02-16 13:36:36 +00:00
dependabot[bot]
90ba71ca69
Bump cffi from 1.14.4 to 1.14.5
Bumps [cffi](https://github.com/python-cffi/release-doc) from 1.14.4 to 1.14.5.
- [Release notes](https://github.com/python-cffi/release-doc/releases)
- [Commits](https://github.com/python-cffi/release-doc/commits)

Signed-off-by: dependabot[bot] <support@github.com>
2021-02-16 13:16:07 +00:00
Joshua Lock
70f2f3951c
Merge pull request #1282 from jku/pin-cryptography
Bump Cryptography, pin the py2 version separately
2021-02-16 13:15:19 +00:00
Jussi Kukkonen
b5304e42a4 Bump Cryptography, pin the py2 version separately
On Python3 bump cryptography from 3.3.1 to 3.4.5.

On python2 bump from 3.3.1 to 3.3.2 (3.3-branch is the last branch
with python2 support).

Signed-off-by: Jussi Kukkonen <jkukkonen@vmware.com>
2021-02-16 11:57:45 +02:00