This is an automated email from the ASF dual-hosted git repository. wuzhiguo pushed a commit to branch trunk in repository https://gitbox.apache.org/repos/asf/ambari.git
The following commit(s) were added to refs/heads/trunk by this push: new 011e752b6a AMBARI-25186: Kerberos Client is unnecessarily installed via Blueprints when kerberos-env/kdc-type is none (#3432) 011e752b6a is described below commit 011e752b6a1b7c93a5c4e5070bca4b1b772ec9b0 Author: Zhiguo Wu <wuzhi...@apache.org> AuthorDate: Thu Nov 3 17:40:53 2022 +0800 AMBARI-25186: Kerberos Client is unnecessarily installed via Blueprints when kerberos-env/kdc-type is none (#3432) --- .../ambari/server/topology/TopologyManager.java | 25 ++++++- .../server/topology/TopologyManagerTest.java | 84 ++++++++++++++++++++-- 2 files changed, 102 insertions(+), 7 deletions(-) diff --git a/ambari-server/src/main/java/org/apache/ambari/server/topology/TopologyManager.java b/ambari-server/src/main/java/org/apache/ambari/server/topology/TopologyManager.java index f3fa58ab9a..b0cb3c2d16 100644 --- a/ambari-server/src/main/java/org/apache/ambari/server/topology/TopologyManager.java +++ b/ambari-server/src/main/java/org/apache/ambari/server/topology/TopologyManager.java @@ -44,6 +44,7 @@ import org.apache.ambari.server.actionmanager.HostRoleStatus; import org.apache.ambari.server.api.services.stackadvisor.StackAdvisorBlueprintProcessor; import org.apache.ambari.server.configuration.Configuration; import org.apache.ambari.server.controller.AmbariServer; +import org.apache.ambari.server.controller.KerberosHelper; import org.apache.ambari.server.controller.RequestStatusResponse; import org.apache.ambari.server.controller.internal.ArtifactResourceProvider; import org.apache.ambari.server.controller.internal.BaseClusterRequest; @@ -72,6 +73,7 @@ import org.apache.ambari.server.orm.dao.SettingDAO; import org.apache.ambari.server.orm.entities.SettingEntity; import org.apache.ambari.server.orm.entities.StageEntity; import org.apache.ambari.server.security.authorization.AuthorizationHelper; +import org.apache.ambari.server.serveraction.kerberos.KDCType; import org.apache.ambari.server.state.Host; import org.apache.ambari.server.state.SecurityType; import org.apache.ambari.server.state.host.HostImpl; @@ -209,7 +211,7 @@ public class TopologyManager { replayRequests(persistedState.getAllRequests()); // ensure KERBEROS_CLIENT is present in each hostgroup even if it's not in original BP for(ClusterTopology clusterTopology : clusterTopologyMap.values()) { - if (clusterTopology.isClusterKerberosEnabled()) { + if (clusterTopology.isClusterKerberosEnabled() && isKerberosClientInstallAllowed(clusterTopology)) { addKerberosClient(clusterTopology); } } @@ -296,7 +298,10 @@ public class TopologyManager { if (securityConfiguration != null && securityConfiguration.getType() == SecurityType.KERBEROS) { securityType = SecurityType.KERBEROS; - addKerberosClient(topology); + + if (isKerberosClientInstallAllowed(topology)) { + addKerberosClient(topology); + } // refresh default stack config after adding KERBEROS_CLIENT component to topology topology.getBlueprint().getConfiguration().setParentConfiguration(stack.getConfiguration(topology.getBlueprint().getServices())); @@ -360,6 +365,22 @@ public class TopologyManager { return getRequestStatus(logicalRequest.getRequestId()); } + /** + * The Kerberos Client component is unnecessarily installed via Blueprints when kerberos-env/kdc-type is "none". + * The Blueprint TopologyManager should only force the Kerberos client to be installed if Kerberos is enabled + * and kerberos_env/kdc_type is not "none" or when kerberos_env/manage_identities is true. + * + * @param topology the Cluster Topology which provides the topology's Configuration object. + * @return true if kerberos_env/kdc_type is not "none" or when kerberos_env/manage_identities is true + */ + private boolean isKerberosClientInstallAllowed(final ClusterTopology topology) { + final org.apache.ambari.server.topology.Configuration topologyConfig = topology.getBlueprint().getConfiguration(); + final String kdc_type = topologyConfig.getPropertyValue(KerberosHelper.KERBEROS_ENV, KerberosHelper.KDC_TYPE); + final String manage_identities = topologyConfig.getPropertyValue(KerberosHelper.KERBEROS_ENV, KerberosHelper.MANAGE_IDENTITIES); + + return KDCType.NONE != KDCType.translate(kdc_type) || Boolean.parseBoolean(manage_identities); + } + @Subscribe public void onClusterConfigFinishedEvent(ClusterConfigFinishedEvent event) { ManagedThreadPoolExecutor taskExecutor = topologyTaskExecutorServiceMap.get(event.getClusterId()); diff --git a/ambari-server/src/test/java/org/apache/ambari/server/topology/TopologyManagerTest.java b/ambari-server/src/test/java/org/apache/ambari/server/topology/TopologyManagerTest.java index 71e5fb6678..15c38efcd1 100644 --- a/ambari-server/src/test/java/org/apache/ambari/server/topology/TopologyManagerTest.java +++ b/ambari-server/src/test/java/org/apache/ambari/server/topology/TopologyManagerTest.java @@ -49,13 +49,16 @@ import org.apache.ambari.server.AmbariException; import org.apache.ambari.server.actionmanager.HostRoleStatus; import org.apache.ambari.server.controller.ClusterRequest; import org.apache.ambari.server.controller.ConfigurationRequest; +import org.apache.ambari.server.controller.KerberosHelper; import org.apache.ambari.server.controller.RequestStatusResponse; import org.apache.ambari.server.controller.ShortTaskStatus; import org.apache.ambari.server.controller.internal.HostResourceProvider; import org.apache.ambari.server.controller.internal.ProvisionClusterRequest; +import org.apache.ambari.server.controller.internal.RequestStatusImpl; import org.apache.ambari.server.controller.internal.ScaleClusterRequest; import org.apache.ambari.server.controller.internal.Stack; import org.apache.ambari.server.controller.spi.ClusterController; +import org.apache.ambari.server.controller.spi.Request; import org.apache.ambari.server.controller.spi.Resource; import org.apache.ambari.server.controller.spi.ResourceProvider; import org.apache.ambari.server.events.ClusterProvisionStartedEvent; @@ -66,6 +69,7 @@ import org.apache.ambari.server.orm.dao.SettingDAO; import org.apache.ambari.server.orm.entities.SettingEntity; import org.apache.ambari.server.security.authorization.AuthorizationHelper; import org.apache.ambari.server.security.encryption.CredentialStoreService; +import org.apache.ambari.server.security.encryption.CredentialStoreType; import org.apache.ambari.server.stack.NoSuchStackException; import org.apache.ambari.server.state.SecurityType; import org.apache.ambari.server.state.quicklinksprofile.QuickLinksProfile; @@ -142,12 +146,16 @@ public class TopologyManagerTest { private ExecutorService executor; @Mock(type = MockType.NICE) private PersistedState persistedState; - @Mock(type = MockType.NICE) + @Mock(type = MockType.STRICT) private HostGroup group1; - @Mock(type = MockType.NICE) + @Mock(type = MockType.STRICT) private HostGroup group2; @Mock(type = MockType.STRICT) private SecurityConfigurationFactory securityConfigurationFactory; + @Mock(type = MockType.NICE) + private SecurityConfiguration securityConfiguration; + @Mock(type = MockType.NICE) + private Credential credential; @Mock(type = MockType.STRICT) private CredentialStoreService credentialStoreService; @Mock(type = MockType.STRICT) @@ -246,6 +254,10 @@ public class TopologyManagerTest { group1ServiceComponents.put("service2", Collections.singleton("component2")); group2ServiceComponents.put("service2", Arrays.asList("component3", "component4")); + expect(securityConfiguration.getType()).andReturn(SecurityType.KERBEROS).anyTimes(); + + expect(credential.getType()).andReturn(CredentialStoreType.TEMPORARY).anyTimes(); + expect(blueprint.getHostGroup("group1")).andReturn(group1).anyTimes(); expect(blueprint.getHostGroup("group2")).andReturn(group2).anyTimes(); expect(blueprint.getComponents("service1")).andReturn(Arrays.asList("component1", "component3")).anyTimes(); @@ -349,6 +361,8 @@ public class TopologyManagerTest { expect(clusterController.ensureResourceProvider(anyObject(Resource.Type.class))).andReturn(resourceProvider); + expect(resourceProvider.createResources(anyObject(Request.class))).andReturn(new RequestStatusImpl(null)); + expect(configureClusterTaskFactory.createConfigureClusterTask(anyObject(), anyObject(), anyObject())).andReturn(configureClusterTask); expect(configureClusterTask.getTimeout()).andReturn(1000L); expect(configureClusterTask.getRepeatDelay()).andReturn(50L); @@ -372,6 +386,12 @@ public class TopologyManagerTest { EasyMockSupport.injectMocks(topologyManagerReplay); + clazz = AmbariContext.class; + f = clazz.getDeclaredField("clusterController"); + f.setAccessible(true); + f.set(ambariContext, clusterController); + + EasyMockSupport.injectMocks(ambariContext); } @After @@ -379,12 +399,14 @@ public class TopologyManagerTest { PowerMock.verify(System.class); verify(blueprint, stack, request, group1, group2, ambariContext, logicalRequestFactory, logicalRequest, configurationRequest, configurationRequest2, configurationRequest3, - requestStatusResponse, executor, persistedState, clusterTopologyMock, mockFuture, settingDAO, eventPublisher); + requestStatusResponse, executor, persistedState, clusterTopologyMock, mockFuture, settingDAO, eventPublisher, + securityConfiguration, credential); PowerMock.reset(System.class); reset(blueprint, stack, request, group1, group2, ambariContext, logicalRequestFactory, logicalRequest, configurationRequest, configurationRequest2, configurationRequest3, - requestStatusResponse, executor, persistedState, clusterTopologyMock, mockFuture, settingDAO, eventPublisher); + requestStatusResponse, executor, persistedState, clusterTopologyMock, mockFuture, settingDAO, eventPublisher, + securityConfiguration, credential); } @Test @@ -430,6 +452,58 @@ public class TopologyManagerTest { //todo: assertions } + @Test + public void testDoNotAddKerberosClientAtTopologyInit_KdcTypeNone() throws Exception { + Map<ClusterTopology, List<LogicalRequest>> allRequests = Collections.singletonMap(clusterTopologyMock, Collections.singletonList(logicalRequest)); + + expect(logicalRequest.hasPendingHostRequests()).andReturn(false).anyTimes(); + expect(logicalRequest.isFinished()).andReturn(false).anyTimes(); + expect(requestStatusResponse.getTasks()).andReturn(Collections.emptyList()).anyTimes(); + + expect(clusterTopologyMock.isClusterKerberosEnabled()).andReturn(true); + expect(clusterTopologyMock.getClusterId()).andReturn(CLUSTER_ID).anyTimes(); + expect(clusterTopologyMock.getBlueprint()).andReturn(blueprint).anyTimes(); + + expect(persistedState.getAllRequests()).andReturn(allRequests).anyTimes(); + expect(persistedState.getProvisionRequest(CLUSTER_ID)).andReturn(logicalRequest).anyTimes(); + expect(ambariContext.isTopologyResolved(CLUSTER_ID)).andReturn(true).anyTimes(); + + expect(blueprint.getSecurity()).andReturn(securityConfiguration).anyTimes(); + expect(request.getCredentialsMap()).andReturn(Collections.singletonMap(TopologyManager.KDC_ADMIN_CREDENTIAL, credential)); + + bpConfiguration.setProperty(KerberosHelper.KERBEROS_ENV, KerberosHelper.KDC_TYPE, "none"); + + replayAll(); + + topologyManager.provisionCluster(request); + } + + @Test + public void testDoNotAddKerberosClientAtTopologyInit_ManageIdentity() throws Exception { + Map<ClusterTopology, List<LogicalRequest>> allRequests = Collections.singletonMap(clusterTopologyMock, Collections.singletonList(logicalRequest)); + + expect(logicalRequest.hasPendingHostRequests()).andReturn(false).anyTimes(); + expect(logicalRequest.isFinished()).andReturn(false).anyTimes(); + expect(requestStatusResponse.getTasks()).andReturn(Collections.emptyList()).anyTimes(); + + expect(clusterTopologyMock.isClusterKerberosEnabled()).andReturn(true); + expect(clusterTopologyMock.getClusterId()).andReturn(CLUSTER_ID).anyTimes(); + expect(clusterTopologyMock.getBlueprint()).andReturn(blueprint).anyTimes(); + + expect(persistedState.getAllRequests()).andReturn(allRequests).anyTimes(); + expect(persistedState.getProvisionRequest(CLUSTER_ID)).andReturn(logicalRequest).anyTimes(); + expect(ambariContext.isTopologyResolved(CLUSTER_ID)).andReturn(true).anyTimes(); + + expect(blueprint.getSecurity()).andReturn(securityConfiguration).anyTimes(); + expect(request.getCredentialsMap()).andReturn(Collections.singletonMap(TopologyManager.KDC_ADMIN_CREDENTIAL, credential)); + + bpConfiguration.setProperty(KerberosHelper.KERBEROS_ENV, KerberosHelper.MANAGE_IDENTITIES, "false"); + + replayAll(); + + topologyManager.provisionCluster(request); + } + @Test public void testBlueprintRequestCompletion() throws Exception { List<ShortTaskStatus> tasks = new ArrayList<>(); @@ -554,7 +628,7 @@ public class TopologyManagerTest { configurationRequest, configurationRequest2, configurationRequest3, executor, persistedState, clusterTopologyMock, securityConfigurationFactory, credentialStoreService, clusterController, resourceProvider, mockFuture, requestStatusResponse, logicalRequest, settingDAO, - configureClusterTaskFactory, configureClusterTask, eventPublisher); + configureClusterTaskFactory, configureClusterTask, eventPublisher, securityConfiguration, credential); } @Test(expected = InvalidTopologyException.class) --------------------------------------------------------------------- To unsubscribe, e-mail: commits-unsubscr...@ambari.apache.org For additional commands, e-mail: commits-h...@ambari.apache.org