[Python-modules-commits] [py-macaroon-bakery] 01/04: Import py-macaroon-bakery_1.1.0.orig.tar.gz
Colin Watson
cjwatson at moszumanska.debian.org
Mon Feb 5 16:05:35 UTC 2018
This is an automated email from the git hooks/post-receive script.
cjwatson pushed a commit to branch master
in repository py-macaroon-bakery.
commit 9e4403035a9953c99117083e6373ae3c441a76b5
Author: Colin Watson <cjwatson at debian.org>
Date: Tue Dec 12 15:20:49 2017 +0000
Import py-macaroon-bakery_1.1.0.orig.tar.gz
---
Makefile | 15 +-
docs/conf.py | 2 +-
macaroonbakery/__init__.py | 137 -----------------
macaroonbakery/{utils.py => _utils/__init__.py} | 39 +++--
macaroonbakery/{ => bakery}/__init__.py | 32 ++--
.../{authorizer.py => bakery/_authorizer.py} | 5 +-
macaroonbakery/{bakery.py => bakery/_bakery.py} | 8 +-
macaroonbakery/{checker.py => bakery/_checker.py} | 36 +++--
macaroonbakery/{codec.py => bakery/_codec.py} | 66 ++++----
.../{discharge.py => bakery/_discharge.py} | 48 ++++--
macaroonbakery/{error.py => bakery/_error.py} | 0
.../{identity.py => bakery/_identity.py} | 4 +-
.../{internal => bakery/_internal}/__init__.py | 0
.../{internal => bakery/_internal}/id.proto | 0
.../{internal => bakery/_internal}/id_pb2.py | 0
macaroonbakery/{keys.py => bakery/_keys.py} | 20 ++-
.../{macaroon.py => bakery/_macaroon.py} | 70 +++++----
macaroonbakery/{oven.py => bakery/_oven.py} | 57 ++++---
macaroonbakery/{store.py => bakery/_store.py} | 0
.../{third_party.py => bakery/_third_party.py} | 0
.../{versions.py => bakery/_versions.py} | 0
macaroonbakery/checkers/__init__.py | 18 +--
.../checkers/{auth_context.py => _auth_context.py} | 0
macaroonbakery/checkers/{caveat.py => _caveat.py} | 11 +-
.../checkers/{checkers.py => _checkers.py} | 23 +--
.../checkers/{conditions.py => _conditions.py} | 0
.../checkers/{declared.py => _declared.py} | 12 +-
.../checkers/{namespace.py => _namespace.py} | 4 +-
.../checkers/{operation.py => _operation.py} | 2 +-
macaroonbakery/checkers/{time.py => _time.py} | 14 +-
macaroonbakery/checkers/{utils.py => _utils.py} | 0
macaroonbakery/httpbakery/__init__.py | 12 +-
.../httpbakery/{browser.py => _browser.py} | 17 +-
.../httpbakery/{client.py => _client.py} | 111 +++++++------
.../httpbakery/{discharge.py => _discharge.py} | 7 +-
macaroonbakery/httpbakery/{error.py => _error.py} | 10 +-
.../httpbakery/{interactor.py => _interactor.py} | 9 +-
.../httpbakery/{keyring.py => _keyring.py} | 6 +-
macaroonbakery/httpbakery/agent/__init__.py | 8 +-
.../httpbakery/agent/{agent.py => _agent.py} | 115 +++++++-------
macaroonbakery/tests/common.py | 5 +-
macaroonbakery/tests/test_agent.py | 171 ++++++++-------------
macaroonbakery/tests/test_authorizer.py | 2 +-
macaroonbakery/tests/test_bakery.py | 87 +++++++++--
macaroonbakery/tests/test_checker.py | 34 ++--
macaroonbakery/tests/test_checkers.py | 7 +-
macaroonbakery/tests/test_client.py | 130 +++++++++++++---
macaroonbakery/tests/test_codec.py | 7 +-
macaroonbakery/tests/test_discharge.py | 5 +-
macaroonbakery/tests/test_discharge_all.py | 5 +-
macaroonbakery/tests/test_keyring.py | 16 +-
macaroonbakery/tests/test_macaroon.py | 12 +-
macaroonbakery/tests/test_oven.py | 8 +-
macaroonbakery/tests/test_store.py | 2 +-
macaroonbakery/tests/test_time.py | 19 ++-
macaroonbakery/tests/test_utils.py | 74 +++++++++
setup.py | 2 +-
tox.ini | 2 +-
58 files changed, 832 insertions(+), 674 deletions(-)
diff --git a/Makefile b/Makefile
index 75d0e27..8466ce9 100644
--- a/Makefile
+++ b/Makefile
@@ -33,8 +33,7 @@ endif
.PHONY: check
-check: setup
- @tox -e lint
+check: setup lint
@tox
.PHONY: clean
@@ -54,7 +53,7 @@ clean:
.PHONY: docs
docs: setup
- tox -e docs
+ @tox -e docs
.PHONY: help
help:
@@ -76,7 +75,7 @@ help:
.PHONY: lint
lint: setup
- @$(DEVENV)/bin/flake8 --show-source macaroonbakery --exclude macaroonbakery/internal/id_pb2.py
+ @tox -e lint
.PHONY: release
release: check
@@ -97,3 +96,11 @@ test: setup
@$(DEVENV)/bin/nosetests \
--verbosity 2 --with-coverage --cover-erase \
--cover-package macaroonbakery
+
+.PHONY: isort
+isort:
+ isort \
+ --trailing-comma \
+ --recursive \
+ --multi-line 3 \
+ `find macaroonbakery -name '*.py' | grep -v 'internal/id_pb2\.py'`
diff --git a/docs/conf.py b/docs/conf.py
index a64ec3a..ff5c82e 100755
--- a/docs/conf.py
+++ b/docs/conf.py
@@ -63,7 +63,7 @@ copyright = u'2017, Juju UI Team'
# the built documents.
#
# The short X.Y version and the full version.
-version = release = '0.0.6'
+version = release = '1.1.0'
# The language for content autogenerated by Sphinx. Refer to documentation
# for a list of supported languages.
diff --git a/macaroonbakery/__init__.py b/macaroonbakery/__init__.py
index 6397a19..e69de29 100644
--- a/macaroonbakery/__init__.py
+++ b/macaroonbakery/__init__.py
@@ -1,137 +0,0 @@
-# Copyright 2017 Canonical Ltd.
-# Licensed under the LGPLv3, see LICENCE file for details.
-
-from macaroonbakery.versions import (
- VERSION_0,
- VERSION_1,
- VERSION_2,
- VERSION_3,
- LATEST_VERSION,
-)
-from macaroonbakery.authorizer import (
- ACLAuthorizer,
- Authorizer,
- AuthorizerFunc,
- ClosedAuthorizer,
- EVERYONE,
-)
-from macaroonbakery.codec import (
- decode_caveat,
- encode_caveat,
- encode_uvarint,
-)
-from macaroonbakery.checker import (
- AuthChecker,
- AuthInfo,
- Checker,
- LOGIN_OP,
- Op,
-)
-from macaroonbakery.error import (
- AuthInitError,
- CaveatNotRecognizedError,
- DischargeRequiredError,
- IdentityError,
- PermissionDenied,
- ThirdPartyCaveatCheckFailed,
- ThirdPartyInfoNotFound,
- VerificationError,
-)
-from macaroonbakery.identity import (
- ACLIdentity,
- Identity,
- IdentityClient,
- NoIdentities,
- SimpleIdentity,
-)
-from macaroonbakery.keys import (
- generate_key,
- PrivateKey,
- PublicKey,
-)
-from macaroonbakery.store import (
- MemoryOpsStore,
- MemoryKeyStore,
-)
-from macaroonbakery.third_party import (
- ThirdPartyCaveatInfo,
- ThirdPartyInfo,
- legacy_namespace,
-)
-from macaroonbakery.macaroon import (
- Macaroon,
- MacaroonJSONDecoder,
- MacaroonJSONEncoder,
- ThirdPartyLocator,
- ThirdPartyStore,
- macaroon_version,
-)
-from macaroonbakery.discharge import (
- ThirdPartyCaveatChecker,
- discharge,
- discharge_all,
- local_third_party_caveat,
-)
-from macaroonbakery.oven import (
- Oven,
- canonical_ops,
-)
-from macaroonbakery.bakery import Bakery
-from macaroonbakery.utils import b64decode
-
-__all__ = [
- 'ACLAuthorizer',
- 'ACLIdentity',
- 'AuthChecker',
- 'AuthInfo',
- 'AuthInitError',
- 'Authorizer',
- 'AuthorizerFunc',
- 'VERSION_0',
- 'VERSION_1',
- 'VERSION_2',
- 'VERSION_3',
- 'Bakery',
- 'CaveatNotRecognizedError',
- 'Checker',
- 'ClosedAuthorizer',
- 'DischargeRequiredError',
- 'EVERYONE',
- 'Identity',
- 'IdentityClient',
- 'IdentityError',
- 'LATEST_VERSION',
- 'LOGIN_OP',
- 'Macaroon',
- 'MacaroonJSONDecoder',
- 'MacaroonJSONEncoder',
- 'MemoryKeyStore',
- 'MemoryOpsStore',
- 'NoIdentities',
- 'Op',
- 'Oven',
- 'PermissionDenied',
- 'PrivateKey',
- 'PublicKey',
- 'SimpleIdentity',
- 'ThirdPartyCaveatCheckFailed',
- 'ThirdPartyCaveatChecker',
- 'ThirdPartyCaveatInfo',
- 'ThirdPartyInfo',
- 'ThirdPartyInfoNotFound',
- 'ThirdPartyLocator',
- 'ThirdPartyStore',
- 'VERSION',
- 'VerificationError',
- 'b64decode',
- 'canonical_ops',
- 'decode_caveat',
- 'discharge',
- 'discharge_all',
- 'encode_caveat',
- 'encode_uvarint',
- 'generate_key',
- 'legacy_namespace',
- 'local_third_party_caveat',
- 'macaroon_version',
-]
diff --git a/macaroonbakery/utils.py b/macaroonbakery/_utils/__init__.py
similarity index 80%
rename from macaroonbakery/utils.py
rename to macaroonbakery/_utils/__init__.py
index 43b0bf2..f2779e0 100644
--- a/macaroonbakery/utils.py
+++ b/macaroonbakery/_utils/__init__.py
@@ -1,15 +1,18 @@
# Copyright 2017 Canonical Ltd.
# Licensed under the LGPLv3, see LICENCE file for details.
import base64
+import binascii
import json
import webbrowser
-import six
-import six.moves.http_cookiejar as http_cookiejar
-from six.moves.urllib.parse import urlparse
+from datetime import datetime
+import six
from pymacaroons import Macaroon
from pymacaroons.serializers import json_serializer
+import six.moves.http_cookiejar as http_cookiejar
+from six.moves.urllib.parse import urlparse
+
def to_bytes(s):
'''Return s as a bytes type, using utf-8 encoding if necessary.
@@ -34,6 +37,13 @@ def macaroon_from_dict(json_macaroon):
json_serializer.JsonSerializer())
+def macaroon_to_dict(macaroon):
+ '''Turn macaroon into JSON-serializable dict object
+ @param pymacaroons.Macaroon.
+ '''
+ return json.loads(macaroon.serialize(json_serializer.JsonSerializer()))
+
+
def macaroon_to_json_string(macaroon):
'''Serialize macaroon object to a JSON-encoded string.
@@ -72,14 +82,19 @@ def b64decode(s):
@param s bytes decode
@return bytes decoded
+ @raises ValueError on failure
'''
# add padding if necessary.
s = to_bytes(s)
- s = s + b'=' * (-len(s) % 4)
- if '_' or '-' in s:
- return base64.urlsafe_b64decode(s)
- else:
- return base64.b64decode(s)
+ if not s.endswith(b'='):
+ s = s + b'=' * (-len(s) % 4)
+ try:
+ if '_' or '-' in s:
+ return base64.urlsafe_b64decode(s)
+ else:
+ return base64.b64decode(s)
+ except (TypeError, binascii.Error) as e:
+ raise ValueError(str(e))
def raw_urlsafe_b64encode(b):
@@ -111,17 +126,21 @@ def cookie(
expires=None):
'''Return a new Cookie using a slightly more
friendly API than that provided by six.moves.http_cookiejar
+
@param name The cookie name {str}
@param value The cookie value {str}
@param url The URL path of the cookie {str}
- @param expires The expiry time of the cookie {datetime}
+ @param expires The expiry time of the cookie {datetime}. If provided,
+ it must be a naive timestamp in UTC.
'''
u = urlparse(url)
domain = u.hostname or u.netloc
port = str(u.port) if u.port is not None else None
secure = u.scheme == 'https'
if expires is not None:
- expires = expires.strftime("%s")
+ if expires.tzinfo is not None:
+ raise ValueError('Cookie expiration must be a naive datetime')
+ expires = (expires - datetime(1970, 1, 1)).total_seconds()
return http_cookiejar.Cookie(
version=0,
name=name,
diff --git a/macaroonbakery/__init__.py b/macaroonbakery/bakery/__init__.py
similarity index 81%
copy from macaroonbakery/__init__.py
copy to macaroonbakery/bakery/__init__.py
index 6397a19..4b973e9 100644
--- a/macaroonbakery/__init__.py
+++ b/macaroonbakery/bakery/__init__.py
@@ -1,33 +1,33 @@
# Copyright 2017 Canonical Ltd.
# Licensed under the LGPLv3, see LICENCE file for details.
-from macaroonbakery.versions import (
+from ._versions import (
VERSION_0,
VERSION_1,
VERSION_2,
VERSION_3,
LATEST_VERSION,
)
-from macaroonbakery.authorizer import (
+from ._authorizer import (
ACLAuthorizer,
Authorizer,
AuthorizerFunc,
ClosedAuthorizer,
EVERYONE,
)
-from macaroonbakery.codec import (
+from ._codec import (
decode_caveat,
encode_caveat,
encode_uvarint,
)
-from macaroonbakery.checker import (
+from ._checker import (
AuthChecker,
AuthInfo,
Checker,
LOGIN_OP,
Op,
)
-from macaroonbakery.error import (
+from ._error import (
AuthInitError,
CaveatNotRecognizedError,
DischargeRequiredError,
@@ -37,28 +37,28 @@ from macaroonbakery.error import (
ThirdPartyInfoNotFound,
VerificationError,
)
-from macaroonbakery.identity import (
+from ._identity import (
ACLIdentity,
Identity,
IdentityClient,
NoIdentities,
SimpleIdentity,
)
-from macaroonbakery.keys import (
+from ._keys import (
generate_key,
PrivateKey,
PublicKey,
)
-from macaroonbakery.store import (
+from ._store import (
MemoryOpsStore,
MemoryKeyStore,
)
-from macaroonbakery.third_party import (
+from ._third_party import (
ThirdPartyCaveatInfo,
ThirdPartyInfo,
legacy_namespace,
)
-from macaroonbakery.macaroon import (
+from ._macaroon import (
Macaroon,
MacaroonJSONDecoder,
MacaroonJSONEncoder,
@@ -66,18 +66,21 @@ from macaroonbakery.macaroon import (
ThirdPartyStore,
macaroon_version,
)
-from macaroonbakery.discharge import (
+from ._discharge import (
ThirdPartyCaveatChecker,
discharge,
discharge_all,
local_third_party_caveat,
)
-from macaroonbakery.oven import (
+from ._oven import (
Oven,
canonical_ops,
)
-from macaroonbakery.bakery import Bakery
-from macaroonbakery.utils import b64decode
+from ._bakery import Bakery
+from macaroonbakery._utils import (
+ b64decode,
+ macaroon_to_dict,
+)
__all__ = [
'ACLAuthorizer',
@@ -133,5 +136,6 @@ __all__ = [
'generate_key',
'legacy_namespace',
'local_third_party_caveat',
+ 'macaroon_to_dict',
'macaroon_version',
]
diff --git a/macaroonbakery/authorizer.py b/macaroonbakery/bakery/_authorizer.py
similarity index 97%
rename from macaroonbakery/authorizer.py
rename to macaroonbakery/bakery/_authorizer.py
index ae84104..f900430 100644
--- a/macaroonbakery/authorizer.py
+++ b/macaroonbakery/bakery/_authorizer.py
@@ -2,8 +2,7 @@
# Licensed under the LGPLv3, see LICENCE file for details.
import abc
-import macaroonbakery as bakery
-
+from ._identity import ACLIdentity
# EVERYONE is recognized by ACLAuthorizer as the name of a
# group that has everyone in it.
@@ -90,7 +89,7 @@ class ACLAuthorizer(Authorizer):
# Anyone is allowed to do nothing.
return [], []
allowed = [False] * len(ops)
- has_allow = isinstance(identity, bakery.ACLIdentity)
+ has_allow = isinstance(identity, ACLIdentity)
for i, op in enumerate(ops):
acl = self._get_acl(ctx, op)
if has_allow:
diff --git a/macaroonbakery/bakery.py b/macaroonbakery/bakery/_bakery.py
similarity index 94%
rename from macaroonbakery/bakery.py
rename to macaroonbakery/bakery/_bakery.py
index 5d9d56a..8fac9ce 100644
--- a/macaroonbakery/bakery.py
+++ b/macaroonbakery/bakery/_bakery.py
@@ -1,10 +1,10 @@
# Copyright 2017 Canonical Ltd.
# Licensed under the LGPLv3, see LICENCE file for details.
-from macaroonbakery.checkers import checkers
-from macaroonbakery.oven import Oven
-from macaroonbakery.checker import Checker
-from macaroonbakery.authorizer import ClosedAuthorizer
+from ._authorizer import ClosedAuthorizer
+from ._checker import Checker
+import macaroonbakery.checkers as checkers
+from ._oven import Oven
class Bakery(object):
diff --git a/macaroonbakery/checker.py b/macaroonbakery/bakery/_checker.py
similarity index 95%
rename from macaroonbakery/checker.py
rename to macaroonbakery/bakery/_checker.py
index 568fd7c..b796502 100644
--- a/macaroonbakery/checker.py
+++ b/macaroonbakery/bakery/_checker.py
@@ -3,11 +3,17 @@
from collections import namedtuple
from threading import Lock
-
-import pyrfc3339
-
-import macaroonbakery as bakery
+from ._authorizer import ClosedAuthorizer
+from ._identity import NoIdentities
+from ._error import (
+ AuthInitError,
+ VerificationError,
+ IdentityError,
+ DischargeRequiredError,
+ PermissionDenied,
+)
import macaroonbakery.checkers as checkers
+import pyrfc3339
class Op(namedtuple('Op', 'entity, action')):
@@ -38,7 +44,7 @@ class Checker(object):
See the Oven type (TODO) for one way of doing that.
'''
def __init__(self, checker=checkers.Checker(),
- authorizer=bakery.ClosedAuthorizer(),
+ authorizer=ClosedAuthorizer(),
identity_client=None,
macaroon_opstore=None):
'''
@@ -57,7 +63,7 @@ class Checker(object):
self._first_party_caveat_checker = checker
self._authorizer = authorizer
if identity_client is None:
- identity_client = bakery.NoIdentities()
+ identity_client = NoIdentities()
self._identity_client = identity_client
self._macaroon_opstore = macaroon_opstore
@@ -105,8 +111,8 @@ class AuthChecker(object):
if not self._executed:
self._init_once(ctx)
self._executed = True
- if self._init_errors is not None and len(self._init_errors) > 0:
- raise bakery.AuthInitError(self._init_errors[0])
+ if self._init_errors:
+ raise AuthInitError(self._init_errors[0])
def _init_once(self, ctx):
self._auth_indexes = {}
@@ -115,7 +121,7 @@ class AuthChecker(object):
try:
ops, conditions = self.parent._macaroon_opstore.macaroon_ops(
ms)
- except bakery.VerificationError:
+ except VerificationError:
raise
except Exception as exc:
self._init_errors.append(exc.args[0])
@@ -157,7 +163,7 @@ class AuthChecker(object):
try:
identity = self.parent._identity_client.declared_identity(
ctx, declared)
- except bakery.IdentityError as exc:
+ except IdentityError as exc:
self._init_errors.append(
'cannot decode declared identity: {}'.format(exc.args[0]))
continue
@@ -171,7 +177,7 @@ class AuthChecker(object):
try:
identity, cavs = self.parent.\
_identity_client.identity_from_context(ctx)
- except bakery.IdentityError:
+ except IdentityError:
self._init_errors.append('could not determine identity')
if cavs is None:
cavs = []
@@ -292,7 +298,7 @@ class AuthChecker(object):
# no caveats to be discharged.
return authed, used
if self._identity is None and len(self._identity_caveats) > 0:
- raise bakery.DischargeRequiredError(
+ raise DischargeRequiredError(
msg='authentication required',
ops=[LOGIN_OP],
cavs=self._identity_caveats)
@@ -303,8 +309,8 @@ class AuthChecker(object):
err = ''
if len(all_errors) > 0:
err = all_errors[0]
- raise bakery.PermissionDenied(err)
- raise bakery.DischargeRequiredError(
+ raise PermissionDenied(err)
+ raise DischargeRequiredError(
msg='some operations have extra caveats', ops=ops, cavs=caveats)
def allow_capability(self, ctx, ops):
@@ -391,7 +397,7 @@ class _CaveatSquasher(object):
if cond == checkers.COND_TIME_BEFORE:
try:
- et = pyrfc3339.parse(args)
+ et = pyrfc3339.parse(args, utc=True).replace(tzinfo=None)
except ValueError:
# Again, if it doesn't seem valid, leave it alone.
return True
diff --git a/macaroonbakery/codec.py b/macaroonbakery/bakery/_codec.py
similarity index 85%
rename from macaroonbakery/codec.py
rename to macaroonbakery/bakery/_codec.py
index 2946da9..903e604 100644
--- a/macaroonbakery/codec.py
+++ b/macaroonbakery/bakery/_codec.py
@@ -3,11 +3,13 @@
import base64
import json
-import six
-import nacl.public
-
-import macaroonbakery as bakery
+from ._versions import (VERSION_1, VERSION_2, VERSION_3)
+from ._third_party import legacy_namespace, ThirdPartyCaveatInfo
+from ._keys import PublicKey
+from ._error import VerificationError
import macaroonbakery.checkers as checkers
+import nacl.public
+import six
_PUBLIC_KEY_PREFIX_LEN = 4
_KEY_LEN = 32
@@ -33,11 +35,11 @@ def encode_caveat(condition, root_key, third_party_info, key, ns):
@param ns not used yet
@return bytes
'''
- if third_party_info.version == bakery.VERSION_1:
+ if third_party_info.version == VERSION_1:
return _encode_caveat_v1(condition, root_key,
third_party_info.public_key, key)
- if (third_party_info.version == bakery.VERSION_2 or
- third_party_info.version == bakery.VERSION_3):
+ if (third_party_info.version == VERSION_2 or
+ third_party_info.version == VERSION_3):
return _encode_caveat_v2_v3(third_party_info.version, condition,
root_key, third_party_info.public_key,
key, ns)
@@ -67,8 +69,8 @@ def _encode_caveat_v1(condition, root_key, third_party_pub_key, key):
nonce = encrypted[0:nacl.public.Box.NONCE_SIZE]
encrypted = encrypted[nacl.public.Box.NONCE_SIZE:]
return base64.b64encode(six.b(json.dumps({
- 'ThirdPartyPublicKey': third_party_pub_key.encode().decode('ascii'),
- 'FirstPartyPublicKey': key.public_key.encode().decode('ascii'),
+ 'ThirdPartyPublicKey': str(third_party_pub_key),
+ 'FirstPartyPublicKey': str(key.public_key),
'Nonce': base64.b64encode(nonce).decode('ascii'),
'Id': base64.b64encode(encrypted).decode('ascii')
})))
@@ -99,12 +101,12 @@ def _encode_caveat_v2_v3(version, condition, root_key, third_party_pub_key,
condition [rest of encrypted part]
'''
ns_data = bytearray()
- if version >= bakery.VERSION_3:
+ if version >= VERSION_3:
ns_data = ns.serialize_text()
data = bytearray()
data.append(version)
- data.extend(third_party_pub_key.encode(raw=True)[:_PUBLIC_KEY_PREFIX_LEN])
- data.extend(key.public_key.encode(raw=True)[:])
+ data.extend(third_party_pub_key.serialize(raw=True)[:_PUBLIC_KEY_PREFIX_LEN])
+ data.extend(key.public_key.serialize(raw=True)[:])
secret = _encode_secret_part_v2_v3(version, condition, root_key, ns_data)
box = nacl.public.Box(key.key, third_party_pub_key.key)
encrypted = box.encrypt(secret)
@@ -131,7 +133,7 @@ def _encode_secret_part_v2_v3(version, condition, root_key, ns):
data.append(version)
encode_uvarint(len(root_key), data)
data.extend(root_key)
- if version >= bakery.VERSION_3:
+ if version >= VERSION_3:
encode_uvarint(len(ns), data)
data.extend(ns)
data.extend(condition.encode('utf-8'))
@@ -146,7 +148,7 @@ def decode_caveat(key, caveat):
@return ThirdPartyCaveatInfo
'''
if len(caveat) == 0:
- raise bakery.VerificationError('empty third party caveat')
+ raise VerificationError('empty third party caveat')
first = caveat[:1]
if first == b'e':
@@ -154,17 +156,17 @@ def decode_caveat(key, caveat):
# encoded JSON object.
return _decode_caveat_v1(key, caveat)
first_as_int = six.byte2int(first)
- if (first_as_int == bakery.VERSION_2 or
- first_as_int == bakery.VERSION_3):
+ if (first_as_int == VERSION_2 or
+ first_as_int == VERSION_3):
if (len(caveat) < _VERSION3_CAVEAT_MIN_LEN
- and first_as_int == bakery.VERSION_3):
+ and first_as_int == VERSION_3):
# If it has the version 3 caveat tag and it's too short, it's
# almost certainly an id, not an encrypted payload.
- raise bakery.VerificationError(
+ raise VerificationError(
'caveat id payload not provided for caveat id {}'.format(
caveat))
return _decode_caveat_v2_v3(first_as_int, key, caveat)
- raise bakery.VerificationError('unknown version for caveat')
+ raise VerificationError('unknown version for caveat')
def _decode_caveat_v1(key, caveat):
@@ -196,15 +198,15 @@ def _decode_caveat_v1(key, caveat):
record = json.loads(c.decode('utf-8'))
fp_key = nacl.public.PublicKey(
base64.b64decode(wrapper.get('FirstPartyPublicKey')))
- return bakery.ThirdPartyCaveatInfo(
+ return ThirdPartyCaveatInfo(
condition=record.get('Condition'),
- first_party_public_key=bakery.PublicKey(fp_key),
+ first_party_public_key=PublicKey(fp_key),
third_party_key_pair=key,
root_key=base64.b64decode(record.get('RootKey')),
caveat=caveat,
id=None,
- version=bakery.VERSION_1,
- namespace=bakery.legacy_namespace()
+ version=VERSION_1,
+ namespace=legacy_namespace()
)
@@ -213,14 +215,14 @@ def _decode_caveat_v2_v3(version, key, caveat):
'''
if (len(caveat) < 1 + _PUBLIC_KEY_PREFIX_LEN +
_KEY_LEN + nacl.public.Box.NONCE_SIZE + 16):
- raise bakery.VerificationError('caveat id too short')
+ raise VerificationError('caveat id too short')
original_caveat = caveat
caveat = caveat[1:] # skip version (already checked)
pk_prefix = caveat[:_PUBLIC_KEY_PREFIX_LEN]
caveat = caveat[_PUBLIC_KEY_PREFIX_LEN:]
- if key.public_key.encode(raw=True)[:_PUBLIC_KEY_PREFIX_LEN] != pk_prefix:
- raise bakery.VerificationError('public key mismatch')
+ if key.public_key.serialize(raw=True)[:_PUBLIC_KEY_PREFIX_LEN] != pk_prefix:
+ raise VerificationError('public key mismatch')
first_party_pub = caveat[:_KEY_LEN]
caveat = caveat[_KEY_LEN:]
@@ -230,9 +232,9 @@ def _decode_caveat_v2_v3(version, key, caveat):
box = nacl.public.Box(key.key, fp_public_key)
data = box.decrypt(caveat, nonce)
root_key, condition, ns = _decode_secret_part_v2_v3(version, data)
- return bakery.ThirdPartyCaveatInfo(
+ return ThirdPartyCaveatInfo(
condition=condition.decode('utf-8'),
- first_party_public_key=bakery.PublicKey(fp_public_key),
+ first_party_public_key=PublicKey(fp_public_key),
third_party_key_pair=key,
root_key=root_key,
caveat=original_caveat,
@@ -244,25 +246,25 @@ def _decode_caveat_v2_v3(version, key, caveat):
def _decode_secret_part_v2_v3(version, data):
if len(data) < 1:
- raise bakery.VerificationError('secret part too short')
+ raise VerificationError('secret part too short')
got_version = six.byte2int(data[:1])
data = data[1:]
if version != got_version:
- raise bakery.VerificationError(
+ raise VerificationError(
'unexpected secret part version, got {} want {}'.format(
got_version, version))
root_key_length, read = decode_uvarint(data)
data = data[read:]
root_key = data[:root_key_length]
data = data[root_key_length:]
- if version >= bakery.VERSION_3:
+ if version >= VERSION_3:
namespace_length, read = decode_uvarint(data)
data = data[read:]
ns_data = data[:namespace_length]
data = data[namespace_length:]
ns = checkers.deserialize_namespace(ns_data)
else:
- ns = bakery.legacy_namespace()
+ ns = legacy_namespace()
return root_key, data, ns
diff --git a/macaroonbakery/discharge.py b/macaroonbakery/bakery/_discharge.py
similarity index 87%
rename from macaroonbakery/discharge.py
rename to macaroonbakery/bakery/_discharge.py
index f54fc97..1831209 100644
--- a/macaroonbakery/discharge.py
+++ b/macaroonbakery/bakery/_discharge.py
@@ -3,7 +3,19 @@
import abc
from collections import namedtuple
-import macaroonbakery as bakery
+from ._error import (
+ ThirdPartyCaveatCheckFailed,
+ CaveatNotRecognizedError,
+ VerificationError,
+)
+from ._codec import decode_caveat
+from ._macaroon import (
+ Macaroon,
+ ThirdPartyLocator,
+)
+from ._versions import VERSION_2
+from ._third_party import ThirdPartyCaveatInfo
+
import macaroonbakery.checkers as checkers
emptyContext = checkers.AuthContext()
@@ -46,7 +58,11 @@ def discharge_all(m, get_discharge, local_key=None):
while len(need) > 0:
cav = need[0]
need = need[1:]
- if local_key is not None and cav.cav.location == 'local':
+ if cav.cav.location == 'local':
+ if local_key is None:
+ raise ThirdPartyCaveatCheckFailed(
+ 'found local third party caveat but no private key provided',
+ )
# TODO use a small caveat id.
dm = discharge(ctx=emptyContext,
key=local_key,
@@ -90,7 +106,7 @@ class ThirdPartyCaveatChecker(object):
class _LocalDischargeChecker(ThirdPartyCaveatChecker):
def check_third_party_caveat(self, ctx, info):
if info.condition != 'true':
- raise bakery.CaveatNotRecognizedError()
+ raise CaveatNotRecognizedError()
return []
@@ -125,8 +141,8 @@ def discharge(ctx, id, caveat, key, checker, locator):
# caveats are added, use that id as the prefix
# for any more ids.
caveat_id_prefix = id
- cav_info = bakery.decode_caveat(key, caveat)
- cav_info = bakery.ThirdPartyCaveatInfo(
+ cav_info = decode_caveat(key, caveat)
+ cav_info = ThirdPartyCaveatInfo(
condition=cav_info.condition,
first_party_public_key=cav_info.first_party_public_key,
third_party_key_pair=cav_info.third_party_key_pair,
@@ -142,7 +158,7 @@ def discharge(ctx, id, caveat, key, checker, locator):
try:
cond, arg = checkers.parse_caveat(cav_info.condition)
except ValueError as exc:
- raise bakery.VerificationError(exc.args[0])
+ raise VerificationError(exc.args[0])
if cond == checkers.COND_NEED_DECLARED:
cav_info = cav_info._replace(condition=arg.encode('utf-8'))
@@ -154,7 +170,7 @@ def discharge(ctx, id, caveat, key, checker, locator):
# be stored persistently. Indeed, it would be a problem if
# we did, because then the macaroon could potentially be used
# for normal authorization with the third party.
- m = bakery.Macaroon(
+ m = Macaroon(
cav_info.root_key,
id,
'',
@@ -172,15 +188,15 @@ def _check_need_declared(ctx, cav_info, checker):
arg = cav_info.condition.decode('utf-8')
i = arg.find(' ')
if i <= 0:
- raise bakery.VerificationError(
+ raise VerificationError(
'need-declared caveat requires an argument, got %q'.format(arg),
)
need_declared = arg[0:i].split(',')
for d in need_declared:
if d == '':
- raise bakery.VerificationError('need-declared caveat with empty required attribute')
+ raise VerificationError('need-declared caveat with empty required attribute')
if len(need_declared) == 0:
- raise bakery.VerificationError('need-declared caveat with no required attributes')
+ raise VerificationError('need-declared caveat with no required attributes')
cav_info = cav_info._replace(condition=arg[i + 1:].encode('utf-8'))
caveats = checker.check_third_party_caveat(ctx, cav_info)
declared = {}
@@ -197,7 +213,7 @@ def _check_need_declared(ctx, cav_info, checker):
continue
parts = arg.split()
if len(parts) != 2:
- raise bakery.VerificationError('declared caveat has no value')
+ raise VerificationError('declared caveat has no value')
declared[parts[0]] = True
# Add empty declarations for everything mentioned in need-declared
# that was not actually declared.
@@ -207,7 +223,7 @@ def _check_need_declared(ctx, cav_info, checker):
return caveats
-class _EmptyLocator(bakery.ThirdPartyLocator):
+class _EmptyLocator(ThirdPartyLocator):
def third_party_info(self, loc):
return None
@@ -218,8 +234,8 @@ def local_third_party_caveat(key, version):
the given PublicKey.
This can be automatically discharged by discharge_all passing a local key.
'''
- encoded_key = key.encode().decode('utf-8')
- loc = 'local {}'.format(encoded_key)
- if version >= bakery.VERSION_2:
- loc = 'local {} {}'.format(version, encoded_key)
+ if version >= VERSION_2:
+ loc = 'local {} {}'.format(version, key)
+ else:
+ loc = 'local {}'.format(key)
return checkers.Caveat(location=loc, condition='')
diff --git a/macaroonbakery/error.py b/macaroonbakery/bakery/_error.py
similarity index 100%
rename from macaroonbakery/error.py
rename to macaroonbakery/bakery/_error.py
diff --git a/macaroonbakery/identity.py b/macaroonbakery/bakery/_identity.py
similarity index 97%
rename from macaroonbakery/identity.py
rename to macaroonbakery/bakery/_identity.py
index 1579bba..4389cd9 100644
--- a/macaroonbakery/identity.py
+++ b/macaroonbakery/bakery/_identity.py
@@ -2,7 +2,7 @@
# Licensed under the LGPLv3, see LICENCE file for details.
import abc
-import macaroonbakery as bakery
+from ._error import IdentityError
class Identity(object):
@@ -123,4 +123,4 @@ class NoIdentities(IdentityClient):
return None, None
def declared_identity(self, ctx, declared):
- raise bakery.IdentityError('no identity declared or possible')
+ raise IdentityError('no identity declared or possible')
diff --git a/macaroonbakery/internal/__init__.py b/macaroonbakery/bakery/_internal/__init__.py
similarity index 100%
rename from macaroonbakery/internal/__init__.py
rename to macaroonbakery/bakery/_internal/__init__.py
diff --git a/macaroonbakery/internal/id.proto b/macaroonbakery/bakery/_internal/id.proto
similarity index 100%
rename from macaroonbakery/internal/id.proto
rename to macaroonbakery/bakery/_internal/id.proto
diff --git a/macaroonbakery/internal/id_pb2.py b/macaroonbakery/bakery/_internal/id_pb2.py
similarity index 100%
rename from macaroonbakery/internal/id_pb2.py
rename to macaroonbakery/bakery/_internal/id_pb2.py
diff --git a/macaroonbakery/keys.py b/macaroonbakery/bakery/_keys.py
similarity index 78%
rename from macaroonbakery/keys.py
rename to macaroonbakery/bakery/_keys.py
index 5cf61c5..1da5f05 100644
--- a/macaroonbakery/keys.py
+++ b/macaroonbakery/bakery/_keys.py
@@ -34,15 +34,19 @@ class PrivateKey(object):
nacl.public.PrivateKey(serialized,
encoder=nacl.encoding.Base64Encoder))
- def encode(self, raw=False):
- ''' Encode the key in a base64 format by default but when raw is True
... 2425 lines suppressed ...
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/python-modules/packages/py-macaroon-bakery.git
More information about the Python-modules-commits
mailing list