cloud-init fails to build with Python 3.12.0a7. =================================== FAILURES =================================== _________ TestDualStack.test_dual_stack[<lambda>-addresses1-1-0-None] __________ self = <tests.unittests.test_url_helper.TestDualStack object at 0x7ffa61d6a2d0> func = <function TestDualStack.<lambda> at 0x7ffa61947380> addresses = ('one', 'two'), stagger_delay = 1, timeout = 0, expected_val = None @pytest.mark.parametrize( ["func", "addresses", "stagger_delay", "timeout", "expected_val"], [ # Assert order based on timeout (lambda x, _: x, ("one", "two"), 1, 1, "one"), # Assert timeout results in (None, None) (lambda _a, _b: event.wait(1), ("one", "two"), 1, 0, None), ( lambda a, _b: 1 / 0 if a == "one" else a, ("one", "two"), 0, 1, "two", ), # Assert that exception in func is only raised # if neither thread gets a valid result ( lambda a, _b: 1 / 0 if a == "two" else a, ("one", "two"), 0, 1, "one", ), # simulate a slow response to verify correct order ( lambda x, _: event.wait(1) if x != "two" else x, ("one", "two"), 0, 1, "two", ), # simulate a slow response to verify correct order ( lambda x, _: event.wait(1) if x != "tri" else x, ("one", "two", "tri"), 0, 1, "tri", ), ], ) def test_dual_stack( self, func, addresses, stagger_delay, timeout, expected_val, ): """Assert various failure modes behave as expected""" event.clear() gen = partial( dual_stack, func, addresses, stagger_delay=stagger_delay, timeout=timeout, ) > _, result = assert_time(gen) tests/unittests/test_url_helper.py:363: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ tests/unittests/test_url_helper.py:289: in assert_time out = func() cloudinit/url_helper.py:469: in dual_stack executor.shutdown(wait=False) _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ fs = {<Future at 0x7ffa5f5496a0 state=running>, <Future at 0x7ffa5f5488c0 state=running>} timeout = 0 def as_completed(fs, timeout=None): """An iterator over the given futures that yields each as it completes. Args: fs: The sequence of Futures (possibly created by different Executors) to iterate over. timeout: The maximum number of seconds to wait. If None, then there is no limit on the wait time. Returns: An iterator that yields the given Futures as they complete (finished or cancelled). If any given Futures are duplicated, they will be returned once. Raises: TimeoutError: If the entire result iterator could not be generated before the given timeout. """ if timeout is not None: end_time = timeout + time.monotonic() fs = set(fs) total_futures = len(fs) with _AcquireFutures(fs): finished = set( f for f in fs if f._state in [CANCELLED_AND_NOTIFIED, FINISHED]) pending = fs - finished waiter = _create_and_install_waiters(fs, _AS_COMPLETED) finished = list(finished) try: yield from _yield_finished_futures(finished, waiter, ref_collect=(fs,)) while pending: if timeout is None: wait_timeout = None else: wait_timeout = end_time - time.monotonic() if wait_timeout < 0: > raise TimeoutError( '%d (of %d) futures unfinished' % ( len(pending), total_futures)) E TimeoutError: 2 (of 2) futures unfinished /usr/lib64/python3.12/concurrent/futures/_base.py:239: TimeoutError __________________ TestUdevadmSettle.test_udevadm_not_present __________________ self = <tests.unittests.test_util.TestUdevadmSettle testMethod=test_udevadm_not_present> m_which = <MagicMock name='subp' id='140713320029008'> m_subp = <MagicMock name='which' id='140713322657360'> def test_udevadm_not_present(self, m_which, m_subp): """where udevadm program does not exist should not invoke subp.""" m_which.side_effect = lambda m: m in ("",) util.udevadm_settle() > m_subp.called_once_with(["which", "udevadm"]) tests/unittests/test_util.py:870: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ self = <MagicMock name='which' id='140713322657360'>, name = 'called_once_with' def __getattr__(self, name): if name in {'_mock_methods', '_mock_unsafe'}: raise AttributeError(name) elif self._mock_methods is not None: if name not in self._mock_methods or name in _all_magics: raise AttributeError("Mock object has no attribute %r" % name) elif _is_magic(name): raise AttributeError(name) if not self._mock_unsafe and (not self._mock_methods or name not in self._mock_methods): if name.startswith(('assert', 'assret', 'asert', 'aseert', 'assrt')) or name in _ATTRIB_DENY_LIST: > raise AttributeError( f"{name!r} is not a valid assertion. Use a spec " f"for the mock if {name!r} is meant to be an attribute.") E AttributeError: 'called_once_with' is not a valid assertion. Use a spec for the mock if 'called_once_with' is meant to be an attribute.. Did you mean: 'assert_called_once_with'? /usr/lib64/python3.12/unittest/mock.py:657: AttributeError ______________ TestUdevadmSettle.test_with_exists_and_file_exists ______________ self = <tests.unittests.test_util.TestUdevadmSettle testMethod=test_with_exists_and_file_exists> m_which = <MagicMock name='subp' id='140713300180672'> m_subp = <MagicMock name='which' id='140713300175728'> def test_with_exists_and_file_exists(self, m_which, m_subp): """with exists=file where file does exist should only invoke subp once for 'which' call.""" m_which.side_effect = lambda m: m in ("udevadm",) mydev = self.tmp_path("mydev") util.write_file(mydev, "foo\n") util.udevadm_settle(exists=mydev) > m_subp.called_once_with(["which", "udevadm"]) tests/unittests/test_util.py:888: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ self = <MagicMock name='which' id='140713300175728'>, name = 'called_once_with' def __getattr__(self, name): if name in {'_mock_methods', '_mock_unsafe'}: raise AttributeError(name) elif self._mock_methods is not None: if name not in self._mock_methods or name in _all_magics: raise AttributeError("Mock object has no attribute %r" % name) elif _is_magic(name): raise AttributeError(name) if not self._mock_unsafe and (not self._mock_methods or name not in self._mock_methods): if name.startswith(('assert', 'assret', 'asert', 'aseert', 'assrt')) or name in _ATTRIB_DENY_LIST: > raise AttributeError( f"{name!r} is not a valid assertion. Use a spec " f"for the mock if {name!r} is meant to be an attribute.") E AttributeError: 'called_once_with' is not a valid assertion. Use a spec for the mock if 'called_once_with' is meant to be an attribute.. Did you mean: 'assert_called_once_with'? /usr/lib64/python3.12/unittest/mock.py:657: AttributeError ------------------------------ Captured log call ------------------------------- 2023-05-09 11:30:38 DEBUG cloudinit.util:util.py:2204 Writing to /tmp/ci-TestUdevadmSettle.rb8h1_zm/mydev - wb: [644] 4 bytes ______________ TestUdevadmSettle.test_with_exists_and_not_exists _______________ self = <tests.unittests.test_util.TestUdevadmSettle testMethod=test_with_exists_and_not_exists> m_which = <MagicMock name='subp' id='140713317827216'> m_subp = <MagicMock name='which' id='140713317837104'> def test_with_exists_and_not_exists(self, m_which, m_subp): """with exists=file where file does not exist should invoke subp.""" m_which.side_effect = lambda m: m in ("udevadm",) mydev = self.tmp_path("mydev") util.udevadm_settle(exists=mydev) > m_subp.called_once_with( ["udevadm", "settle", "--exit-if-exists=%s" % mydev] ) tests/unittests/test_util.py:877: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ self = <MagicMock name='which' id='140713317837104'>, name = 'called_once_with' def __getattr__(self, name): if name in {'_mock_methods', '_mock_unsafe'}: raise AttributeError(name) elif self._mock_methods is not None: if name not in self._mock_methods or name in _all_magics: raise AttributeError("Mock object has no attribute %r" % name) elif _is_magic(name): raise AttributeError(name) if not self._mock_unsafe and (not self._mock_methods or name not in self._mock_methods): if name.startswith(('assert', 'assret', 'asert', 'aseert', 'assrt')) or name in _ATTRIB_DENY_LIST: > raise AttributeError( f"{name!r} is not a valid assertion. Use a spec " f"for the mock if {name!r} is meant to be an attribute.") E AttributeError: 'called_once_with' is not a valid assertion. Use a spec for the mock if 'called_once_with' is meant to be an attribute.. Did you mean: 'assert_called_once_with'? /usr/lib64/python3.12/unittest/mock.py:657: AttributeError ________________ TestUdevadmSettle.test_with_exists_and_timeout ________________ self = <tests.unittests.test_util.TestUdevadmSettle testMethod=test_with_exists_and_timeout> m_which = <MagicMock name='subp' id='140713300179664'> m_subp = <MagicMock name='which' id='140713300166272'> def test_with_exists_and_timeout(self, m_which, m_subp): """test call with both exists and timeout.""" m_which.side_effect = lambda m: m in ("udevadm",) mydev = self.tmp_path("mydev") timeout = "3" util.udevadm_settle(exists=mydev) > m_subp.called_once_with( [ "udevadm", "settle", "--exit-if-exists=%s" % mydev, "--timeout=%s" % timeout, ] ) tests/unittests/test_util.py:914: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ self = <MagicMock name='which' id='140713300166272'>, name = 'called_once_with' def __getattr__(self, name): if name in {'_mock_methods', '_mock_unsafe'}: raise AttributeError(name) elif self._mock_methods is not None: if name not in self._mock_methods or name in _all_magics: raise AttributeError("Mock object has no attribute %r" % name) elif _is_magic(name): raise AttributeError(name) if not self._mock_unsafe and (not self._mock_methods or name not in self._mock_methods): if name.startswith(('assert', 'assret', 'asert', 'aseert', 'assrt')) or name in _ATTRIB_DENY_LIST: > raise AttributeError( f"{name!r} is not a valid assertion. Use a spec " f"for the mock if {name!r} is meant to be an attribute.") E AttributeError: 'called_once_with' is not a valid assertion. Use a spec for the mock if 'called_once_with' is meant to be an attribute.. Did you mean: 'assert_called_once_with'? /usr/lib64/python3.12/unittest/mock.py:657: AttributeError ____________________ TestUdevadmSettle.test_with_no_params _____________________ self = <tests.unittests.test_util.TestUdevadmSettle testMethod=test_with_no_params> m_which = <MagicMock name='subp' id='140713319825184'> m_subp = <MagicMock name='which' id='140713321133168'> def test_with_no_params(self, m_which, m_subp): """called with no parameters.""" m_which.side_effect = lambda m: m in ("udevadm",) util.udevadm_settle() > m_subp.called_once_with(mock.call(["udevadm", "settle"])) tests/unittests/test_util.py:864: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ self = <MagicMock name='which' id='140713321133168'>, name = 'called_once_with' def __getattr__(self, name): if name in {'_mock_methods', '_mock_unsafe'}: raise AttributeError(name) elif self._mock_methods is not None: if name not in self._mock_methods or name in _all_magics: raise AttributeError("Mock object has no attribute %r" % name) elif _is_magic(name): raise AttributeError(name) if not self._mock_unsafe and (not self._mock_methods or name not in self._mock_methods): if name.startswith(('assert', 'assret', 'asert', 'aseert', 'assrt')) or name in _ATTRIB_DENY_LIST: > raise AttributeError( f"{name!r} is not a valid assertion. Use a spec " f"for the mock if {name!r} is meant to be an attribute.") E AttributeError: 'called_once_with' is not a valid assertion. Use a spec for the mock if 'called_once_with' is meant to be an attribute.. Did you mean: 'assert_called_once_with'? /usr/lib64/python3.12/unittest/mock.py:657: AttributeError ___________________ TestUdevadmSettle.test_with_timeout_int ____________________ self = <tests.unittests.test_util.TestUdevadmSettle testMethod=test_with_timeout_int> m_which = <MagicMock name='subp' id='140713300975424'> m_subp = <MagicMock name='which' id='140713300970336'> def test_with_timeout_int(self, m_which, m_subp): """timeout can be an integer.""" m_which.side_effect = lambda m: m in ("udevadm",) timeout = 9 util.udevadm_settle(timeout=timeout) > m_subp.called_once_with( ["udevadm", "settle", "--timeout=%s" % timeout] ) tests/unittests/test_util.py:895: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ self = <MagicMock name='which' id='140713300970336'>, name = 'called_once_with' def __getattr__(self, name): if name in {'_mock_methods', '_mock_unsafe'}: raise AttributeError(name) elif self._mock_methods is not None: if name not in self._mock_methods or name in _all_magics: raise AttributeError("Mock object has no attribute %r" % name) elif _is_magic(name): raise AttributeError(name) if not self._mock_unsafe and (not self._mock_methods or name not in self._mock_methods): if name.startswith(('assert', 'assret', 'asert', 'aseert', 'assrt')) or name in _ATTRIB_DENY_LIST: > raise AttributeError( f"{name!r} is not a valid assertion. Use a spec " f"for the mock if {name!r} is meant to be an attribute.") E AttributeError: 'called_once_with' is not a valid assertion. Use a spec for the mock if 'called_once_with' is meant to be an attribute.. Did you mean: 'assert_called_once_with'? /usr/lib64/python3.12/unittest/mock.py:657: AttributeError __________________ TestUdevadmSettle.test_with_timeout_string __________________ self = <tests.unittests.test_util.TestUdevadmSettle testMethod=test_with_timeout_string> m_which = <MagicMock name='subp' id='140713317872896'> m_subp = <MagicMock name='which' id='140713317903504'> def test_with_timeout_string(self, m_which, m_subp): """timeout can be a string.""" m_which.side_effect = lambda m: m in ("udevadm",) timeout = "555" util.udevadm_settle(timeout=timeout) > m_subp.called_once_with( ["udevadm", "settle", "--timeout=%s" % timeout] ) tests/unittests/test_util.py:904: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ self = <MagicMock name='which' id='140713317903504'>, name = 'called_once_with' def __getattr__(self, name): if name in {'_mock_methods', '_mock_unsafe'}: raise AttributeError(name) elif self._mock_methods is not None: if name not in self._mock_methods or name in _all_magics: raise AttributeError("Mock object has no attribute %r" % name) elif _is_magic(name): raise AttributeError(name) if not self._mock_unsafe and (not self._mock_methods or name not in self._mock_methods): if name.startswith(('assert', 'assret', 'asert', 'aseert', 'assrt')) or name in _ATTRIB_DENY_LIST: > raise AttributeError( f"{name!r} is not a valid assertion. Use a spec " f"for the mock if {name!r} is meant to be an attribute.") E AttributeError: 'called_once_with' is not a valid assertion. Use a spec for the mock if 'called_once_with' is meant to be an attribute.. Did you mean: 'assert_called_once_with'? /usr/lib64/python3.12/unittest/mock.py:657: AttributeError _ TestEphemeralDhcpNoNetworkSetup.test_ephemeral_dhcp_setup_network_if_url_connectivity _ self = <tests.unittests.net.test_dhcp.TestEphemeralDhcpNoNetworkSetup testMethod=test_ephemeral_dhcp_setup_network_if_url_connectivity> m_dhcp = <MagicMock name='maybe_perform_dhcp_discovery' id='140713283780144'> m_subp = <MagicMock name='subp' id='140713287435424'> @mock.patch("cloudinit.net.dhcp.subp.subp") @mock.patch("cloudinit.net.ephemeral.maybe_perform_dhcp_discovery") def test_ephemeral_dhcp_setup_network_if_url_connectivity( self, m_dhcp, m_subp ): """No EphemeralDhcp4 network setup when connectivity_url succeeds.""" url = "http://example.org/index.html" fake_lease = { "interface": "eth9", "fixed-address": "192.168.2.2", "subnet-mask": "255.255.0.0", } m_dhcp.return_value = [fake_lease] m_subp.return_value = ("", "") self.responses.add(responses.GET, url, body=b"", status=404) with EphemeralDHCPv4( connectivity_url_data={"url": url}, ) as lease: self.assertEqual(fake_lease, lease) # Ensure that dhcp discovery occurs > m_dhcp.called_once_with() tests/unittests/net/test_dhcp.py:708: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ self = <MagicMock name='maybe_perform_dhcp_discovery' id='140713283780144'> name = 'called_once_with' def __getattr__(self, name): if name in {'_mock_methods', '_mock_unsafe'}: raise AttributeError(name) elif self._mock_methods is not None: if name not in self._mock_methods or name in _all_magics: raise AttributeError("Mock object has no attribute %r" % name) elif _is_magic(name): raise AttributeError(name) if not self._mock_unsafe and (not self._mock_methods or name not in self._mock_methods): if name.startswith(('assert', 'assret', 'asert', 'aseert', 'assrt')) or name in _ATTRIB_DENY_LIST: > raise AttributeError( f"{name!r} is not a valid assertion. Use a spec " f"for the mock if {name!r} is meant to be an attribute.") E AttributeError: 'called_once_with' is not a valid assertion. Use a spec for the mock if 'called_once_with' is meant to be an attribute.. Did you mean: 'assert_called_once_with'? /usr/lib64/python3.12/unittest/mock.py:657: AttributeError ----------------------------- Captured stdout call ----------------------------- FALLBACK: 2023-05-09 11:30:49,910 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,910 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,910 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,910 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,910 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration 2023-05-09 11:30:49,910 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration DEBUG: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration DEBUG: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,911 - ephemeral.py[DEBUG]: Received dhcp lease on eth9 for 192.168.2.2/255.255.0.0 FALLBACK: 2023-05-09 11:30:49,911 - ephemeral.py[DEBUG]: Received dhcp lease on eth9 for 192.168.2.2/255.255.0.0 FALLBACK: 2023-05-09 11:30:49,911 - ephemeral.py[DEBUG]: Received dhcp lease on eth9 for 192.168.2.2/255.255.0.0 FALLBACK: 2023-05-09 11:30:49,911 - ephemeral.py[DEBUG]: Received dhcp lease on eth9 for 192.168.2.2/255.255.0.0 FALLBACK: 2023-05-09 11:30:49,911 - ephemeral.py[DEBUG]: Received dhcp lease on eth9 for 192.168.2.2/255.255.0.0 2023-05-09 11:30:49,911 - ephemeral.py[DEBUG]: Received dhcp lease on eth9 for 192.168.2.2/255.255.0.0 DEBUG: Received dhcp lease on eth9 for 192.168.2.2/255.255.0.0 DEBUG: Received dhcp lease on eth9 for 192.168.2.2/255.255.0.0 FALLBACK: 2023-05-09 11:30:49,911 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,911 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,911 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,911 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,911 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration 2023-05-09 11:30:49,911 - url_helper.py[DEBUG]: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration DEBUG: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration DEBUG: [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration FALLBACK: 2023-05-09 11:30:49,912 - ephemeral.py[DEBUG]: Attempting setup of ephemeral network on eth9 with 192.168.2.2/16 brd 192.168.255.255 FALLBACK: 2023-05-09 11:30:49,912 - ephemeral.py[DEBUG]: Attempting setup of ephemeral network on eth9 with 192.168.2.2/16 brd 192.168.255.255 FALLBACK: 2023-05-09 11:30:49,912 - ephemeral.py[DEBUG]: Attempting setup of ephemeral network on eth9 with 192.168.2.2/16 brd 192.168.255.255 FALLBACK: 2023-05-09 11:30:49,912 - ephemeral.py[DEBUG]: Attempting setup of ephemeral network on eth9 with 192.168.2.2/16 brd 192.168.255.255 FALLBACK: 2023-05-09 11:30:49,912 - ephemeral.py[DEBUG]: Attempting setup of ephemeral network on eth9 with 192.168.2.2/16 brd 192.168.255.255 2023-05-09 11:30:49,912 - ephemeral.py[DEBUG]: Attempting setup of ephemeral network on eth9 with 192.168.2.2/16 brd 192.168.255.255 DEBUG: Attempting setup of ephemeral network on eth9 with 192.168.2.2/16 brd 192.168.255.255 DEBUG: Attempting setup of ephemeral network on eth9 with 192.168.2.2/16 brd 192.168.255.255 ------------------------------ Captured log call ------------------------------- 2023-05-09 11:30:49 DEBUG cloudinit.url_helper:url_helper.py:305 [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration 2023-05-09 11:30:49 DEBUG cloudinit.net.ephemeral:ephemeral.py:369 Received dhcp lease on eth9 for 192.168.2.2/255.255.0.0 2023-05-09 11:30:49 DEBUG cloudinit.url_helper:url_helper.py:305 [0/1] open 'http://example.org/index.html' with {'url': 'http://example.org/index.html', 'stream': False, 'allow_redirects': True, 'method': 'GET', 'timeout': 5.0, 'headers': {'User-Agent': 'Cloud-Init/23.1.2'}} configuration 2023-05-09 11:30:49 DEBUG cloudinit.net.ephemeral:ephemeral.py:129 Attempting setup of ephemeral network on eth9 with 192.168.2.2/16 brd 192.168.255.255 =============================== warnings summary =============================== ../../../../usr/lib/python3.12/site-packages/_pytest/config/__init__.py:1248 /usr/lib/python3.12/site-packages/_pytest/config/__init__.py:1248: PytestRemovedIn8Warning: The --strict option is deprecated, use --strict-markers instead. self.issue_config_time_warning( cloudinit/sources/DataSourceAzure.py:8 /builddir/build/BUILD/cloud-init-23.1.2/cloudinit/sources/DataSourceAzure.py:8: DeprecationWarning: 'crypt' is deprecated and slated for removal in Python 3.13 import crypt cloudinit/distros/parsers/sys_conf.py:7 /builddir/build/BUILD/cloud-init-23.1.2/cloudinit/distros/parsers/sys_conf.py:7: DeprecationWarning: 'pipes' is deprecated and slated for removal in Python 3.13 import pipes tests/unittests/test_ds_identify.py::TestDsIdentify::test_ibmcloud_template_no_userdata_in_provisioning /usr/lib64/python3.12/unittest/case.py:690: DeprecationWarning: It is deprecated to return a value that is not None from a test case (<bound method TestDsIdentify.test_ibmcloud_template_no_userdata_in_provisioning of <tests.unittests.test_ds_identify.TestDsIdentify testMethod=test_ibmcloud_template_no_userdata_in_provisioning>>) return self.run(*args, **kwds) tests/unittests/test_ds_identify.py::TestDsIdentify::test_ibmcloud_template_userdata_in_provisioning /usr/lib64/python3.12/unittest/case.py:690: DeprecationWarning: It is deprecated to return a value that is not None from a test case (<bound method TestDsIdentify.test_ibmcloud_template_userdata_in_provisioning of <tests.unittests.test_ds_identify.TestDsIdentify testMethod=test_ibmcloud_template_userdata_in_provisioning>>) return self.run(*args, **kwds) tests/unittests/test_ds_identify.py::TestDsIdentify::test_vmware_on_vmware_open_vm_tools_64 /usr/lib64/python3.12/unittest/case.py:690: DeprecationWarning: It is deprecated to return a value that is not None from a test case (<bound method TestDsIdentify.test_vmware_on_vmware_open_vm_tools_64 of <tests.unittests.test_ds_identify.TestDsIdentify testMethod=test_vmware_on_vmware_open_vm_tools_64>>) return self.run(*args, **kwds) tests/unittests/test_ds_identify.py::TestDsIdentify::test_vmware_on_vmware_open_vm_tools_aarch64_linux_gnu /usr/lib64/python3.12/unittest/case.py:690: DeprecationWarning: It is deprecated to return a value that is not None from a test case (<bound method TestDsIdentify.test_vmware_on_vmware_open_vm_tools_aarch64_linux_gnu of <tests.unittests.test_ds_identify.TestDsIdentify testMethod=test_vmware_on_vmware_open_vm_tools_aarch64_linux_gnu>>) return self.run(*args, **kwds) tests/unittests/test_ds_identify.py::TestDsIdentify::test_vmware_on_vmware_open_vm_tools_x86_64_linux_gnu /usr/lib64/python3.12/unittest/case.py:690: DeprecationWarning: It is deprecated to return a value that is not None from a test case (<bound method TestDsIdentify.test_vmware_on_vmware_open_vm_tools_x86_64_linux_gnu of <tests.unittests.test_ds_identify.TestDsIdentify testMethod=test_vmware_on_vmware_open_vm_tools_x86_64_linux_gnu>>) return self.run(*args, **kwds) tests/unittests/cmd/test_main.py: 8 warnings tests/unittests/config/test_cc_apt_pipelining.py: 4 warnings tests/unittests/config/test_cc_bootcmd.py: 1 warning tests/unittests/config/test_cc_growpart.py: 1 warning tests/unittests/config/test_cc_grub_dpkg.py: 1 warning tests/unittests/config/test_cc_mcollective.py: 2 warnings tests/unittests/config/test_cc_mounts.py: 12 warnings tests/unittests/config/test_cc_power_state_change.py: 5 warnings tests/unittests/config/test_cc_runcmd.py: 9 warnings tests/unittests/config/test_cc_scripts_vendor.py: 2 warnings tests/unittests/config/test_cc_set_passwords.py: 3 warnings tests/unittests/config/test_cc_snap.py: 3 warnings tests/unittests/config/test_cc_update_etc_hosts.py: 3 warnings tests/unittests/config/test_cc_users_groups.py: 28 warnings tests/unittests/config/test_schema.py: 163 warnings tests/unittests/reporting/test_reporting.py: 19 warnings /builddir/build/BUILD/cloud-init-23.1.2/cloudinit/config/schema.py:375: DeprecationWarning: Passing a schema to Validator.iter_errors is deprecated and will be removed in a future release. Call validator.evolve(schema=new_schema).iter_errors(...) instead. return next(errors, None) is None tests/unittests/sources/test_azure.py: 71 warnings tests/unittests/sources/test_azure_helper.py: 17 warnings /builddir/build/BUILD/cloud-init-23.1.2/cloudinit/sources/helpers/azure.py:1152: DeprecationWarning: Testing an element's truth value will raise an exception in future versions. Use specific 'len(elem)' or 'elem is not None' test instead. if not root.find("./wa:ProvisioningSection", cls.NAMESPACES): -- Docs: https://docs.pytest.org/en/stable/how-to/capture-warnings.html =========================== short test summary info ============================ FAILED tests/unittests/test_url_helper.py::TestDualStack::test_dual_stack[<lambda>-addresses1-1-0-None] FAILED tests/unittests/test_util.py::TestUdevadmSettle::test_udevadm_not_present FAILED tests/unittests/test_util.py::TestUdevadmSettle::test_with_exists_and_file_exists FAILED tests/unittests/test_util.py::TestUdevadmSettle::test_with_exists_and_not_exists FAILED tests/unittests/test_util.py::TestUdevadmSettle::test_with_exists_and_timeout FAILED tests/unittests/test_util.py::TestUdevadmSettle::test_with_no_params FAILED tests/unittests/test_util.py::TestUdevadmSettle::test_with_timeout_int FAILED tests/unittests/test_util.py::TestUdevadmSettle::test_with_timeout_string FAILED tests/unittests/net/test_dhcp.py::TestEphemeralDhcpNoNetworkSetup::test_ephemeral_dhcp_setup_network_if_url_connectivity =========== 9 failed, 4571 passed, 5 skipped, 360 warnings in 40.42s =========== All test failures except for test_dual_stack can be fixed with this commit: https://github.com/canonical/cloud-init/commit/e3f1ec3f57cc1f5eacff9506d285007966414481 https://docs.python.org/3.12/whatsnew/3.12.html For the build logs, see: https://copr-be.cloud.fedoraproject.org/results/@python/python3.12/fedora-rawhide-x86_64/05900415-cloud-init/ For all our attempts to build cloud-init with Python 3.12, see: https://copr.fedorainfracloud.org/coprs/g/python/python3.12/package/cloud-init/ Testing and mass rebuild of packages is happening in copr. You can follow these instructions to test locally in mock if your package builds with Python 3.12: https://copr.fedorainfracloud.org/coprs/g/python/python3.12/ Let us know here if you have any questions. Python 3.12 is planned to be included in Fedora 39. To make that update smoother, we're building Fedora packages with all pre-releases of Python 3.12. A build failure prevents us from testing all dependent packages (transitive [Build]Requires), so if this package is required a lot, it's important for us to get it fixed soon. We'd appreciate help from the people who know this package best, but if you don't want to work on this now, let us know so we can try to work around it on our side.
Tomáš: Thanks for the ticket, but I'm a bit lost on how to get this fixed. I'm happy to open an issue with upstream, though.
@
This should be okay now, Tomáš. Want to verify? https://src.fedoraproject.org/rpms/cloud-init/c/1ddecd3a8bc2f7a6ad4df243ec7daa2a83c7a024?branch=rawhide https://copr.fedorainfracloud.org/coprs/g/python/python3.12/build/6104851/
Thank you! I've tried to do a scratch build in f39-python side-tag, but it seems like some deps are not yet ready. We will submit the build once they are.
This one is good to go now.