diff -Nru python-libmaas-0.6.0/debian/changelog python-libmaas-0.6.0/debian/changelog --- python-libmaas-0.6.0/debian/changelog 2018-02-07 02:15:00.000000000 +0000 +++ python-libmaas-0.6.0/debian/changelog 2019-07-18 11:24:25.000000000 +0100 @@ -1,3 +1,9 @@ +python-libmaas (0.6.0-0ubuntu2) disco; urgency=medium + + * d/p/async_keyword_rename.diff: Rename async.py (LP: #1823718) + + -- Adam Collard Thu, 18 Jul 2019 11:24:25 +0100 + python-libmaas (0.6.0-0ubuntu1) bionic; urgency=medium * New upstream release diff -Nru python-libmaas-0.6.0/debian/patches/async_keyword_rename.diff python-libmaas-0.6.0/debian/patches/async_keyword_rename.diff --- python-libmaas-0.6.0/debian/patches/async_keyword_rename.diff 1970-01-01 01:00:00.000000000 +0100 +++ python-libmaas-0.6.0/debian/patches/async_keyword_rename.diff 2019-07-18 11:22:34.000000000 +0100 @@ -0,0 +1,425 @@ +Author: Adam Collard +Origin: upstream, https://github.com/maas/python-libmaas/commit/585a85ac9b93156e074702de05c56761ed09b9b9 +Bug-Ubuntu: https://bugs.launchpad.net/ubuntu/+source/python-libmaas/+bug/1823718 +Forwarded: not-needed +Last-Update: 2019-07-18 +Subject: Fix incompatibility with Python 3.7 + * Rename to async.py to maas_async.py +--- +Index: python-libmaas-0.6.0/maas/client/__init__.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/__init__.py ++++ python-libmaas-0.6.0/maas/client/__init__.py +@@ -5,7 +5,7 @@ __all__ = [ + "login", + ] + +-from .utils.async import asynchronous ++from .utils.maas_async import asynchronous + + + @asynchronous +Index: python-libmaas-0.6.0/maas/client/bones/__init__.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/bones/__init__.py ++++ python-libmaas-0.6.0/maas/client/bones/__init__.py +@@ -20,7 +20,7 @@ import aiohttp + from . import helpers + from .. import utils + from ..utils import profiles +-from ..utils.async import asynchronous ++from ..utils.maas_async import asynchronous + + + class SessionError(Exception): +Index: python-libmaas-0.6.0/maas/client/bones/helpers.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/bones/helpers.py ++++ python-libmaas-0.6.0/maas/client/bones/helpers.py +@@ -28,7 +28,7 @@ from urllib.parse import ( + import aiohttp + + from ..utils import api_url +-from ..utils.async import asynchronous ++from ..utils.maas_async import asynchronous + from ..utils.creds import Credentials + from ..utils.profiles import Profile + +Index: python-libmaas-0.6.0/maas/client/bones/tests/test_helpers.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/bones/tests/test_helpers.py ++++ python-libmaas-0.6.0/maas/client/bones/tests/test_helpers.py +@@ -322,7 +322,6 @@ class TestAuthenticate(TestCase): + @builder.handle("anon:Version.read") + async def version(request): + return {"capabilities": []} +- + async with builder.serve() as baseurl: + with ExpectedException(helpers.LoginNotSupported): + await helpers.authenticate(baseurl, "username", "password") +@@ -337,7 +336,6 @@ class TestAuthenticate(TestCase): + @builder.route("POST", "/accounts/authenticate/") + async def deploy(request): + raise aiohttp.web.HTTPForbidden() +- + async with builder.serve() as baseurl: + with ExpectedException(helpers.RemoteError): + await helpers.authenticate(baseurl, "username", "password") +Index: python-libmaas-0.6.0/maas/client/flesh/controllers.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/flesh/controllers.py ++++ python-libmaas-0.6.0/maas/client/flesh/controllers.py +@@ -13,7 +13,7 @@ from . import ( + tables, + ) + from ..enum import NodeType +-from ..utils.async import asynchronous ++from ..utils.maas_async import asynchronous + + + class cmd_controllers(OriginPagedTableCommand): +Index: python-libmaas-0.6.0/maas/client/flesh/fabrics.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/flesh/fabrics.py ++++ python-libmaas-0.6.0/maas/client/flesh/fabrics.py +@@ -12,7 +12,7 @@ from . import ( + tables, + ) + from ..bones import CallError +-from ..utils.async import asynchronous ++from ..utils.maas_async import asynchronous + + + class cmd_fabrics(OriginPagedTableCommand): +Index: python-libmaas-0.6.0/maas/client/flesh/machines.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/flesh/machines.py ++++ python-libmaas-0.6.0/maas/client/flesh/machines.py +@@ -23,7 +23,7 @@ from . import ( + from .. import utils + from ..bones import CallError + from ..enum import NodeStatus +-from ..utils.async import asynchronous ++from ..utils.maas_async import asynchronous + + + def validate_file(parser, arg): +Index: python-libmaas-0.6.0/maas/client/flesh/profiles.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/flesh/profiles.py ++++ python-libmaas-0.6.0/maas/client/flesh/profiles.py +@@ -25,7 +25,7 @@ from ..utils import ( + auth, + profiles, + ) +-from ..utils.async import asynchronous ++from ..utils.maas_async import asynchronous + + + class cmd_login(Command): +Index: python-libmaas-0.6.0/maas/client/flesh/spaces.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/flesh/spaces.py ++++ python-libmaas-0.6.0/maas/client/flesh/spaces.py +@@ -12,7 +12,7 @@ from . import ( + tables, + ) + from ..bones import CallError +-from ..utils.async import asynchronous ++from ..utils.maas_async import asynchronous + + + class cmd_spaces(OriginPagedTableCommand): +Index: python-libmaas-0.6.0/maas/client/flesh/subnets.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/flesh/subnets.py ++++ python-libmaas-0.6.0/maas/client/flesh/subnets.py +@@ -12,7 +12,7 @@ from . import ( + tables, + ) + from ..bones import CallError +-from ..utils.async import asynchronous ++from ..utils.maas_async import asynchronous + + + class cmd_subnets(OriginPagedTableCommand): +Index: python-libmaas-0.6.0/maas/client/flesh/vlans.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/flesh/vlans.py ++++ python-libmaas-0.6.0/maas/client/flesh/vlans.py +@@ -12,7 +12,7 @@ from . import ( + tables, + ) + from ..bones import CallError +-from ..utils.async import asynchronous ++from ..utils.maas_async import asynchronous + + + class cmd_vlans(OriginPagedTableCommand): +Index: python-libmaas-0.6.0/maas/client/testing/__init__.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/testing/__init__.py ++++ python-libmaas-0.6.0/maas/client/testing/__init__.py +@@ -33,7 +33,7 @@ import testscenarios + from testtools import testcase + from testtools.matchers import DocTestMatches + +-from ..utils.async import Asynchronous ++from ..utils.maas_async import Asynchronous + + + random_letters = map( +Index: python-libmaas-0.6.0/maas/client/utils/async.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/utils/async.py ++++ /dev/null +@@ -1,83 +0,0 @@ +-# Copyright 2016-2017 Canonical Ltd. +-# +-# Licensed under the Apache License, Version 2.0 (the "License"); +-# you may not use this file except in compliance with the License. +-# You may obtain a copy of the License at +-# +-# http://www.apache.org/licenses/LICENSE-2.0 +-# +-# Unless required by applicable law or agreed to in writing, software +-# distributed under the License is distributed on an "AS IS" BASIS, +-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +-# See the License for the specific language governing permissions and +-# limitations under the License. +- +-"""Asynchronous helpers, for use with `asyncio`.""" +- +-__all__ = [ +- "asynchronous", +- "Asynchronous", +- "is_loop_running", +-] +- +-from asyncio import get_event_loop +-from functools import wraps +-from inspect import ( +- isawaitable, +- iscoroutinefunction, +-) +- +- +-def asynchronous(func): +- """Return `func` in a "smart" asynchronous-aware wrapper. +- +- If `func` is called within the event-loop — i.e. when it is running — this +- returns the result of `func` without alteration. However, when called from +- outside of the event-loop, and the result is awaitable, the result will be +- passed though the current event-loop's `run_until_complete` method. +- +- In other words, this automatically blocks when calling an asynchronous +- function from outside of the event-loop, and so makes interactive use of +- these APIs far more intuitive. +- """ +- @wraps(func) +- def wrapper(*args, **kwargs): +- eventloop = get_event_loop() +- result = func(*args, **kwargs) +- if not eventloop.is_running(): +- while isawaitable(result): +- result = eventloop.run_until_complete(result) +- return result +- +- return wrapper +- +- +-class Asynchronous(type): +- """Metaclass that wraps callable attributes with `asynchronous`. +- +- Use this to create classes instances of which work naturally when working +- with them interactively. +- """ +- +- def __new__(cls, name, bases, attrs): +- attrs.setdefault("__slots__", ()) +- attrs = {name: _maybe_wrap(value) for name, value in attrs.items()} +- return super(Asynchronous, cls).__new__(cls, name, bases, attrs) +- +- +-def _maybe_wrap(attribute): +- """Helper for `Asynchronous`.""" +- if iscoroutinefunction(attribute): +- return asynchronous(attribute) +- if isinstance(attribute, (classmethod, staticmethod)): +- if iscoroutinefunction(attribute.__func__): +- return attribute.__class__(asynchronous(attribute.__func__)) +- return attribute +- +- +-def is_loop_running(): +- """Is the current event-loop running right now? +- +- Then we don't want to block, do we? +- """ +- return get_event_loop().is_running() +Index: python-libmaas-0.6.0/maas/client/utils/tests/test_async.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/utils/tests/test_async.py ++++ python-libmaas-0.6.0/maas/client/utils/tests/test_async.py +@@ -23,7 +23,7 @@ from testtools.matchers import ( + MatchesPredicate, + ) + +-from .. import async ++from .. import maas_async + from ...testing import TestCase + + +@@ -35,12 +35,12 @@ class TestAsynchronousWrapper(TestCase): + + def test_returns_plain_result_unaltered_when_loop_not_running(self): + token = object() +- func = async.asynchronous(lambda: token) ++ func = maas_async.asynchronous(lambda: token) + self.assertThat(func(), Is(token)) + + def test_returns_plain_result_unaltered_when_loop_running(self): + token = object() +- func = async.asynchronous(lambda: token) ++ func = maas_async.asynchronous(lambda: token) + + async def within_event_loop(): + loop = asyncio.get_event_loop() +@@ -53,12 +53,12 @@ class TestAsynchronousWrapper(TestCase): + + def test_blocks_on_awaitable_result_when_loop_not_running(self): + token = asyncio.sleep(0.0) +- func = async.asynchronous(lambda: token) ++ func = maas_async.asynchronous(lambda: token) + self.assertThat(func(), Is(None)) + + def test_returns_awaitable_result_unaltered_when_loop_running(self): + token = asyncio.sleep(0.0) +- func = async.asynchronous(lambda: token) ++ func = maas_async.asynchronous(lambda: token) + + async def within_event_loop(): + loop = asyncio.get_event_loop() +@@ -78,7 +78,7 @@ class TestAsynchronousType(TestCase): + def test_callable_attributes_are_wrapped(self): + # `Asynchronous` groks class- and static-methods. + +- class Class(metaclass=async.Asynchronous): ++ class Class(metaclass=maas_async.Asynchronous): + + attribute = 123 + +Index: python-libmaas-0.6.0/maas/client/viscera/__init__.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/viscera/__init__.py ++++ python-libmaas-0.6.0/maas/client/viscera/__init__.py +@@ -46,7 +46,7 @@ from ..utils import ( + get_all_subclasses, + vars_class, + ) +-from ..utils.async import Asynchronous ++from ..utils.maas_async import Asynchronous + + + undefined = object() +Index: python-libmaas-0.6.0/maas/client/viscera/events.py +=================================================================== +--- python-libmaas-0.6.0.orig/maas/client/viscera/events.py ++++ python-libmaas-0.6.0/maas/client/viscera/events.py +@@ -22,7 +22,7 @@ from . import ( + ObjectSet, + ObjectType, + ) +-from ..utils.async import is_loop_running ++from ..utils.maas_async import is_loop_running + + # + # The query API call returns: +Index: python-libmaas-0.6.0/maas/client/utils/maas_async.py +=================================================================== +--- /dev/null ++++ python-libmaas-0.6.0/maas/client/utils/maas_async.py +@@ -0,0 +1,83 @@ ++# Copyright 2016-2017 Canonical Ltd. ++# ++# Licensed under the Apache License, Version 2.0 (the "License"); ++# you may not use this file except in compliance with the License. ++# You may obtain a copy of the License at ++# ++# http://www.apache.org/licenses/LICENSE-2.0 ++# ++# Unless required by applicable law or agreed to in writing, software ++# distributed under the License is distributed on an "AS IS" BASIS, ++# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. ++# See the License for the specific language governing permissions and ++# limitations under the License. ++ ++"""Asynchronous helpers, for use with `asyncio`.""" ++ ++__all__ = [ ++ "asynchronous", ++ "Asynchronous", ++ "is_loop_running", ++] ++ ++from asyncio import get_event_loop ++from functools import wraps ++from inspect import ( ++ isawaitable, ++ iscoroutinefunction, ++) ++ ++ ++def asynchronous(func): ++ """Return `func` in a "smart" asynchronous-aware wrapper. ++ ++ If `func` is called within the event-loop — i.e. when it is running — this ++ returns the result of `func` without alteration. However, when called from ++ outside of the event-loop, and the result is awaitable, the result will be ++ passed though the current event-loop's `run_until_complete` method. ++ ++ In other words, this automatically blocks when calling an asynchronous ++ function from outside of the event-loop, and so makes interactive use of ++ these APIs far more intuitive. ++ """ ++ @wraps(func) ++ def wrapper(*args, **kwargs): ++ eventloop = get_event_loop() ++ result = func(*args, **kwargs) ++ if not eventloop.is_running(): ++ while isawaitable(result): ++ result = eventloop.run_until_complete(result) ++ return result ++ ++ return wrapper ++ ++ ++class Asynchronous(type): ++ """Metaclass that wraps callable attributes with `asynchronous`. ++ ++ Use this to create classes instances of which work naturally when working ++ with them interactively. ++ """ ++ ++ def __new__(cls, name, bases, attrs): ++ attrs.setdefault("__slots__", ()) ++ attrs = {name: _maybe_wrap(value) for name, value in attrs.items()} ++ return super(Asynchronous, cls).__new__(cls, name, bases, attrs) ++ ++ ++def _maybe_wrap(attribute): ++ """Helper for `Asynchronous`.""" ++ if iscoroutinefunction(attribute): ++ return asynchronous(attribute) ++ if isinstance(attribute, (classmethod, staticmethod)): ++ if iscoroutinefunction(attribute.__func__): ++ return attribute.__class__(asynchronous(attribute.__func__)) ++ return attribute ++ ++ ++def is_loop_running(): ++ """Is the current event-loop running right now? ++ ++ Then we don't want to block, do we? ++ """ ++ return get_event_loop().is_running() diff -Nru python-libmaas-0.6.0/debian/patches/series python-libmaas-0.6.0/debian/patches/series --- python-libmaas-0.6.0/debian/patches/series 2018-02-07 02:15:00.000000000 +0000 +++ python-libmaas-0.6.0/debian/patches/series 2019-07-18 11:06:00.000000000 +0100 @@ -0,0 +1 @@ +async_keyword_rename.diff