Merge ~cgrabowski/maas:vault-proxy into maas:master

Proposed by Christian Grabowski
Status: Rejected
Rejected by: Adam Collard
Proposed branch: ~cgrabowski/maas:vault-proxy
Merge into: maas:master
Diff against target: 172 lines (+81/-11)
2 files modified
src/maasserver/bootsources.py (+36/-10)
src/maasserver/tests/test_bootsources.py (+45/-1)
Reviewer Review Type Date Requested Status
Adam Collard (community) Disapprove
MAAS Lander Needs Fixing
Review via email: mp+435400@code.launchpad.net

Commit message

account for no_proxy set on test host

LP:2002111 manage no_proxy better in bootsources
Signed-off-by: Adam Collard <email address hidden>

To post a comment you must log in.
Revision history for this message
MAAS Lander (maas-lander) wrote :

UNIT TESTS
-b vault-proxy lp:~cgrabowski/maas/+git/maas into -b master lp:~maas-committers/maas

STATUS: FAILED
LOG: http://maas-ci.internal:8080/job/maas-tester/1725/consoleText
COMMIT: b1c3a662782de5fd08cf1cb326723943838a9c9f

review: Needs Fixing
Revision history for this message
Adam Collard (adam-collard) wrote :

Thanks for trying to get this over the line - i hadn't seen this branch when i pushed a revised commit on my branch - https://code.launchpad.net/~adam-collard/maas/+git/maas/+merge/435387

I took the approach of patching out no_proxy in the environ before running the tests.

review: Disapprove

Unmerged commits

b1c3a66... by Christian Grabowski

account for no_proxy set on test host

0a04d97... by Adam Collard

LP:2002111 manage no_proxy better in bootsources

Signed-off-by: Adam Collard <email address hidden>

Update scan failed

At least one of the branches involved have failed to scan. You can manually schedule a rescan if required.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
diff --git a/src/maasserver/bootsources.py b/src/maasserver/bootsources.py
index c58b19a..58c6cb7 100644
--- a/src/maasserver/bootsources.py
+++ b/src/maasserver/bootsources.py
@@ -97,6 +97,15 @@ def get_boot_sources():
97 return [source.to_dict() for source in BootSource.objects.all()]97 return [source.to_dict() for source in BootSource.objects.all()]
9898
9999
100def _upsert_no_proxy_env(env, entry):
101 """Updates $no_proxy appropriately."""
102 if no_proxy := env.get("no_proxy"):
103 if entry not in no_proxy.split(","):
104 env["no_proxy"] = f"{no_proxy},{entry}"
105 else:
106 env["no_proxy"] = entry
107
108
100@transactional109@transactional
101def get_simplestreams_env():110def get_simplestreams_env():
102 """Get environment that should be used with simplestreams."""111 """Get environment that should be used with simplestreams."""
@@ -106,24 +115,28 @@ def get_simplestreams_env():
106 if http_proxy is not None:115 if http_proxy is not None:
107 env["http_proxy"] = http_proxy116 env["http_proxy"] = http_proxy
108 env["https_proxy"] = http_proxy117 env["https_proxy"] = http_proxy
118 if no_proxy := os.environ.get("no_proxy"):
119 env["no_proxy"] = no_proxy
109 # When the proxy environment variables are set they effect the120 # When the proxy environment variables are set they effect the
110 # entire process, including controller refresh. When the region121 # entire process, including controller refresh. When the region
111 # needs to refresh itself it sends itself results over HTTP to122 # needs to refresh itself it sends itself results over HTTP to
112 # 127.0.0.1.123 # 127.0.0.1.
113 no_proxy_hosts = "127.0.0.1,localhost"124 no_proxy_hosts = ["127.0.0.1", "localhost"]
114 # When using a proxy and using an image mirror, we may not want125 # When using a proxy and using an image mirror, we may not want
115 # to use the proxy to download the images, as they could be126 # to use the proxy to download the images, as they could be
116 # located in the local network, hence it makes no sense to use127 # located in the local network, hence it makes no sense to use
117 # it. With this, we add the image mirror location(s) to the128 # it. With this, we add the image mirror location(s) to the
118 # no proxy variable, which ensures MAAS contacts the mirror129 # no proxy variable, which ensures MAAS contacts the mirror
119 # directly instead of through the proxy.130 # directly instead of through the proxy.
120 no_proxy = Config.objects.get_config("boot_images_no_proxy")131 if Config.objects.get_config("boot_images_no_proxy"):
121 if no_proxy:132 no_proxy_hosts.extend(
122 sources = get_boot_sources()133 [
123 for source in sources:134 urlparse(source["url"]).hostname
124 host = urlparse(source["url"]).netloc.split(":")[0]135 for source in get_boot_sources()
125 no_proxy_hosts = ",".join((no_proxy_hosts, host))136 ]
126 env["no_proxy"] = no_proxy_hosts137 )
138 for host in no_proxy_hosts:
139 _upsert_no_proxy_env(env, host)
127 else:140 else:
128 # The proxy is disabled, let's not accidentally use proxy from141 # The proxy is disabled, let's not accidentally use proxy from
129 # encompassing environment.142 # encompassing environment.
@@ -134,12 +147,24 @@ def get_simplestreams_env():
134147
135def set_simplestreams_env():148def set_simplestreams_env():
136 """Set the environment that simplestreams needs."""149 """Set the environment that simplestreams needs."""
150 bodged_env = get_simplestreams_env()
151 pristine_env = {k: os.environ.get(k) for k in bodged_env}
137 # We simply set the env variables here as another simplestreams-based152 # We simply set the env variables here as another simplestreams-based
138 # import might be running concurrently (bootresources._import_resources)153 # import might be running concurrently (bootresources._import_resources)
139 # and we don't want to use the environment_variables context manager that154 # and we don't want to use the environment_variables context manager that
140 # would reset the environment variables (they are global to the entire155 # would reset the environment variables (they are global to the entire
141 # process) while the other import is still running.156 # process) while the other import is still running.
142 os.environ.update(get_simplestreams_env())157 os.environ.update(bodged_env)
158 return pristine_env
159
160
161def restore_pristine_env(pristine_env):
162 """Restored the environment that simplestreams needs' bodged."""
163 for key, value in pristine_env.items():
164 if value is None and key in os.environ:
165 del os.environ[key]
166 else:
167 os.environ[key] = value
143168
144169
145def get_os_info_from_boot_sources(os):170def get_os_info_from_boot_sources(os):
@@ -353,7 +378,7 @@ def cache_boot_sources():
353378
354 # FIXME: This modifies the environment of the entire process, which is Not379 # FIXME: This modifies the environment of the entire process, which is Not
355 # Cool. We should integrate with simplestreams in a more Pythonic manner.380 # Cool. We should integrate with simplestreams in a more Pythonic manner.
356 yield deferToDatabase(set_simplestreams_env)381 pristine_env = yield deferToDatabase(set_simplestreams_env)
357382
358 errors = []383 errors = []
359 sources = yield deferToDatabase(get_sources)384 sources = yield deferToDatabase(get_sources)
@@ -392,6 +417,7 @@ def cache_boot_sources():
392 else:417 else:
393 yield deferToDatabase(_update_cache, source, descriptions)418 yield deferToDatabase(_update_cache, source, descriptions)
394419
420 yield deferToDatabase(restore_pristine_env, pristine_env)
395 yield deferToDatabase(check_commissioning_series_selected)421 yield deferToDatabase(check_commissioning_series_selected)
396422
397 component = COMPONENT.REGION_IMAGE_IMPORT423 component = COMPONENT.REGION_IMAGE_IMPORT
diff --git a/src/maasserver/tests/test_bootsources.py b/src/maasserver/tests/test_bootsources.py
index b37e025..bc2534d 100644
--- a/src/maasserver/tests/test_bootsources.py
+++ b/src/maasserver/tests/test_bootsources.py
@@ -365,8 +365,11 @@ class TestPrivateCacheBootSources(MAASTransactionServerTestCase):
365 )365 )
366 factory.make_BootSource(keyring_data=b"1234")366 factory.make_BootSource(keyring_data=b"1234")
367 cache_boot_sources()367 cache_boot_sources()
368 no_proxy_hosts = "127.0.0.1,localhost"
369 if environ.get("no_proxy"):
370 no_proxy_hosts = f"{environ['no_proxy']},{no_proxy_hosts}"
368 self.assertEqual(371 self.assertEqual(
369 (proxy_address, proxy_address, "127.0.0.1,localhost"),372 (proxy_address, proxy_address, no_proxy_hosts),
370 (373 (
371 capture.env["http_proxy"],374 capture.env["http_proxy"],
372 capture.env["https_proxy"],375 capture.env["https_proxy"],
@@ -386,6 +389,8 @@ class TestPrivateCacheBootSources(MAASTransactionServerTestCase):
386 )389 )
387 cache_boot_sources()390 cache_boot_sources()
388 no_proxy_hosts = "127.0.0.1,localhost,192.168.1.100"391 no_proxy_hosts = "127.0.0.1,localhost,192.168.1.100"
392 if environ.get("no_proxy"):
393 no_proxy_hosts = f"{environ['no_proxy']},{no_proxy_hosts}"
389 self.assertEqual(394 self.assertEqual(
390 (proxy_address, proxy_address, no_proxy_hosts),395 (proxy_address, proxy_address, no_proxy_hosts),
391 (396 (
@@ -395,6 +400,45 @@ class TestPrivateCacheBootSources(MAASTransactionServerTestCase):
395 ),400 ),
396 )401 )
397402
403 def test_retains_existing_no_proxy(self):
404 proxy_address = factory.make_name("proxy")
405 Config.objects.set_config("http_proxy", proxy_address)
406 Config.objects.set_config("boot_images_no_proxy", True)
407 capture = patch_and_capture_env_for_download_all_image_descriptions(
408 self
409 )
410 factory.make_BootSource(
411 keyring_data=b"1234", url="http://192.168.1.100:8080/ephemeral-v3/"
412 )
413 with patch.dict("os.environ", {"no_proxy": "http://my.direct.host"}):
414 cache_boot_sources()
415 no_proxy_hosts = (
416 "http://my.direct.host,127.0.0.1,localhost,192.168.1.100"
417 )
418 self.assertEqual(no_proxy_hosts, capture.env["no_proxy"])
419
420 def test_restores_proxy_settings_post_call(self):
421 proxy_address = factory.make_name("proxy")
422 Config.objects.set_config("http_proxy", proxy_address)
423 Config.objects.set_config("boot_images_no_proxy", True)
424 mock_download = self.patch(
425 bootsources, "download_all_image_descriptions"
426 )
427 mock_download.return_value = make_boot_image_mapping()
428
429 with patch.dict(
430 "os.environ",
431 {
432 "no_proxy": "my.no_proxy",
433 "http_proxy": "my.http_proxy",
434 "https_proxy": "my.https_proxy",
435 },
436 ):
437 cache_boot_sources()
438 self.assertEqual(environ.get("no_proxy"), "my.no_proxy")
439 self.assertEqual(environ.get("http_proxy"), "my.http_proxy")
440 self.assertEqual(environ.get("https_proxy"), "my.https_proxy")
441
398 def test_passes_user_agent_with_maas_version(self):442 def test_passes_user_agent_with_maas_version(self):
399 mock_download = self.patch(443 mock_download = self.patch(
400 bootsources, "download_all_image_descriptions"444 bootsources, "download_all_image_descriptions"

Subscribers

People subscribed via source and target branches