diff --git a/documentation/4.0/content/managing-domains/domain-lifecycle/scaling.md b/documentation/4.0/content/managing-domains/domain-lifecycle/scaling.md index 9ebe72a23fc..1bccfa9b59a 100644 --- a/documentation/4.0/content/managing-domains/domain-lifecycle/scaling.md +++ b/documentation/4.0/content/managing-domains/domain-lifecycle/scaling.md @@ -228,6 +228,10 @@ operations on a cluster. These policies monitor one or more types of WebLogic Se in a policy is met, the policy is triggered, and the corresponding scaling action is executed. The WebLogic Kubernetes Operator project provides a shell script, [`scalingAction.sh`](https://github.com/oracle/weblogic-kubernetes-operator/blob/{{< latestMinorVersion >}}/operator/scripts/scaling/scalingAction.sh), for use as a Script Action, which illustrates how to issue a request to the operator’s REST endpoint. +{{% notice note %}} +Beginning with operator version 4.0.5, the operator's REST endpoint is disabled by default. Install the operator with the Helm install option `--set "enableRest=true"` to enable the REST endpoint. +{{% /notice %}} + ##### Configure automatic scaling of WebLogic clusters in Kubernetes with WLDF The following steps are provided as a guideline on how to configure a WLDF Policy and Script Action component for issuing scaling requests to the operator's REST endpoint: diff --git a/documentation/4.0/content/managing-operators/the-rest-api.md b/documentation/4.0/content/managing-operators/the-rest-api.md index 38935de479d..e91bb25132b 100644 --- a/documentation/4.0/content/managing-operators/the-rest-api.md +++ b/documentation/4.0/content/managing-operators/the-rest-api.md @@ -15,6 +15,10 @@ or for getting certain aspects of a domain's status (for example, instead of cal You also can use the REST API as an alternative approach for initiating scaling operations (instead of using the Kubernetes API or command line to alter a domain resource's `replicas` values). +{{% notice note %}} +Beginning with operator version 4.0.5, the operator's REST endpoint is disabled by default. Install the operator with the Helm install option `--set "enableRest=true"` to enable the REST endpoint. +{{% /notice %}} + ### Configure the operator's external REST HTTPS interface The operator can expose an external REST HTTPS interface which can be accessed from outside the Kubernetes cluster. As with the operator's internal REST interface, the external REST interface requires an SSL/TLS certificate and private key that the operator will use as the identity of the external REST interface. diff --git a/documentation/4.0/content/managing-operators/using-helm.md b/documentation/4.0/content/managing-operators/using-helm.md index c4776c10aaa..129b7dc306e 100644 --- a/documentation/4.0/content/managing-operators/using-helm.md +++ b/documentation/4.0/content/managing-operators/using-helm.md @@ -493,8 +493,16 @@ The REST interface configuration options are advanced settings for configuring t For usage information, see the operator [REST Services]({{}}). +##### `enableRest` +Determines whether the operator's REST endpoint is enabled. + +Beginning with operator version 4.0.5, the operator's REST endpoint is disabled by default. + +Defaults to `false`. + ##### `externalRestEnabled` -Determines whether the operator's REST interface will be exposed outside the Kubernetes cluster using a node port. +Determines whether the operator's REST interface will be exposed outside the Kubernetes cluster using a node port. This +value is ignored if `enableRest` is not `true`. See also `externalRestHttpsPort` for customizing the port number. diff --git a/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItDiagnosticsCompleteAvailableCondition.java b/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItDiagnosticsCompleteAvailableCondition.java index f810aa0cceb..76aa7c6346a 100644 --- a/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItDiagnosticsCompleteAvailableCondition.java +++ b/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItDiagnosticsCompleteAvailableCondition.java @@ -1,4 +1,4 @@ -// Copyright (c) 2022, Oracle and/or its affiliates. +// Copyright (c) 2022, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.weblogic.kubernetes; @@ -33,7 +33,7 @@ import static oracle.weblogic.kubernetes.actions.TestActions.getServiceNodePort; import static oracle.weblogic.kubernetes.actions.TestActions.imageTag; import static oracle.weblogic.kubernetes.actions.TestActions.patchClusterCustomResource; -import static oracle.weblogic.kubernetes.actions.TestActions.scaleClusterWithRestApi; +import static oracle.weblogic.kubernetes.actions.TestActions.scaleCluster; import static oracle.weblogic.kubernetes.actions.impl.Domain.patchDomainCustomResource; import static oracle.weblogic.kubernetes.assertions.TestAssertions.verifyRollingRestartOccurred; import static oracle.weblogic.kubernetes.utils.CommonMiiTestUtils.createMiiDomainAndVerify; @@ -43,8 +43,6 @@ import static oracle.weblogic.kubernetes.utils.DomainUtils.verifyDomainStatusConditionTypeDoesNotExist; import static oracle.weblogic.kubernetes.utils.ImageUtils.createBaseRepoSecret; import static oracle.weblogic.kubernetes.utils.ImageUtils.imageRepoLoginAndPushImageToRegistry; -import static oracle.weblogic.kubernetes.utils.OKDUtils.createRouteForOKD; -import static oracle.weblogic.kubernetes.utils.OKDUtils.setTlsTerminationForRoute; import static oracle.weblogic.kubernetes.utils.OperatorUtils.installAndVerifyOperator; import static oracle.weblogic.kubernetes.utils.PodUtils.checkPodDoesNotExist; import static oracle.weblogic.kubernetes.utils.PodUtils.getPodCreationTime; @@ -107,13 +105,6 @@ public static void initAll(@Namespaces(2) List namespaces) { installAndVerifyOperator(opNamespace, opServiceAccount, true, 0, domainNamespace1); externalRestHttpsPort = getServiceNodePort(opNamespace, "external-weblogic-operator-svc"); - // This test uses the operator restAPI to scale the domain. To do this in OKD cluster, - // we need to expose the external service as route and set tls termination to passthrough - logger.info("Create a route for the operator external service - only for OKD"); - createRouteForOKD("external-weblogic-operator-svc", opNamespace); - // Patch the route just created to set tls termination to passthrough - setTlsTerminationForRoute("external-weblogic-operator-svc", opNamespace); - // create pull secrets for WebLogic image when running in non Kind Kubernetes cluster // this secret is used only for non-kind cluster createBaseRepoSecret(domainNamespace1); @@ -512,7 +503,7 @@ void testCompleteAvailableConditionWithScaleUpDownCluster() { // scale down the cluster int newReplicaCount = 1; assertDoesNotThrow(() -> - scaleClusterWithRestApi(domainUid, cluster1Name, 1, externalRestHttpsPort, opNamespace, opServiceAccount)); + scaleCluster(clusterResName, domainNamespace1, 1)); // verify the admin server service exists checkPodReadyAndServiceExists(adminServerPodName, domainUid, domainNamespace1); @@ -544,7 +535,7 @@ void testCompleteAvailableConditionWithScaleUpDownCluster() { // scale up the cluster newReplicaCount = 2; assertDoesNotThrow(() -> - scaleClusterWithRestApi(domainUid, cluster1Name, 2, externalRestHttpsPort, opNamespace, opServiceAccount)); + scaleCluster(clusterResName, domainNamespace1, 2)); // verify the admin server service exists checkPodReadyAndServiceExists(adminServerPodName, domainUid, domainNamespace1); diff --git a/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItKubernetesDomainEvents.java b/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItKubernetesDomainEvents.java index 6b9ff14e14d..58f1fd8ac59 100644 --- a/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItKubernetesDomainEvents.java +++ b/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItKubernetesDomainEvents.java @@ -61,7 +61,7 @@ import static oracle.weblogic.kubernetes.actions.TestActions.getServiceNodePort; import static oracle.weblogic.kubernetes.actions.TestActions.getServicePort; import static oracle.weblogic.kubernetes.actions.TestActions.now; -import static oracle.weblogic.kubernetes.actions.TestActions.scaleClusterWithRestApi; +import static oracle.weblogic.kubernetes.actions.TestActions.scaleCluster; import static oracle.weblogic.kubernetes.actions.TestActions.shutdownDomain; import static oracle.weblogic.kubernetes.actions.impl.Cluster.listClusterCustomResources; import static oracle.weblogic.kubernetes.actions.impl.Domain.patchDomainCustomResource; @@ -70,7 +70,6 @@ import static oracle.weblogic.kubernetes.utils.ClusterUtils.createClusterResource; import static oracle.weblogic.kubernetes.utils.ClusterUtils.createClusterResourceAndAddReferenceToDomain; import static oracle.weblogic.kubernetes.utils.ClusterUtils.removeReplicasSettingAndVerify; -import static oracle.weblogic.kubernetes.utils.ClusterUtils.scaleCluster; import static oracle.weblogic.kubernetes.utils.CommonTestUtils.checkPodReadyAndServiceExists; import static oracle.weblogic.kubernetes.utils.CommonTestUtils.checkServiceExists; import static oracle.weblogic.kubernetes.utils.CommonTestUtils.getNextFreePort; @@ -104,8 +103,6 @@ import static oracle.weblogic.kubernetes.utils.K8sEvents.checkDomainFailedEventWithReason; import static oracle.weblogic.kubernetes.utils.K8sEvents.getDomainEventCount; import static oracle.weblogic.kubernetes.utils.K8sEvents.getOpGeneratedEventCount; -import static oracle.weblogic.kubernetes.utils.OKDUtils.createRouteForOKD; -import static oracle.weblogic.kubernetes.utils.OKDUtils.setTlsTerminationForRoute; import static oracle.weblogic.kubernetes.utils.OperatorUtils.installAndVerifyOperator; import static oracle.weblogic.kubernetes.utils.PatchDomainUtils.patchDomainResource; import static oracle.weblogic.kubernetes.utils.PersistentVolumeUtils.createPV; @@ -162,6 +159,7 @@ class ItKubernetesDomainEvents { static String managedServerPodNamePrefix = domainUid + "-" + managedServerNameBase; static final int managedServerPort = 8001; static int replicaCount = 2; + String clusterRes2Name = cluster2Name; String clusterRes1Name = cluster1Name; static final String pvName1 = getUniqueName(domainUid + "-pv-"); @@ -219,13 +217,6 @@ public static void initAll(@Namespaces(6) List namespaces) { domainNamespace4, domainNamespace5); externalRestHttpsPort = getServiceNodePort(opNamespace, "external-weblogic-operator-svc"); - // This test uses the operator restAPI to scale the domain. To do this in OKD cluster, - // we need to expose the external service as route and set tls termination to passthrough - logger.info("Create a route for the operator external service - only for OKD"); - String opExternalSvc = createRouteForOKD("external-weblogic-operator-svc", opNamespace); - // Patch the route just created to set tls termination to passthrough - setTlsTerminationForRoute("external-weblogic-operator-svc", opNamespace); - createDomain(domainNamespace3, domainUid, pvName3, pvcName3); } @@ -394,8 +385,7 @@ void testK8SEventsMultiClusterEvents() { createNewCluster(); OffsetDateTime timestamp2 = now(); logger.info("Scale the newly-added cluster"); - scaleClusterWithRestApi(domainUid, cluster2Name, 1, - externalRestHttpsPort, opNamespace, opServiceAccount); + scaleCluster(clusterRes2Name, domainNamespace3, 1); logger.info("verify the Domain_Available event is generated"); checkEvent(opNamespace, domainNamespace3, domainUid, DOMAIN_AVAILABLE, "Normal", timestamp); diff --git a/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItManageNameSpace.java b/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItManageNameSpace.java index 7abcc7dced6..ba34904b570 100644 --- a/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItManageNameSpace.java +++ b/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItManageNameSpace.java @@ -1,4 +1,4 @@ -// Copyright (c) 2020, 2022, Oracle and/or its affiliates. +// Copyright (c) 2020, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.weblogic.kubernetes; @@ -52,7 +52,7 @@ import static oracle.weblogic.kubernetes.actions.TestActions.deleteNamespace; import static oracle.weblogic.kubernetes.actions.TestActions.deleteSecret; import static oracle.weblogic.kubernetes.actions.TestActions.getServiceNodePort; -import static oracle.weblogic.kubernetes.actions.TestActions.scaleClusterWithRestApi; +import static oracle.weblogic.kubernetes.actions.TestActions.scaleCluster; import static oracle.weblogic.kubernetes.actions.TestActions.uninstallOperator; import static oracle.weblogic.kubernetes.utils.CleanupUtil.deleteNamespacedArtifacts; import static oracle.weblogic.kubernetes.utils.ClusterUtils.createClusterResourceAndAddReferenceToDomain; @@ -249,13 +249,7 @@ void testNameSpaceManageByRegularExpression() { //verify domain is started createSecrets(manageByLabelNS); assertTrue(createDomainResourceAndVerifyDomainIsRunning(manageByLabelNS,manageByLabelDomainUid)); - checkOperatorCanScaleDomain(opNamespaces[1],manageByLabelDomainUid); - - //check operator can't manage anymore manageByExp1NS - assertTrue(isOperatorFailedToScaleDomain(opNamespaces[1], manageByExpDomain1Uid, - manageByExp1NS), "Operator can still manage domain " - + manageByExp1NS + " in the namespace " + manageByExp1NS); - + checkOperatorCanScaleDomain(manageByLabelNS, manageByLabelDomainUid); } /** @@ -299,7 +293,7 @@ void testNameSpaceManagedByLabelSelector() { "Failed to create domain CRD or " + "verify that domain " + domainsUid[1] + " is running in namespace " + domainNamespaces[1]); - checkOperatorCanScaleDomain(opNamespaces[0], domainsUid[1]); + checkOperatorCanScaleDomain(domainNamespaces[1], domainsUid[1]); //check that with specific Selector default namespace is not under operator management checkDomainNotStartedInDefaultNS(); @@ -325,11 +319,7 @@ void testNameSpaceManagedByLabelSelector() { //verify domain is started in namespace with name starting with weblogic* and operator can scale it. createSecrets(manageByExpDomainNS); assertTrue(createDomainResourceAndVerifyDomainIsRunning(manageByExpDomainNS,manageByExpDomainUid)); - checkOperatorCanScaleDomain(opNamespaces[0],manageByExpDomainUid); - //verify operator can't manage anymore domain running in the namespace with label - assertTrue(isOperatorFailedToScaleDomain(opNamespaces[0], domainsUid[0], domainNamespaces[0]), - "Operator can still manage domain " - + domainsUid[0] + " in the namespace " + domainNamespaces[0]); + checkOperatorCanScaleDomain(manageByExpDomainNS, manageByExpDomainUid); checkUpgradeFailedToAddNSManagedByAnotherOperator(); } @@ -374,7 +364,7 @@ void testNameSpaceWithOperatorRbacFalse() { assertTrue(upgradeAndVerifyOperator(opNamespaces[3], opParams)); assertTrue(createDomainResourceAndVerifyDomainIsRunning(manageByLabelDomainNS, manageByLabelDomainUid)); - checkOperatorCanScaleDomain(opNamespaces[3], manageByLabelDomainUid); + checkOperatorCanScaleDomain(manageByLabelDomainNS, manageByLabelDomainUid); } private void checkUpgradeFailedToAddNSManagedByAnotherOperator() { @@ -411,7 +401,7 @@ private HelmParams installAndVerifyOperatorCanManageDomainBySelector(Map lab assertDoesNotThrow(() -> Kubernetes.replaceNamespace(namespaceObject1)); } - private void checkOperatorCanScaleDomain(String opNamespace, String domainUid) { - int externalRestHttpsPort = getServiceNodePort(opNamespace, "external-weblogic-operator-svc"); - assertTrue(scaleClusterWithRestApi(domainUid, clusterName, 3, - externalRestHttpsPort, opNamespace, OPERATOR_RELEASE_NAME + "-sa"), + private void checkOperatorCanScaleDomain(String domainNamespace, String domainUid) { + assertTrue(scaleCluster(domainUid + "-" + clusterName, domainNamespace, 3), "Domain " + domainUid + " scaling operation failed"); } diff --git a/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItUsabilityOperatorHelmChart.java b/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItUsabilityOperatorHelmChart.java index 6235729d423..d27ea47e51c 100644 --- a/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItUsabilityOperatorHelmChart.java +++ b/integration-tests/src/test/java/oracle/weblogic/kubernetes/ItUsabilityOperatorHelmChart.java @@ -1,4 +1,4 @@ -// Copyright (c) 2020, 2022, Oracle and/or its affiliates. +// Copyright (c) 2020, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.weblogic.kubernetes; @@ -70,7 +70,7 @@ import static oracle.weblogic.kubernetes.actions.TestActions.helmValuesToString; import static oracle.weblogic.kubernetes.actions.TestActions.installOperator; import static oracle.weblogic.kubernetes.actions.TestActions.listSecrets; -import static oracle.weblogic.kubernetes.actions.TestActions.scaleClusterWithRestApi; +import static oracle.weblogic.kubernetes.actions.TestActions.scaleCluster; import static oracle.weblogic.kubernetes.actions.TestActions.uninstallOperator; import static oracle.weblogic.kubernetes.assertions.TestAssertions.checkHelmReleaseStatus; import static oracle.weblogic.kubernetes.assertions.TestAssertions.isHelmReleaseDeployed; @@ -356,7 +356,6 @@ void testCreateDeleteCreateOperatorButNotDomain() { null,"deployed", 0, opHelmParams, LIST_STRATEGY, domain1Namespace); assertNotNull(opHelmParams, "Can't install operator"); - createRouteForOKD("external-weblogic-operator-svc", opNamespace); setTlsTerminationForRoute("external-weblogic-operator-svc", opNamespace); int externalRestHttpsPort = getServiceNodePort(opNamespace, "external-weblogic-operator-svc"); assertNotEquals(-1, externalRestHttpsPort, @@ -365,8 +364,7 @@ void testCreateDeleteCreateOperatorButNotDomain() { //check if the operator can still manage domain1 int replicaCountDomain1 = 2; - assertTrue(scaleClusterWithRestApi(domain1Uid, clusterName,replicaCountDomain1 - 1, - externalRestHttpsPort,opNamespace, opServiceAccount), + assertTrue(scaleCluster(domain1Uid + "-" + clusterName, domain1Namespace, replicaCountDomain1 - 1), "Domain1 " + domain1Namespace + " scaling failed"); String managedServerPodName1 = domain1Uid + managedServerPrefix + replicaCountDomain1; logger.info("Checking that the managed server pod {0} exists in namespace {1}", @@ -435,8 +433,7 @@ void testAddRemoveDomainNameSpacesOnOperator() { assertTrue(createVerifyDomain(domain3Namespace, domain3Uid), "can't start or verify domain in namespace " + domain3Namespace); - assertTrue(scaleClusterWithRestApi(domain3Uid, clusterName,3, - externalRestHttpsPort,op2Namespace, opServiceAccount), + assertTrue(scaleCluster(domain3Uid + "-" + clusterName, domain3Namespace, 3), "Domain3 " + domain3Namespace + " scaling operation failed"); String managedServerPodName1 = domain3Uid + managedServerPrefix + 3; logger.info("Checking that the managed server pod {0} exists in namespace {1}", @@ -448,8 +445,7 @@ void testAddRemoveDomainNameSpacesOnOperator() { // scale domain2 int replicaCountDomain2 = 2; - assertTrue(scaleClusterWithRestApi(domain2Uid, clusterName,replicaCountDomain2 + 1, - externalRestHttpsPort,op2Namespace, opServiceAccount), + assertTrue(scaleCluster(domain2Uid + "-" + clusterName, domain2Namespace, replicaCountDomain2 + 1), "Domain2 in namespace " + domain2Namespace + " scaling operation failed"); String managedServerPodName2 = domain2Uid + managedServerPrefix + (replicaCountDomain2 + 1); @@ -471,8 +467,7 @@ void testAddRemoveDomainNameSpacesOnOperator() { assertTrue(upgradeAndVerifyOperator(op2Namespace, opParams)); // scale domain2 - assertTrue(scaleClusterWithRestApi(domain2Uid, clusterName,replicaCountDomain2 - 1, - externalRestHttpsPort,op2Namespace, opServiceAccount), + assertTrue(scaleCluster(domain2Uid + "-" + clusterName, domain2Namespace, replicaCountDomain2 - 1), "Domain2 in namespace " + domain2Namespace + " scaling execution failed"); // check new managed server pod does not exist in the namespace @@ -485,8 +480,7 @@ void testAddRemoveDomainNameSpacesOnOperator() { logger.info("Domain2 scaled to " + replicaCountDomain2 + " servers"); //verify operator can't scale domain3 anymore - assertTrue(scaleClusterWithRestApi(domain3Uid, clusterName,2, - externalRestHttpsPort, op2Namespace, opServiceAccount), + assertTrue(scaleCluster(domain3Uid + "-" + clusterName, domain3Namespace, 2), "Domain " + domain3Namespace + " scaling execution failed "); // check new managed server pod exists in the namespace @@ -720,8 +714,7 @@ void testCreateWithEmptyDomainNamespaceInstall() { //verify operator can scale domain int replicaCountDomain2 = 2; - assertTrue(scaleClusterWithRestApi(domain2Uid, clusterName,replicaCountDomain2 - 1, - externalRestHttpsPort, op2Namespace, opServiceAccount), + assertTrue(scaleCluster(domain2Uid + "-" + clusterName, domain2Namespace, replicaCountDomain2 - 1), "Domain2 in namespace " + domain2Namespace + " scaling operation failed"); String managedServerPodName2 = domain2Uid + managedServerPrefix + replicaCountDomain2; @@ -850,8 +843,7 @@ void testTwoDomainsInSameNameSpaceOnOperator() { assertTrue(createVerifyDomain(domain4Namespace, domain5Uid), "can't start or verify domain5 in namespace " + domain4Namespace); - assertTrue(scaleClusterWithRestApi(domain4Uid, clusterName,3, - externalRestHttpsPort,op3Namespace, opServiceAccount), + assertTrue(scaleCluster(domain4Uid + "-" + clusterName, domain4Namespace, 3), "Domain4 " + domain4Namespace + " scaling operation failed"); String managedServerPodName1 = domain4Uid + managedServerPrefix + 3; logger.info("Checking that the managed server pod {0} exists in namespace {1}", @@ -861,8 +853,7 @@ void testTwoDomainsInSameNameSpaceOnOperator() { "operator failed to manage domain4, scaling was not succeeded"); logger.info("Domain4 scaled to 3 servers"); - assertTrue(scaleClusterWithRestApi(domain5Uid, clusterName,3, - externalRestHttpsPort,op3Namespace, opServiceAccount), + assertTrue(scaleCluster(domain5Uid + "-" + clusterName, domain4Namespace, 3), "Domain2 " + domain4Namespace + " scaling operation failed"); String managedServerPodName2 = domain5Uid + managedServerPrefix + 3; logger.info("Checking that the managed server pod {0} exists in namespace {1}", @@ -1120,6 +1111,7 @@ private static HelmParams installOperatorHelmChart(String operNamespace, DEFAULT_EXTERNAL_REST_IDENTITY_SECRET_NAME + operNamespace), "failed to create external REST identity secret"); opParams + .restEnabled(true) .externalRestEnabled(true) .externalRestHttpsPort(externalRestHttpsPort) .externalRestIdentitySecret(DEFAULT_EXTERNAL_REST_IDENTITY_SECRET_NAME + operNamespace); diff --git a/integration-tests/src/test/java/oracle/weblogic/kubernetes/actions/impl/OperatorParams.java b/integration-tests/src/test/java/oracle/weblogic/kubernetes/actions/impl/OperatorParams.java index 45e30836dd9..8ef900ab7c9 100644 --- a/integration-tests/src/test/java/oracle/weblogic/kubernetes/actions/impl/OperatorParams.java +++ b/integration-tests/src/test/java/oracle/weblogic/kubernetes/actions/impl/OperatorParams.java @@ -1,4 +1,4 @@ -// Copyright (c) 2020, 2022, Oracle and/or its affiliates. +// Copyright (c) 2020, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.weblogic.kubernetes.actions.impl; @@ -18,6 +18,7 @@ public class OperatorParams { private static final String DOMAIN_NAMESPACES = "domainNamespaces"; private static final String IMAGE = "image"; private static final String SERVICE_ACCOUNT = "serviceAccount"; + private static final String ENABLE_REST = "enableRest"; private static final String EXTERNAL_REST_ENABLED = "externalRestEnabled"; private static final String EXTERNAL_REST_IDENTITY_SECRET = "externalRestIdentitySecret"; private static final String EXTERNAL_REST_HTTPS_PORT = "externalRestHttpsPort"; @@ -42,6 +43,7 @@ public class OperatorParams { private List domainNamespaces; private String image; private String serviceAccount; + private boolean enableRest; private boolean externalRestEnabled; private String externalRestIdentitySecret; private int externalRestHttpsPort = 0; @@ -80,6 +82,11 @@ public OperatorParams serviceAccount(String serviceAccount) { return this; } + public OperatorParams restEnabled(boolean restEnabled) { + this.enableRest = restEnabled; + return this; + } + public OperatorParams externalRestEnabled(boolean externalRestEnabled) { this.externalRestEnabled = externalRestEnabled; return this; @@ -216,6 +223,7 @@ public Map getValues() { values.put(IMAGE, image); values.put(SERVICE_ACCOUNT, serviceAccount); + values.put(ENABLE_REST, Boolean.valueOf(enableRest)); values.put(EXTERNAL_REST_ENABLED, Boolean.valueOf(externalRestEnabled)); values.put(EXTERNAL_REST_IDENTITY_SECRET, externalRestIdentitySecret); diff --git a/integration-tests/src/test/java/oracle/weblogic/kubernetes/utils/OperatorUtils.java b/integration-tests/src/test/java/oracle/weblogic/kubernetes/utils/OperatorUtils.java index 28824211e8a..b022dd486a0 100644 --- a/integration-tests/src/test/java/oracle/weblogic/kubernetes/utils/OperatorUtils.java +++ b/integration-tests/src/test/java/oracle/weblogic/kubernetes/utils/OperatorUtils.java @@ -85,14 +85,14 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, HelmPa * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param domainNamespace the list of the domain namespaces which will be managed by the operator * @return the operator Helm installation parameters */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, String... domainNamespace) { HelmParams opHelmParams = @@ -100,7 +100,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, .namespace(opNamespace) .chartDir(OPERATOR_CHART_DIR); return installAndVerifyOperator(opNamespace, opServiceAccount, - withRestAPI, externalRestHttpsPort, opHelmParams, domainNamespace); + withExternalRestAPI, externalRestHttpsPort, opHelmParams, domainNamespace); } @@ -109,7 +109,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param elkIntegrationEnabled boolean value indicating elk enabled or not * @param domainNamespace the list of the domain namespaces which will be managed by the operator @@ -117,7 +117,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, boolean elkIntegrationEnabled, String... domainNamespace) { @@ -127,7 +127,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, .chartDir(OPERATOR_CHART_DIR); return installAndVerifyOperator(opNamespace, opServiceAccount, - withRestAPI, externalRestHttpsPort, opHelmParams, elkIntegrationEnabled, domainNamespace); + withExternalRestAPI, externalRestHttpsPort, opHelmParams, elkIntegrationEnabled, domainNamespace); } /** @@ -135,7 +135,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param opHelmParams the Helm parameters to install operator * @param domainNamespace the list of the domain namespaces which will be managed by the operator @@ -143,12 +143,12 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, HelmParams opHelmParams, String... domainNamespace) { return installAndVerifyOperator(opNamespace, opServiceAccount, - withRestAPI, externalRestHttpsPort, opHelmParams, false, domainNamespace); + withExternalRestAPI, externalRestHttpsPort, opHelmParams, false, domainNamespace); } /** @@ -156,7 +156,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param opHelmParams the Helm parameters to install operator * @param loggingLevel operator logging level @@ -165,7 +165,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, String loggingLevel, HelmParams opHelmParams, @@ -173,7 +173,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, return installAndVerifyOperator(opNamespace, opServiceAccount, - withRestAPI, + withExternalRestAPI, externalRestHttpsPort, opHelmParams, false, @@ -189,7 +189,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param opHelmParams the Helm parameters to install operator * @param elkIntegrationEnabled true to enable ELK Stack, false otherwise @@ -198,13 +198,13 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, HelmParams opHelmParams, boolean elkIntegrationEnabled, String... domainNamespace) { return installAndVerifyOperator(opNamespace, opServiceAccount, - withRestAPI, externalRestHttpsPort, opHelmParams, elkIntegrationEnabled, + withExternalRestAPI, externalRestHttpsPort, opHelmParams, elkIntegrationEnabled, null, null, false, domainNamespace); } @@ -213,7 +213,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param opHelmParams the Helm parameters to install operator * @param elkIntegrationEnabled true to enable ELK Stack, false otherwise @@ -224,14 +224,14 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, HelmParams opHelmParams, String domainNamespaceSelectionStrategy, boolean elkIntegrationEnabled, String... domainNamespace) { return installAndVerifyOperator(opNamespace, opServiceAccount, - withRestAPI, externalRestHttpsPort, opHelmParams, elkIntegrationEnabled, + withExternalRestAPI, externalRestHttpsPort, opHelmParams, elkIntegrationEnabled, domainNamespaceSelectionStrategy, null, false, domainNamespace); } @@ -240,7 +240,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param elkIntegrationEnabled boolean value indicating elk enabled or not * @param domainNamespace the list of the domain namespaces which will be managed by the operator @@ -248,7 +248,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, String elasticSearchHost, boolean elkIntegrationEnabled, @@ -259,7 +259,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, .namespace(opNamespace) .chartDir(OPERATOR_CHART_DIR); - return installAndVerifyOperator(opNamespace, opServiceAccount, withRestAPI, + return installAndVerifyOperator(opNamespace, opServiceAccount, withExternalRestAPI, externalRestHttpsPort, opHelmParams, elasticSearchHost, elkIntegrationEnabled, createLogStashConfigMap, null, @@ -275,7 +275,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param opHelmParams the Helm parameters to install operator * @param elkIntegrationEnabled true to enable ELK Stack, false otherwise @@ -288,7 +288,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, HelmParams opHelmParams, boolean elkIntegrationEnabled, @@ -298,7 +298,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, String... domainNamespace) { return installAndVerifyOperator(opNamespace, opServiceAccount, - withRestAPI, + withExternalRestAPI, externalRestHttpsPort, opHelmParams, elkIntegrationEnabled, @@ -314,7 +314,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param opHelmParams the Helm parameters to install operator * @param elkIntegrationEnabled true to enable ELK Stack, false otherwise @@ -328,7 +328,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, HelmParams opHelmParams, boolean elkIntegrationEnabled, @@ -339,7 +339,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, String... domainNamespace) { return installAndVerifyOperator(opNamespace, opServiceAccount, - withRestAPI, + withExternalRestAPI, externalRestHttpsPort, opHelmParams, ELASTICSEARCH_HOST, @@ -358,7 +358,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param opHelmParams the Helm parameters to install operator * @param elasticSearchHost Elasticsearchhost @@ -375,7 +375,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, HelmParams opHelmParams, String elasticSearchHost, @@ -448,11 +448,12 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, opParams.logStashImage(LOGSTASH_IMAGE); } - if (withRestAPI) { + if (withExternalRestAPI) { // create externalRestIdentitySecret assertTrue(createExternalRestIdentitySecret(opNamespace, DEFAULT_EXTERNAL_REST_IDENTITY_SECRET_NAME), "failed to create external REST identity secret"); opParams + .restEnabled(true) .externalRestEnabled(true) .externalRestHttpsPort(externalRestHttpsPort) .externalRestIdentitySecret(DEFAULT_EXTERNAL_REST_IDENTITY_SECRET_NAME); @@ -511,7 +512,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, opNamespace); } - if (withRestAPI) { + if (withExternalRestAPI) { logger.info("Wait for the operator external service in namespace {0}", opNamespace); testUntil( withLongRetryPolicy, @@ -557,7 +558,7 @@ public static OperatorParams installAndVerifyOperator(String opReleaseName, Stri * * @param opNamespace the operator namespace in which the operator will be installed * @param opServiceAccount the service account name for operator - * @param withRestAPI whether to use REST API + * @param withExternalRestAPI whether to use REST API * @param externalRestHttpsPort the node port allocated for the external operator REST HTTPS interface * @param opHelmParams the Helm parameters to install operator * @param elkIntegrationEnabled true to enable ELK Stack, false otherwise @@ -574,7 +575,7 @@ public static OperatorParams installAndVerifyOperator(String opReleaseName, Stri */ public static OperatorParams installAndVerifyOperator(String opNamespace, String opServiceAccount, - boolean withRestAPI, + boolean withExternalRestAPI, int externalRestHttpsPort, HelmParams opHelmParams, boolean elkIntegrationEnabled, @@ -642,7 +643,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, .logStashImage(LOGSTASH_IMAGE); } - if (withRestAPI) { + if (withExternalRestAPI) { // create externalRestIdentitySecret assertTrue(createExternalRestIdentitySecret(opNamespace, DEFAULT_EXTERNAL_REST_IDENTITY_SECRET_NAME), "failed to create external REST identity secret"); @@ -708,7 +709,7 @@ public static OperatorParams installAndVerifyOperator(String opNamespace, .until(assertDoesNotThrow(() -> operatorIsReady(opNamespace), "operatorIsReady failed with ApiException")); - if (withRestAPI) { + if (withExternalRestAPI) { logger.info("Wait for the operator external service in namespace {0}", opNamespace); CommonTestUtils.withStandardRetryPolicy .conditionEvaluationListener( diff --git a/kubernetes/charts/weblogic-operator/templates/_operator-dep.tpl b/kubernetes/charts/weblogic-operator/templates/_operator-dep.tpl index c8a22d289b7..41c8fe0d0d7 100644 --- a/kubernetes/charts/weblogic-operator/templates/_operator-dep.tpl +++ b/kubernetes/charts/weblogic-operator/templates/_operator-dep.tpl @@ -73,12 +73,16 @@ spec: fieldPath: "metadata.uid" - name: "OPERATOR_VERBOSE" value: "false" - - name: "JAVA_LOGGING_LEVEL" - value: {{ .javaLoggingLevel | quote }} {{- if .kubernetesPlatform }} - name: "KUBERNETES_PLATFORM" value: {{ .kubernetesPlatform | quote }} {{- end }} + {{- if and (hasKey . "enableRest") .enableRest }} + - name: "ENABLE_REST_ENDPOINT" + value: "true" + {{- end }} + - name: "JAVA_LOGGING_LEVEL" + value: {{ .javaLoggingLevel | quote }} - name: "JAVA_LOGGING_MAXSIZE" value: {{ .javaLoggingFileSizeLimit | default 20000000 | quote }} - name: "JAVA_LOGGING_COUNT" diff --git a/kubernetes/charts/weblogic-operator/templates/_operator-external-svc.tpl b/kubernetes/charts/weblogic-operator/templates/_operator-external-svc.tpl index 0fd2ee2025c..f7936f537a8 100644 --- a/kubernetes/charts/weblogic-operator/templates/_operator-external-svc.tpl +++ b/kubernetes/charts/weblogic-operator/templates/_operator-external-svc.tpl @@ -1,8 +1,8 @@ -# Copyright (c) 2018, 2022, Oracle and/or its affiliates. +# Copyright (c) 2018, 2023, Oracle and/or its affiliates. # Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. {{- define "operator.operatorExternalService" }} -{{- if or .externalRestEnabled .remoteDebugNodePortEnabled }} +{{- if or (and (hasKey . "enableRest") .enableRest .externalRestEnabled) .remoteDebugNodePortEnabled }} --- apiVersion: "v1" kind: "Service" diff --git a/kubernetes/charts/weblogic-operator/templates/_operator-internal-svc.tpl b/kubernetes/charts/weblogic-operator/templates/_operator-internal-svc.tpl index 5e7725825e8..c8c91bc1e73 100644 --- a/kubernetes/charts/weblogic-operator/templates/_operator-internal-svc.tpl +++ b/kubernetes/charts/weblogic-operator/templates/_operator-internal-svc.tpl @@ -1,7 +1,8 @@ -# Copyright (c) 2018, 2022, Oracle and/or its affiliates. +# Copyright (c) 2018, 2023, Oracle and/or its affiliates. # Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. {{- define "operator.operatorInternalService" }} +{{- if and (hasKey . "enableRest") .enableRest }} --- apiVersion: "v1" kind: "Service" @@ -21,6 +22,7 @@ spec: - port: 8083 name: "metrics" appProtocol: http +{{- end }} --- {{- if not .operatorOnly }} apiVersion: "v1" diff --git a/kubernetes/charts/weblogic-operator/values.yaml b/kubernetes/charts/weblogic-operator/values.yaml index f2bfed81356..f1a1aeb0de9 100644 --- a/kubernetes/charts/weblogic-operator/values.yaml +++ b/kubernetes/charts/weblogic-operator/values.yaml @@ -1,4 +1,4 @@ -# Copyright (c) 2018, 2022, Oracle and/or its affiliates. +# Copyright (c) 2018, 2023, Oracle and/or its affiliates. # Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. # serviceAccount specifies the name of the ServiceAccount in the operator's namespace that the @@ -69,9 +69,13 @@ imagePullPolicy: IfNotPresent # imagePullSecrets: # - name: "my-operator-secret" +# enableRest specifies whether the operator's REST interface is enabled. Beginning with version 4.0.5, +# the REST interface will be disabled by default. +# enableRest: true + # externalRestEnabled specifies whether the operator's REST interface is exposed # outside the Kubernetes cluster on the port specified by the 'externalRestHttpsPort' -# property. +# property. Ignored if 'enableRest' is not true. # # If set to true, then the customer must provide the SSL certificate and private key for # the operator's external REST interface by specifying the 'externalOperatorCert' and diff --git a/kubernetes/src/test/java/oracle/kubernetes/operator/create/CreateOperatorGeneratedFilesTestBase.java b/kubernetes/src/test/java/oracle/kubernetes/operator/create/CreateOperatorGeneratedFilesTestBase.java index a1db36c3819..b6bad69d215 100644 --- a/kubernetes/src/test/java/oracle/kubernetes/operator/create/CreateOperatorGeneratedFilesTestBase.java +++ b/kubernetes/src/test/java/oracle/kubernetes/operator/create/CreateOperatorGeneratedFilesTestBase.java @@ -253,6 +253,8 @@ protected V1Deployment getExpectedWeblogicOperatorDeployment() { .fieldPath("metadata.uid")))) .addEnvItem( newEnvVar().name("OPERATOR_VERBOSE").value("false")) + .addEnvItem( + newEnvVar().name("ENABLE_REST_ENDPOINT").value("true")) .addEnvItem( newEnvVar() .name("JAVA_LOGGING_LEVEL") diff --git a/kubernetes/src/test/java/oracle/kubernetes/operator/helm/HelmOperatorValues.java b/kubernetes/src/test/java/oracle/kubernetes/operator/helm/HelmOperatorValues.java index c8c7ca03e9b..4f69160693d 100644 --- a/kubernetes/src/test/java/oracle/kubernetes/operator/helm/HelmOperatorValues.java +++ b/kubernetes/src/test/java/oracle/kubernetes/operator/helm/HelmOperatorValues.java @@ -1,4 +1,4 @@ -// Copyright (c) 2018, 2022, Oracle and/or its affiliates. +// Copyright (c) 2018, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.kubernetes.operator.helm; @@ -115,6 +115,7 @@ Map createMap() { addStringMapEntry(map, this::getLogStashImage, "logStashImage"); addStringMapEntry(map, this::getElasticSearchHost, "elasticSearchHost"); + addMapEntry(map, this::isRestEnabled, "enableRest"); addMapEntry(map, this::isExternalRestEnabled, "externalRestEnabled"); addMapEntry(map, this::isRemoteDebugNodePortEnabled, "remoteDebugNodePortEnabled"); addMapEntry(map, this::isSuspendOnDebugStartup, "suspendOnDebugStartup"); @@ -145,6 +146,10 @@ private void addImagePullSecrets(HashMap map) { } } + private Boolean isRestEnabled() { + return MapUtils.valueOf(getRestEnabled()); + } + private Boolean isExternalRestEnabled() { return MapUtils.valueOf(getExternalRestEnabled()); } diff --git a/kubernetes/src/test/java/oracle/kubernetes/operator/utils/OperatorValues.java b/kubernetes/src/test/java/oracle/kubernetes/operator/utils/OperatorValues.java index e3f8e459e3b..2da3429b51d 100644 --- a/kubernetes/src/test/java/oracle/kubernetes/operator/utils/OperatorValues.java +++ b/kubernetes/src/test/java/oracle/kubernetes/operator/utils/OperatorValues.java @@ -1,4 +1,4 @@ -// Copyright (c) 2018, 2022, Oracle and/or its affiliates. +// Copyright (c) 2018, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.kubernetes.operator.utils; @@ -27,6 +27,7 @@ public class OperatorValues { private String weblogicOperatorImage = ""; private String weblogicOperatorImagePullPolicy = "Never"; private String weblogicOperatorImagePullSecretName = ""; + private String restEnabled = ""; private String externalRestEnabled = ""; private String externalRestHttpsPort = ""; private String externalOperatorCert = ""; @@ -56,6 +57,7 @@ public OperatorValues withTestDefaults() { .weblogicOperatorImagePullPolicy("Never") .javaLoggingLevel("FINEST") .logStashImage("test-logstash-image") + .restEnabled("true") .elasticSearchHost("test-elastic-search_host") .elasticSearchPort("9200") .elasticSearchProtocol("http"); @@ -224,6 +226,19 @@ public OperatorValues weblogicOperatorImagePullSecretName(String val) { return this; } + public String getRestEnabled() { + return restEnabled; + } + + public void setRestEnabled(String val) { + restEnabled = convertNullToEmptyString(val); + } + + public OperatorValues restEnabled(String val) { + setRestEnabled(val); + return this; + } + public String getExternalRestEnabled() { return externalRestEnabled; } diff --git a/operator/src/main/java/oracle/kubernetes/operator/BaseMain.java b/operator/src/main/java/oracle/kubernetes/operator/BaseMain.java index a6315afd372..52c3c97023b 100644 --- a/operator/src/main/java/oracle/kubernetes/operator/BaseMain.java +++ b/operator/src/main/java/oracle/kubernetes/operator/BaseMain.java @@ -1,4 +1,4 @@ -// Copyright (c) 2022, Oracle and/or its affiliates. +// Copyright (c) 2022, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.kubernetes.operator; @@ -29,6 +29,7 @@ import oracle.kubernetes.common.logging.MessageKeys; import oracle.kubernetes.operator.calls.UnrecoverableCallException; import oracle.kubernetes.operator.helpers.ClientPool; +import oracle.kubernetes.operator.helpers.HelmAccess; import oracle.kubernetes.operator.http.BaseServer; import oracle.kubernetes.operator.http.metrics.MetricsServer; import oracle.kubernetes.operator.http.rest.BaseRestServer; @@ -47,8 +48,6 @@ import oracle.kubernetes.operator.work.ThreadFactorySingleton; import oracle.kubernetes.utils.SystemClock; -import static oracle.kubernetes.operator.http.metrics.MetricsServer.DEFAULT_METRICS_PORT; - /** An abstract base main class for the operator and the webhook. */ public abstract class BaseMain { static final LoggingFacade LOGGER = LoggingFactory.getLogger("Operator", "Operator"); @@ -87,13 +86,13 @@ public abstract class BaseMain { // top-level directory using either an env variable or a property. In the normal, // container-based use case these values won't be set and the operator will with the // /operator directory. - String deploymentHomeLoc = System.getenv("DEPLOYMENT_HOME"); + String deploymentHomeLoc = HelmAccess.getHelmVariable("DEPLOYMENT_HOME"); if (deploymentHomeLoc == null) { deploymentHomeLoc = System.getProperty("deploymentHome", "/deployment"); } deploymentHome = new File(deploymentHomeLoc); - String probesHomeLoc = System.getenv("PROBES_HOME"); + String probesHomeLoc = HelmAccess.getHelmVariable("PROBES_HOME"); if (probesHomeLoc == null) { probesHomeLoc = System.getProperty("probesHome", "/probes"); } @@ -196,7 +195,7 @@ void stopRestServer() { void startMetricsServer(Container container) throws UnrecoverableKeyException, CertificateException, IOException, NoSuchAlgorithmException, KeyStoreException, InvalidKeySpecException, KeyManagementException { - startMetricsServer(container, DEFAULT_METRICS_PORT); + startMetricsServer(container, delegate.getMetricsPort()); } // for test diff --git a/operator/src/main/java/oracle/kubernetes/operator/CoreDelegate.java b/operator/src/main/java/oracle/kubernetes/operator/CoreDelegate.java index 570f8bc0ee9..362f76f2994 100644 --- a/operator/src/main/java/oracle/kubernetes/operator/CoreDelegate.java +++ b/operator/src/main/java/oracle/kubernetes/operator/CoreDelegate.java @@ -4,11 +4,13 @@ package oracle.kubernetes.operator; import java.io.File; +import java.io.IOException; import java.util.concurrent.ScheduledFuture; import java.util.concurrent.TimeUnit; import oracle.kubernetes.operator.helpers.KubernetesVersion; import oracle.kubernetes.operator.helpers.SemanticVersion; +import oracle.kubernetes.operator.http.metrics.MetricsServer; import oracle.kubernetes.operator.work.Component; import oracle.kubernetes.operator.work.Packet; import oracle.kubernetes.operator.work.PacketComponent; @@ -34,6 +36,14 @@ public interface CoreDelegate extends PacketComponent { File getProbesHome(); + default boolean createNewFile(File file) throws IOException { + return file.createNewFile(); + } + + default int getMetricsPort() { + return MetricsServer.DEFAULT_METRICS_PORT; + } + default void runSteps(Step firstStep) { runSteps(new Packet(), firstStep, null); } diff --git a/operator/src/main/java/oracle/kubernetes/operator/DeploymentReady.java b/operator/src/main/java/oracle/kubernetes/operator/DeploymentReady.java index f500dba409f..9d7b5b9171c 100644 --- a/operator/src/main/java/oracle/kubernetes/operator/DeploymentReady.java +++ b/operator/src/main/java/oracle/kubernetes/operator/DeploymentReady.java @@ -1,4 +1,4 @@ -// Copyright (c) 2019, 2022, Oracle and/or its affiliates. +// Copyright (c) 2019, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.kubernetes.operator; @@ -13,10 +13,12 @@ public class DeploymentReady { private static final LoggingFacade LOGGER = LoggingFactory.getLogger("Operator", "Operator"); + private final CoreDelegate delegate; private final File readinessFile; public DeploymentReady(CoreDelegate delegate) { - readinessFile = new File(delegate.getProbesHome(), ".ready"); + this.delegate = delegate; + this.readinessFile = new File(delegate.getProbesHome(), ".ready"); } /** @@ -24,7 +26,7 @@ public DeploymentReady(CoreDelegate delegate) { * @throws IOException if the readiness file does not exist */ public void create() throws IOException { - if (readinessFile.createNewFile()) { + if (delegate.createNewFile(readinessFile)) { LOGGER.fine("Readiness file created"); } } diff --git a/operator/src/main/java/oracle/kubernetes/operator/KubernetesConstants.java b/operator/src/main/java/oracle/kubernetes/operator/KubernetesConstants.java index 58e423d67bd..f30e70ee1f1 100644 --- a/operator/src/main/java/oracle/kubernetes/operator/KubernetesConstants.java +++ b/operator/src/main/java/oracle/kubernetes/operator/KubernetesConstants.java @@ -1,4 +1,4 @@ -// Copyright (c) 2017, 2022, Oracle and/or its affiliates. +// Copyright (c) 2017, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.kubernetes.operator; @@ -44,6 +44,7 @@ public interface KubernetesConstants { String SCRIPT_CONFIG_MAP_NAME = "weblogic-scripts-cm"; String DOMAIN_DEBUG_CONFIG_MAP_SUFFIX = "-weblogic-domain-debug-cm"; + String OPERATOR_ENABLE_REST_ENDPOINT_ENV = "ENABLE_REST_ENDPOINT"; String OPERATOR_NAMESPACE_ENV = "OPERATOR_NAMESPACE"; String OPERATOR_POD_NAME_ENV = "OPERATOR_POD_NAME"; diff --git a/operator/src/main/java/oracle/kubernetes/operator/OperatorMain.java b/operator/src/main/java/oracle/kubernetes/operator/OperatorMain.java index d5942b40573..863285eb306 100644 --- a/operator/src/main/java/oracle/kubernetes/operator/OperatorMain.java +++ b/operator/src/main/java/oracle/kubernetes/operator/OperatorMain.java @@ -1,8 +1,15 @@ -// Copyright (c) 2017, 2022, Oracle and/or its affiliates. +// Copyright (c) 2017, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.kubernetes.operator; +import java.io.IOException; +import java.security.KeyManagementException; +import java.security.KeyStoreException; +import java.security.NoSuchAlgorithmException; +import java.security.UnrecoverableKeyException; +import java.security.cert.CertificateException; +import java.security.spec.InvalidKeySpecException; import java.time.OffsetDateTime; import java.util.Collection; import java.util.Collections; @@ -25,6 +32,7 @@ import oracle.kubernetes.common.logging.MessageKeys; import oracle.kubernetes.operator.calls.CallResponse; import oracle.kubernetes.operator.helpers.CallBuilder; +import oracle.kubernetes.operator.helpers.HelmAccess; import oracle.kubernetes.operator.helpers.KubernetesUtils; import oracle.kubernetes.operator.helpers.PodHelper; import oracle.kubernetes.operator.helpers.ResponseStep; @@ -37,12 +45,14 @@ import oracle.kubernetes.operator.tuning.TuningParameters; import oracle.kubernetes.operator.utils.Certificates; import oracle.kubernetes.operator.work.Component; +import oracle.kubernetes.operator.work.Container; import oracle.kubernetes.operator.work.FiberGate; import oracle.kubernetes.operator.work.NextAction; import oracle.kubernetes.operator.work.Packet; import oracle.kubernetes.operator.work.Step; import oracle.kubernetes.weblogic.domain.model.DomainList; +import static oracle.kubernetes.operator.KubernetesConstants.OPERATOR_ENABLE_REST_ENDPOINT_ENV; import static oracle.kubernetes.operator.ProcessingConstants.WEBHOOK; import static oracle.kubernetes.operator.helpers.NamespaceHelper.getOperatorNamespace; @@ -56,19 +66,21 @@ public class OperatorMain extends BaseMain { @SuppressWarnings({"FieldMayBeFinal", "CanBeFinal"}) private static NextStepFactory nextStepFactory = OperatorMain::createInitializeInternalIdentityStep; - /** The interval in sec that the operator will check the CRD presence and log a message if CRD not installed. */ + /** + * The interval in sec that the operator will check the CRD presence and log a message if CRD not installed. + */ private static final long CRD_DETECTION_DELAY = 10; static { container - .getComponents() - .put( - ProcessingConstants.MAIN_COMPONENT_NAME, - Component.createFor( - ScheduledExecutorService.class, - wrappedExecutorService, - ThreadFactory.class, - threadFactory)); + .getComponents() + .put( + ProcessingConstants.MAIN_COMPONENT_NAME, + Component.createFor( + ScheduledExecutorService.class, + wrappedExecutorService, + ThreadFactory.class, + threadFactory)); } @@ -110,7 +122,7 @@ private void logStartup(LoggingFacade loggingFacade) { loggingFacade.info(MessageKeys.OP_CONFIG_NAMESPACE, getOperatorNamespace()); loggingFacade.info(MessageKeys.OP_CONFIG_SERVICE_ACCOUNT, serviceAccountName); Optional.ofNullable(Namespaces.getConfiguredDomainNamespaces()) - .ifPresent(strings -> logConfiguredNamespaces(loggingFacade, strings)); + .ifPresent(strings -> logConfiguredNamespaces(loggingFacade, strings)); } private void logConfiguredNamespaces(LoggingFacade loggingFacade, Collection configuredDomainNamespaces) { @@ -164,15 +176,17 @@ public AtomicReference getCrdReference() { * @param args none, ignored */ public static void main(String[] args) { - OperatorMain operatorMain = createMain(getBuildProperties()); + createMain(getBuildProperties()).doMain(); + } + void doMain() { try { - operatorMain.startDeployment(operatorMain::completeBegin); + startDeployment(this::completeBegin); // now we just wait until the pod is terminated - operatorMain.waitForDeath(); + waitForDeath(); - operatorMain.stopDeployment(operatorMain::completeStop); + stopDeployment(this::completeStop); } finally { LOGGER.info(MessageKeys.OPERATOR_SHUTTING_DOWN); } @@ -243,9 +257,9 @@ private Step createOperatorNamespaceEventListStep() { @Override public Step getDefaultSelection() { return Step.chain( - new CallBuilder().listNamespaceAsync(new StartNamespaceWatcherStep()), - createOperatorNamespaceEventListStep(), - createDomainRecheckSteps()); + new CallBuilder().listNamespaceAsync(new StartNamespaceWatcherStep()), + createOperatorNamespaceEventListStep(), + createDomainRecheckSteps()); } } @@ -267,7 +281,7 @@ public NextAction onSuccess(Packet packet, CallResponse callRes } } - private void completeBegin() { + void completeBegin() { try { startMetricsServer(container); startRestServer(container); @@ -285,7 +299,17 @@ private void completeBegin() { } } - private void completeStop() { + @Override + void startRestServer(Container container) + throws UnrecoverableKeyException, CertificateException, IOException, NoSuchAlgorithmException, + KeyStoreException, InvalidKeySpecException, KeyManagementException { + if (Optional.ofNullable(HelmAccess.getHelmVariable(OPERATOR_ENABLE_REST_ENDPOINT_ENV)) + .map(Boolean::valueOf).orElse(Boolean.FALSE)) { + super.startRestServer(container); + } + } + + void completeStop() { stopRestServer(); stopMetricsServer(); } diff --git a/operator/src/main/java/oracle/kubernetes/operator/http/metrics/MetricsServer.java b/operator/src/main/java/oracle/kubernetes/operator/http/metrics/MetricsServer.java index ddacd025d47..1b3269ac425 100644 --- a/operator/src/main/java/oracle/kubernetes/operator/http/metrics/MetricsServer.java +++ b/operator/src/main/java/oracle/kubernetes/operator/http/metrics/MetricsServer.java @@ -1,4 +1,4 @@ -// Copyright (c) 2022, Oracle and/or its affiliates. +// Copyright (c) 2022, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.kubernetes.operator.http.metrics; @@ -21,10 +21,6 @@ public class MetricsServer extends BaseServer { private final AtomicReference metricsHttpServer = new AtomicReference<>(); private final int port; - public MetricsServer() { - this(DEFAULT_METRICS_PORT); - } - // for test public MetricsServer(int port) { this.port = port; diff --git a/operator/src/test/java/oracle/kubernetes/operator/OperatorMainTest.java b/operator/src/test/java/oracle/kubernetes/operator/OperatorMainTest.java index 4c925317b4b..574f7aa2c0f 100644 --- a/operator/src/test/java/oracle/kubernetes/operator/OperatorMainTest.java +++ b/operator/src/test/java/oracle/kubernetes/operator/OperatorMainTest.java @@ -1,8 +1,9 @@ -// Copyright (c) 2018, 2022, Oracle and/or its affiliates. +// Copyright (c) 2018, 2023, Oracle and/or its affiliates. // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. package oracle.kubernetes.operator; +import java.io.File; import java.io.IOException; import java.net.HttpURLConnection; import java.security.KeyManagementException; @@ -21,6 +22,8 @@ import java.util.Optional; import java.util.Properties; import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ScheduledFuture; +import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicReference; import java.util.logging.Level; import java.util.logging.LogRecord; @@ -48,9 +51,12 @@ import oracle.kubernetes.operator.helpers.KubernetesUtils; import oracle.kubernetes.operator.helpers.KubernetesVersion; import oracle.kubernetes.operator.helpers.SemanticVersion; +import oracle.kubernetes.operator.http.BaseServer; import oracle.kubernetes.operator.http.metrics.MetricsServer; import oracle.kubernetes.operator.tuning.TuningParametersStub; +import oracle.kubernetes.operator.utils.InMemoryFileSystem; import oracle.kubernetes.operator.work.Component; +import oracle.kubernetes.operator.work.Container; import oracle.kubernetes.operator.work.FiberTestSupport; import oracle.kubernetes.operator.work.Packet; import oracle.kubernetes.operator.work.Step; @@ -59,11 +65,14 @@ import oracle.kubernetes.utils.TestUtils; import org.glassfish.grizzly.http.server.HttpHandlerRegistration; import org.glassfish.grizzly.http.server.HttpServer; +import org.glassfish.jersey.server.ResourceConfig; import org.hamcrest.Description; import org.hamcrest.TypeSafeDiagnosingMatcher; +import org.junit.Assert; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.parallel.ResourceLock; import static com.meterware.simplestub.Stub.createNiceStub; import static com.meterware.simplestub.Stub.createStrictStub; @@ -88,6 +97,7 @@ import static oracle.kubernetes.operator.EventTestUtils.containsEventWithMessageForNamespaces; import static oracle.kubernetes.operator.EventTestUtils.getEvents; import static oracle.kubernetes.operator.EventTestUtils.getFormattedMessage; +import static oracle.kubernetes.operator.KubernetesConstants.OPERATOR_ENABLE_REST_ENDPOINT_ENV; import static oracle.kubernetes.operator.KubernetesConstants.OPERATOR_NAMESPACE_ENV; import static oracle.kubernetes.operator.KubernetesConstants.OPERATOR_POD_NAME_ENV; import static oracle.kubernetes.operator.KubernetesConstants.SCRIPT_CONFIG_MAP_NAME; @@ -115,6 +125,7 @@ import static org.hamcrest.Matchers.notNullValue; import static org.hamcrest.Matchers.nullValue; import static org.hamcrest.junit.MatcherAssert.assertThat; +import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; import static org.junit.jupiter.api.Assertions.assertFalse; import static org.junit.jupiter.api.Assertions.assertInstanceOf; import static org.junit.jupiter.api.Assertions.assertNotNull; @@ -175,6 +186,7 @@ class OperatorMainTest extends ThreadFactoryTestBase { private final DomainNamespaces domainNamespaces = new DomainNamespaces(null); private final MainDelegateStub delegate = createStrictStub(MainDelegateStub.class, testSupport, domainNamespaces); private final OperatorMain operatorMain = new OperatorMain(delegate); + private static final InMemoryFileSystem inMemoryFileSystem = InMemoryFileSystem.createInstance(); private final Map> domainEventObjects = new ConcurrentHashMap<>(); private final Map nsEventObjects = new ConcurrentHashMap<>(); @@ -213,9 +225,11 @@ public void setUp() throws Exception { mementos.add(NoopWatcherStarter.install()); mementos.add(StaticStubSupport.install(DomainProcessorImpl.class, "domainEventK8SObjects", domainEventObjects)); mementos.add(StaticStubSupport.install(DomainProcessorImpl.class, "namespaceEventK8SObjects", nsEventObjects)); + mementos.add(inMemoryFileSystem.install()); HelmAccessStub.defineVariable(OPERATOR_NAMESPACE_ENV, OP_NS); HelmAccessStub.defineVariable(OPERATOR_POD_NAME_ENV, OPERATOR_POD_NAME); + HelmAccessStub.defineVariable(OPERATOR_ENABLE_REST_ENDPOINT_ENV, "true"); } @AfterEach @@ -1235,6 +1249,57 @@ void withNamespaceDedicated_changeToList_onCreateReadNamespaces_StartManagingNSE START_MANAGING_NAMESPACE, Collections.singletonList("NS1")), is(true)); } + @Test + @ResourceLock(value = "operatorMain") + void whenShutdownMarkerIsCreate_stopOperator() { + inMemoryFileSystem.defineFile("/deployment/marker.shutdown", "shutdown"); + operatorMain.doMain(); + assertThat(operatorMain.getShutdownSignalAvailablePermits(), equalTo(0)); + } + + @Test + void whenOperatorStopped_restServerShutdown() { + OperatorMain m = OperatorMain.createMain(buildProperties); + BaseServerStub restServer = new BaseServerStub(); + m.getRestServer().set(restServer); + m.completeStop(); + Assert.assertTrue(restServer.isStopCalled); + assertThat(m.getRestServer().get(), nullValue()); + } + + @Test + @ResourceLock(value = "operatorMain") + void startAndStopOperator() { + assertDoesNotThrow(() -> { + operatorMain.completeBegin(); + operatorMain.completeStop(); + }); + } + + private static class BaseServerStub extends BaseServer { + private boolean isStopCalled = false; + + @Override + public void start(Container container) throws UnrecoverableKeyException, CertificateException, IOException, + NoSuchAlgorithmException, KeyStoreException, InvalidKeySpecException, KeyManagementException { + // no-op + } + + @Override + public void stop() { + isStopCalled = true; + } + + public boolean isStopCalled() { + return isStopCalled; + } + + @Override + protected ResourceConfig createResourceConfig() { + throw new IllegalStateException(); + } + } + abstract static class MainDelegateStub implements MainDelegate { private final FiberTestSupport testSupport; private final DomainNamespaces domainNamespaces; @@ -1286,6 +1351,39 @@ public void hideCRD() { public AtomicReference getCrdReference() { return hideCRD ? new AtomicReference<>() : crdReference; } + + @Override + public File getDeploymentHome() { + return new File("/deployment"); + } + + @Override + public File getProbesHome() { + return new File("/probes"); + } + + public boolean createNewFile(File file) throws IOException { + // skip creating ready probe file + if ("/probes/.ready".equals(file.getPath())) { + return true; + } + return file.createNewFile(); + } + + @Override + public String getPrincipal() { + return null; + } + + @Override + public int getMetricsPort() { + return 8090; + } + + @Override + public ScheduledFuture scheduleWithFixedDelay(Runnable command, long initialDelay, long delay, TimeUnit unit) { + return testSupport.scheduleWithFixedDelay(command, initialDelay, delay, unit); + } } static class TestStepFactory implements OperatorMain.NextStepFactory {