Bug 1939 fixed: : added a random suffix to the end of the Juju app name, in order... 91/11791/4
authorPedro Escaleira <escaleira@av.it.pt>
Mon, 21 Mar 2022 17:54:45 +0000 (17:54 +0000)
committergarciadav <david.garcia@canonical.com>
Fri, 22 Apr 2022 16:03:06 +0000 (18:03 +0200)
I followed the second option of the bug's description. Now, Juju
applications have a random suffix with size=5 (the random suffix
size used by K8s), in order to avoid collisions between applications'
names;

Also fixed unit-test on test_n2vc_juju_conn.py

Change-Id: I5d3eb8282889e58361f7c21214b11071a7530d26
Signed-off-by: Pedro Escaleira <escaleira@av.it.pt>
n2vc/n2vc_juju_conn.py
n2vc/tests/unit/test_n2vc_juju_conn.py
n2vc/utils.py

index 55220d6..4efbd1c 100644 (file)
@@ -39,7 +39,7 @@ from n2vc.n2vc_conn import N2VCConnector
 from n2vc.n2vc_conn import obj_to_dict, obj_to_yaml
 from n2vc.libjuju import Libjuju
 from n2vc.store import MotorStore
-from n2vc.utils import get_ee_id_components
+from n2vc.utils import get_ee_id_components, generate_random_alfanum_string
 from n2vc.vca.connection import get_connection
 from retrying_async import retry
 
@@ -1140,7 +1140,7 @@ class N2VCJujuConnector(N2VCConnector):
         """
         Build application name from namespace
         :param namespace:
-        :return: app-vnf-<vnf id>-vdu-<vdu-id>-cnt-<vdu-count>
+        :return: app-vnf-<vnf id>-vdu-<vdu-id>-cnt-<vdu-count>-<random_value>
         """
 
         # TODO: Enforce the Juju 50-character application limit
@@ -1167,7 +1167,12 @@ class N2VCJujuConnector(N2VCConnector):
         else:
             vdu_count = "-cnt-" + vdu_count
 
-        application_name = "app-{}{}{}".format(vnf_id, vdu_id, vdu_count)
+        # Generate a random suffix with 5 characters (the default size used by K8s)
+        random_suffix = generate_random_alfanum_string(size=5)
+
+        application_name = "app-{}{}{}-{}".format(
+            vnf_id, vdu_id, vdu_count, random_suffix
+        )
 
         return N2VCJujuConnector._format_app_name(application_name)
 
index 2475d01..3caae03 100644 (file)
@@ -16,6 +16,7 @@
 import asyncio
 import logging
 from unittest.mock import Mock
+from unittest.mock import patch
 
 
 import asynctest
@@ -144,8 +145,13 @@ class K8sProxyCharmsTest(N2VCJujuConnTestCase):
         self.n2vc.libjuju.deploy_charm = AsyncMock()
         self.n2vc.libjuju.model_exists.return_value = False
 
+    @patch(
+        "n2vc.n2vc_juju_conn.generate_random_alfanum_string",
+        **{"return_value": "random"}
+    )
     def test_success(
         self,
+        mock_generate_random_alfanum_string,
         mock_path,
         mock_file_exists,
     ):
@@ -163,7 +169,7 @@ class K8sProxyCharmsTest(N2VCJujuConnTestCase):
         self.n2vc.libjuju.add_model.assert_called_once()
         self.n2vc.libjuju.deploy_charm.assert_called_once_with(
             model_name="ns-id-k8s",
-            application_name="app-vnf-vnf-id-vdu-vdu",
+            application_name="app-vnf-vnf-id-vdu-vdu-random",
             path="/path/path/",
             machine_id=None,
             db_dict={},
@@ -171,7 +177,7 @@ class K8sProxyCharmsTest(N2VCJujuConnTestCase):
             total_timeout=None,
             config=None,
         )
-        self.assertEqual(ee_id, "ns-id-k8s.app-vnf-vnf-id-vdu-vdu.k8s")
+        self.assertEqual(ee_id, "ns-id-k8s.app-vnf-vnf-id-vdu-vdu-random.k8s")
 
     def test_no_artifact_path(
         self,
index a661e05..286f0fc 100644 (file)
@@ -16,6 +16,8 @@ import base64
 import re
 import binascii
 import yaml
+import string
+import secrets
 from enum import Enum
 from juju.machine import Machine
 from juju.application import Application
@@ -163,3 +165,15 @@ def get_ee_id_components(ee_id: str) -> Tuple[str, str, str]:
     application_name = parts[1]
     machine_id = parts[2]
     return model_name, application_name, machine_id
+
+
+def generate_random_alfanum_string(size: int) -> str:
+    """
+    Generate random alfa-numeric string with a size given by argument
+    :param size:
+    :return: random generated string
+    """
+
+    return "".join(
+        secrets.choice(string.ascii_letters + string.digits) for i in range(size)
+    )