]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
mgr/cephadm: specify ports for iscsi 49918/head
authorAdam King <adking@redhat.com>
Thu, 6 Oct 2022 18:36:52 +0000 (14:36 -0400)
committerAdam King <adking@redhat.com>
Tue, 31 Jan 2023 22:58:49 +0000 (17:58 -0500)
Fixes: https://tracker.ceph.com/issues/57786
Signed-off-by: Adam King <adking@redhat.com>
(cherry picked from commit 9ee9c940a7d7481a090a2e986753ca7db4fa521e)

src/cephadm/cephadm
src/pybind/mgr/cephadm/tests/test_services.py
src/python-common/ceph/deployment/service_spec.py

index d6965594669fca6a70648bbed9943d9a36f35adb..5c1f1c6cb11c9a86468154cfae9f2d1d5a998642 100755 (executable)
@@ -2969,7 +2969,7 @@ def deploy_daemon(ctx, fsid, daemon_type, daemon_id, c, uid, gid,
     # Open ports explicitly required for the daemon
     if ports:
         fw = Firewalld(ctx)
-        fw.open_ports(ports)
+        fw.open_ports(ports + fw.external_ports.get(daemon_type, []))
         fw.apply_rules()
 
     if reconfig and daemon_type not in Ceph.daemons:
@@ -3198,6 +3198,18 @@ def deploy_daemon_units(
 
 
 class Firewalld(object):
+
+    # for specifying ports we should always open when opening
+    # ports for a daemon of that type. Main use case is for ports
+    # that we should open when deploying the daemon type but that
+    # the daemon itself may not necessarily need to bind to the port.
+    # This needs to be handed differently as we don't want to fail
+    # deployment if the port cannot be bound to but we still want to
+    # open the port in the firewall.
+    external_ports: Dict[str, List[int]] = {
+        'iscsi': [3260]  # 3260 is the well known iSCSI port
+    }
+
     def __init__(self, ctx):
         # type: (CephadmContext) -> None
         self.ctx = ctx
index 57cd12456aaf8fd483cfd20fb60bacec1e247f00..2c90dc5139fa897ed1c39b9e43c150a3459259fe 100644 (file)
@@ -235,6 +235,54 @@ class TestISCSIService:
 
         assert dashboard_expected_call in self.mgr.check_mon_command.mock_calls
 
+    @patch("cephadm.serve.CephadmServe._run_cephadm")
+    @patch("cephadm.module.CephadmOrchestrator.get_unique_name")
+    @patch("cephadm.services.iscsi.IscsiService.get_trusted_ips")
+    def test_iscsi_config(self, _get_trusted_ips, _get_name, _run_cephadm, cephadm_module: CephadmOrchestrator):
+
+        iscsi_daemon_id = 'testpool.test.qwert'
+        trusted_ips = '1.1.1.1,2.2.2.2'
+        api_port = 3456
+        api_user = 'test-user'
+        api_password = 'test-password'
+        pool = 'testpool'
+        _run_cephadm.return_value = ('{}', '', 0)
+        _get_name.return_value = iscsi_daemon_id
+        _get_trusted_ips.return_value = trusted_ips
+
+        iscsi_gateway_conf = f"""# This file is generated by cephadm.
+[config]
+cluster_client_name = client.iscsi.{iscsi_daemon_id}
+pool = {pool}
+trusted_ip_list = {trusted_ips}
+minimum_gateways = 1
+api_port = {api_port}
+api_user = {api_user}
+api_password = {api_password}
+api_secure = False
+log_to_stderr = True
+log_to_stderr_prefix = debug
+log_to_file = False"""
+
+        with with_host(cephadm_module, 'test'):
+            with with_service(cephadm_module, IscsiServiceSpec(service_id=pool,
+                                                               api_port=api_port,
+                                                               api_user=api_user,
+                                                               api_password=api_password,
+                                                               pool=pool,
+                                                               trusted_ip_list=trusted_ips)):
+                _run_cephadm.assert_called_with(
+                    'test',
+                    f'iscsi.{iscsi_daemon_id}',
+                    'deploy',
+                    [
+                        '--name', f'iscsi.{iscsi_daemon_id}',
+                        '--meta-json', f'{"{"}"service_name": "iscsi.{pool}", "ports": [{api_port}], "ip": null, "deployed_by": [], "rank": null, "rank_generation": null, "extra_container_args": null{"}"}',
+                        '--config-json', '-', '--tcp-ports', '3456'
+                    ],
+                    stdin=json.dumps({"config": "", "keyring": "", "files": {"iscsi-gateway.cfg": iscsi_gateway_conf}}),
+                    image='')
+
 
 class TestMonitoring:
     def _get_config(self, url: str) -> str:
index 17130ea9a379c83b6d8286c9499117144fea4e61..53c0b674029674ba869b94f27e6962ccfd616217 100644 (file)
@@ -898,6 +898,9 @@ class IscsiServiceSpec(ServiceSpec):
         if not self.api_secure and self.ssl_cert and self.ssl_key:
             self.api_secure = True
 
+    def get_port_start(self) -> List[int]:
+        return [self.api_port or 5000]
+
     def validate(self) -> None:
         super(IscsiServiceSpec, self).validate()