diff --git a/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/configuration/atlas-application-properties.xml b/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/configuration/atlas-application-properties.xml
new file mode 100644
index 000000000..c6286c9bf
--- /dev/null
+++ b/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/configuration/atlas-application-properties.xml
@@ -0,0 +1,208 @@
+
+
+
+
+
+
+ atlas.graph.storage.backend
+ hbase2
+
+
+ atlas.graph.storage.hbase.table
+ apache_atlas_janus
+
+
+ atlas.graph.storage.hostname
+ ${atlas_graph_storage_hostname}
+
+
+ atlas.graph.storage.hbase.regions-per-server
+ 1
+
+
+
+
+ atlas.graph.index.search.backend
+ ${atlas_graph_index_search_backend}
+
+
+ atlas.graph.index.search.hostname
+ ${atlas_graph_index_search_hostname}
+
+
+ atlas.graph.index.search.elasticsearch.client-only
+ true
+
+
+ atlas.graph.index.search.elasticsearch.http.auth.type
+ basic
+
+
+ atlas.graph.index.search.elasticsearch.http.auth.basic.username
+ ${atlas_elasticsearch_username}
+
+
+ atlas.graph.index.search.elasticsearch.http.auth.basic.password
+ ${atlas_elasticsearch_password}
+
+
+ atlas.graph.index.search.max-result-set-size
+ 150
+
+
+
+
+ atlas.EntityAuditRepository.impl
+ org.apache.atlas.repository.audit.HBaseBasedAuditRepository
+
+
+
+
+ atlas.notification.embedded
+ false
+
+
+ atlas.kafka.zookeeper.connect
+ ${atlas_kafka_zookeeper_connect}
+
+
+ atlas.kafka.bootstrap.servers
+ ${atlas_kafka_bootstrap_servers}
+
+
+ atlas.kafka.hook.group.id
+ atlas
+
+
+ atlas.notification.topics
+ ATLAS_HOOK,ATLAS_ENTITIES
+
+
+ atlas.notification.hook.topic.name
+ ATLAS_HOOK
+
+
+ atlas.notification.entities.topic.name
+ ATLAS_ENTITIES
+
+
+
+
+ atlas.rest.address
+ ${atlas_rest_address}
+
+
+ atlas.server.run.setup.on.start
+ false
+
+
+
+
+ atlas.audit.hbase.tablename
+ apache_atlas_entity_audit
+
+
+ atlas.audit.hbase.zookeeper.quorum
+ ${atlas_audit_hbase_zookeeper_quorum}
+
+
+
+
+ atlas.enableTLS
+ false
+
+
+ atlas.authentication.method.file
+ true
+
+
+ atlas.authentication.method.kerberos
+ false
+
+
+ atlas.authentication.method.ldap.type
+ none
+
+
+ atlas.authentication.method.file.filename
+ ${sys:atlas.home}/conf/users-credentials.properties
+
+
+
+
+ atlas.authorizer.impl
+ simple
+
+
+ atlas.authorizer.simple.authz.policy.file
+ atlas-simple-authz-policy.json
+
+
+
+
+ atlas.search.gremlin.enable
+ false
+
+
+ atlas.query.gremlinOptimizerEnabled
+ true
+
+
+
+
+ atlas.rest-csrf.enabled
+ true
+
+
+ atlas.rest-csrf.browser-useragents-regex
+ ^Mozilla.*,^Opera.*,^Chrome.*
+
+
+ atlas.rest-csrf.methods-to-ignore
+ GET,OPTIONS,HEAD,TRACE
+
+
+ atlas.rest-csrf.custom-header
+ X-XSRF-HEADER
+
+
+
+
+ atlas.ui.default.version
+ v1
+
+
+
+
+ atlas.hook.hive.numRetries
+ 3
+
+
+ atlas.hook.hive.queueSize
+ 10000
+
+
+
+
+ atlas.cluster.name
+ primary
+
+
+
\ No newline at end of file
diff --git a/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/configuration/atlas-env.xml b/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/configuration/atlas-env.xml
new file mode 100644
index 000000000..9018ac59c
--- /dev/null
+++ b/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/configuration/atlas-env.xml
@@ -0,0 +1,89 @@
+
+
+
+
+
+ content
+ Freemarker template for atlas-env.sh
+
+export ATLAS_SERVER_HEAP="${atlas_server_heap}"
+#if>
+<#if atlas_server_opts?has_content>
+export ATLAS_SERVER_OPTS="${atlas_server_opts}"
+#if>
+<#if atlas_client_heap?has_content>
+export ATLAS_CLIENT_HEAP="${atlas_client_heap}"
+#if>
+<#if atlas_client_opts?has_content>
+export ATLAS_CLIENT_OPTS="${atlas_client_opts}"
+#if>
+
+# Solr / ES address
+<#if solr_zk_quorum?has_content>
+export SOLR_ZK_QUORUM=${solr_zk_quorum}
+#if>
+<#if es_hosts?has_content>
+export ES_HOSTS=${es_hosts}
+export ES_HTTP_URLS=${es_http_urls}
+#if>
+]]>
+
+
+ longtext
+
+
+
\ No newline at end of file
diff --git a/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/metainfo.xml b/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/metainfo.xml
new file mode 100644
index 000000000..9f37895ef
--- /dev/null
+++ b/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/metainfo.xml
@@ -0,0 +1,71 @@
+
+
+
+ 2.0
+
+ atlas
+ Atlas
+
+ Apache Atlas is a scalable and extensible set of core foundational governance services
+ enabling enterprises to effectively and efficiently meet their compliance requirements
+ within Hadoop and allows integration with the whole enterprise data ecosystem.
+
+ 2.3.0-1
+ atlas
+ Apache-2.0
+
+
+
+ atlas_instance
+ Atlas Instance
+ server
+ 1+
+
+ Atlas UI
+ atlas_port
+ 21000
+ atlas_port
+ 21443
+
+
+
+
+
+
+
+ x86_64
+ aarch64
+
+
+
+ atlas-2.3.0.tar.gz
+ SHA-256:ebe5a922f0eab640b07f4730b23626db830a28ae4085de54c85d6f11297675f4
+
+
+
+
+
+
+ zookeeper
+ hbase
+ kafka
+
+
+
\ No newline at end of file
diff --git a/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/order.json b/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/order.json
new file mode 100644
index 000000000..ffc683eb2
--- /dev/null
+++ b/bigtop-manager-server/src/main/resources/stacks/bigtop/3.3.0/services/atlas/order.json
@@ -0,0 +1,14 @@
+{
+ "ATLAS_INSTANCE-START": [
+ "ZOOKEEPER_SERVER-START",
+ "HBASE_MASTER-START",
+ "HBASE_REGIONSERVER-START",
+ "KAFKA_BROKER-START"
+ ],
+ "ATLAS_INSTANCE-RESTART": [
+ "ZOOKEEPER_SERVER-RESTART",
+ "HBASE_MASTER-RESTART",
+ "HBASE_REGIONSERVER-RESTART",
+ "KAFKA_BROKER-RESTART"
+ ]
+}
diff --git a/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/main/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasInstanceScript.java b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/main/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasInstanceScript.java
new file mode 100644
index 000000000..971e542ef
--- /dev/null
+++ b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/main/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasInstanceScript.java
@@ -0,0 +1,91 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * https://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.bigtop.manager.stack.bigtop.v3_3_0.atlas;
+
+import com.google.auto.service.AutoService;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.bigtop.manager.common.shell.ShellResult;
+import org.apache.bigtop.manager.stack.core.exception.StackException;
+import org.apache.bigtop.manager.stack.core.spi.param.Params;
+import org.apache.bigtop.manager.stack.core.spi.script.AbstractClientScript;
+import org.apache.bigtop.manager.stack.core.spi.script.Script;
+import org.apache.bigtop.manager.stack.core.utils.linux.LinuxOSUtils;
+
+import java.io.IOException;
+import java.text.MessageFormat;
+import java.util.Properties;
+
+@Slf4j
+@AutoService(Script.class)
+public class AtlasInstanceScript extends AbstractClientScript {
+ @Override
+ public ShellResult add(Params params) {
+ Properties properties = new Properties();
+ properties.setProperty(PROPERTY_KEY_SKIP_LEVELS, "1");
+ return super.add(params, properties);
+ }
+
+ @Override
+ public ShellResult configure(Params params) {
+ super.configure(params);
+ return AtlasSetup.configure(params);
+ }
+
+ @Override
+ public ShellResult init(Params params) {
+ // Atlas does not need to manually create znode like Solr, leave it empty
+ return super.init(params);
+ }
+
+ @Override
+ public ShellResult start(Params params) {
+ configure(params);
+ AtlasParams atlasParams = (AtlasParams) params;
+ String cmd = MessageFormat.format(
+ "{0}/bin/atlas_start.py --port {1}",
+ atlasParams.serviceHome(), atlasParams.getAtlasPort());
+ try {
+ return LinuxOSUtils.sudoExecCmd(cmd, atlasParams.user());
+ } catch (IOException e) {
+ throw new StackException(e);
+ }
+ }
+
+ @Override
+ public ShellResult stop(Params params) {
+ AtlasParams atlasParams = (AtlasParams) params;
+ String cmd = MessageFormat.format("{0}/bin/atlas_stop.py", atlasParams.serviceHome());
+ try {
+ return LinuxOSUtils.sudoExecCmd(cmd, atlasParams.user());
+ } catch (IOException e) {
+ throw new StackException(e);
+ }
+ }
+
+ @Override
+ public ShellResult status(Params params) {
+ AtlasParams atlasParams = (AtlasParams) params;
+ return LinuxOSUtils.checkProcess(atlasParams.getAtlasPidFile());
+ }
+
+ @Override
+ public String getComponentName() {
+ return "atlas_instance";
+ }
+}
diff --git a/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/main/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasParams.java b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/main/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasParams.java
new file mode 100644
index 000000000..33609d1a0
--- /dev/null
+++ b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/main/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasParams.java
@@ -0,0 +1,286 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * https://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.bigtop.manager.stack.bigtop.v3_3_0.atlas;
+
+import org.apache.bigtop.manager.grpc.payload.ComponentCommandPayload;
+import org.apache.bigtop.manager.stack.bigtop.param.BigtopParams;
+import org.apache.bigtop.manager.stack.core.annotations.GlobalParams;
+import org.apache.bigtop.manager.stack.core.spi.param.Params;
+import org.apache.bigtop.manager.stack.core.utils.LocalSettings;
+
+import com.google.auto.service.AutoService;
+import lombok.Getter;
+import lombok.NoArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
+
+import java.text.MessageFormat;
+import java.util.List;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+@Getter
+@Slf4j
+@AutoService(Params.class)
+@NoArgsConstructor
+public class AtlasParams extends BigtopParams {
+
+ /* ======== Atlas Settings ======== */
+ private String atlasPort = "21000";
+ private String atlasLogDir = "/var/log/atlas";
+ private String atlasPidDir = "/var/run/atlas";
+ private String atlasPidFile = atlasPidDir + "/atlas.pid";
+ private String atlasConfDir = null;
+
+ /* ======== External Components ======== */
+ private String hbaseConfDir = "/etc/hbase/conf";
+ private String hadoopHome = "/usr/lib/hadoop";
+ private String zkQuorum = null;
+
+ /* ======== Solr ======== */
+ private String solrZkQuorum = null;
+ private String solrZkZnode = "/solr";
+ private String solrPort = "8983";
+
+ /* ======== Elasticsearch ======== */
+ private String esHosts = null; // host1:9200,host2:9200
+ private String esHttpUrls = null; // http://host1:9200,http://host2:9200
+ private String esUsername = "elastic";
+ private String esPassword = "";
+
+ /* ======== Kafka ======== */
+ private String kafkaBootstrapServers = null;
+
+ /* ======== Search Backend Type ======== */
+ private String searchBackend = "elasticsearch"; // "elasticsearch" or "solr"
+
+ /* ======== Configuration Sources ======== */
+ private Map atlasEnvMap;
+ private Map appPropsMap;
+
+ public AtlasParams(ComponentCommandPayload payload) {
+ super(payload);
+ atlasConfDir = serviceHome() + "/conf";
+ globalParamsMap.put("java_home", javaHome());
+ globalParamsMap.put("atlas_home", serviceHome());
+ globalParamsMap.put("atlas_user", user());
+ globalParamsMap.put("atlas_group", group());
+ globalParamsMap.put("atlas_conf_dir", atlasConfDir);
+ globalParamsMap.put("atlas_pid_file", atlasPidFile);
+ }
+
+ /* --------------------------------------------------
+ * 1. atlas-env.xml
+ * -------------------------------------------------- */
+ @GlobalParams
+ public Map atlasEnv() {
+ atlasEnvMap = LocalSettings.configurations(getServiceName(), "atlas-env");
+
+ atlasLogDir = (String) atlasEnvMap.getOrDefault("atlas_log_dir", atlasLogDir);
+ atlasPidDir = (String) atlasEnvMap.getOrDefault("atlas_pid_dir", atlasPidDir);
+ atlasPort = (String) atlasEnvMap.getOrDefault("atlas_port", atlasPort);
+ atlasPidFile = atlasPidDir + "/atlas.pid";
+
+ hbaseConfDir = (String) atlasEnvMap.getOrDefault("hbase_conf_dir", hbaseConfDir);
+ hadoopHome = (String) atlasEnvMap.getOrDefault("hadoop_home", hadoopHome);
+
+ /* ZooKeeper Quorum */
+ List zkHosts = LocalSettings.componentHosts("zookeeper_server");
+ String zkPort = (String) LocalSettings.configurations("zookeeper", "zoo.cfg").get("clientPort");
+ zkQuorum = zkHosts.stream().map(h -> h + ":" + zkPort).collect(Collectors.joining(","));
+ atlasEnvMap.put("zk_quorum", zkQuorum);
+
+ /* Determine search backend: try Elasticsearch first, then Solr */
+ boolean esAvailable = isElasticsearchAvailable();
+ boolean solrAvailable = isSolrAvailable();
+
+ if (esAvailable) {
+ searchBackend = "elasticsearch";
+ loadEsParams();
+ log.info("Atlas will use Elasticsearch as search backend");
+ } else if (solrAvailable) {
+ searchBackend = "solr";
+ loadSolrParams();
+ log.info("Atlas will use Solr as search backend");
+ } else {
+ log.warn("Neither Elasticsearch nor Solr is available. Atlas search functionality may be limited.");
+ // Load both with empty values for graceful degradation
+ loadSolrParams();
+ loadEsParams();
+ }
+
+ /* Kafka */
+ loadKafkaParams();
+
+ globalParamsMap.putAll(atlasEnvMap);
+ return atlasEnvMap;
+ }
+
+ /* --------------------------------------------------
+ * 2. atlas-application-properties.xmlaa
+ * -------------------------------------------------- */
+ @GlobalParams
+ public Map applicationProperties() {
+ appPropsMap = LocalSettings.configurations(getServiceName(), "application-properties");
+
+ /* Populate dynamic values into template, ${xxx} will be auto-replaced */
+ // Search backend type
+ appPropsMap.put("atlas_graph_index_search_backend", searchBackend);
+
+ // ZooKeeper related
+ appPropsMap.put("atlas_graph_storage_hostname", zkQuorum);
+ appPropsMap.put("atlas_kafka_zookeeper_connect", zkQuorum);
+ appPropsMap.put("atlas_audit_hbase_zookeeper_quorum", zkQuorum);
+
+ // Elasticsearch
+ appPropsMap.put("atlas_graph_index_search_hostname", esHosts);
+ appPropsMap.put("atlas_elasticsearch_username", esUsername);
+ appPropsMap.put("atlas_elasticsearch_password", esPassword);
+
+ // Kafka
+ appPropsMap.put("atlas_kafka_bootstrap_servers", kafkaBootstrapServers);
+
+ // Atlas REST address
+ String atlasRestAddress = MessageFormat.format("http://{0}:{1}", hostname(), atlasPort);
+ appPropsMap.put("atlas_rest_address", atlasRestAddress);
+
+ // Legacy properties for backwards compatibility
+ appPropsMap.put("atlas.graph.index.search.solr.zookeeper-url", solrZkQuorum);
+ appPropsMap.put("atlas.graph.index.search.solr.zookeeper-znode", solrZkZnode);
+ appPropsMap.put("atlas.graph.index.search.elasticsearch.http-urls", esHttpUrls);
+
+ globalParamsMap.putAll(appPropsMap);
+ return appPropsMap;
+ }
+
+ /* ======== Private Helper Methods ======== */
+
+ /**
+ * Check if Elasticsearch is available in the cluster
+ */
+ private boolean isElasticsearchAvailable() {
+ try {
+ List esHosts = LocalSettings.componentHosts("elasticsearch_master");
+ return esHosts != null && !esHosts.isEmpty();
+ } catch (Exception e) {
+ return false;
+ }
+ }
+
+ /**
+ * Check if Solr is available in the cluster
+ */
+ private boolean isSolrAvailable() {
+ try {
+ Map solrEnv = LocalSettings.configurations("solr", "solr-env");
+ List solrHosts = LocalSettings.componentHosts("solr_instance");
+ return solrEnv != null && solrHosts != null && !solrHosts.isEmpty();
+ } catch (Exception e) {
+ return false;
+ }
+ }
+
+ private void loadSolrParams() {
+ try {
+ Map solrEnv = LocalSettings.configurations("solr", "solr-env");
+ if (solrEnv != null) {
+ solrPort = (String) solrEnv.getOrDefault("solr_port", "8983");
+ solrZkZnode = (String) solrEnv.getOrDefault("solr_znode", "/solr");
+ }
+
+ List zkHosts = LocalSettings.componentHosts("zookeeper_server");
+ if (zkHosts != null && !zkHosts.isEmpty()) {
+ String zkPort = (String) LocalSettings.configurations("zookeeper", "zoo.cfg").get("clientPort");
+ solrZkQuorum = zkHosts.stream()
+ .map(h -> h + ":" + zkPort + solrZkZnode)
+ .collect(Collectors.joining(","));
+ } else {
+ solrZkQuorum = "";
+ }
+ atlasEnvMap.put("solr_zk_quorum", solrZkQuorum);
+ atlasEnvMap.put("solr_port", solrPort);
+ atlasEnvMap.put("solr_zk_znode", solrZkZnode);
+ } catch (Exception e) {
+ log.warn("Failed to load Solr params, Solr may not be installed: {}", e.getMessage());
+ atlasEnvMap.put("solr_zk_quorum", "");
+ atlasEnvMap.put("solr_port", solrPort);
+ atlasEnvMap.put("solr_zk_znode", solrZkZnode);
+ }
+ }
+
+ private void loadEsParams() {
+ try {
+ // Try to get Elasticsearch hosts, if not available, use empty string
+ List esHostsList = LocalSettings.componentHosts("elasticsearch_master");
+ if (esHostsList != null && !esHostsList.isEmpty()) {
+ String esPort = "9200"; // Can also read from es-config.xml
+ esHosts = esHostsList.stream().map(h -> h + ":" + esPort).collect(Collectors.joining(","));
+ esHttpUrls = esHostsList.stream().map(h -> "http://" + h + ":" + esPort).collect(Collectors.joining(","));
+ } else {
+ esHosts = "";
+ esHttpUrls = "";
+ }
+
+ // Read ES credentials from configuration if available
+ Map appProps = LocalSettings.configurations(getServiceName(), "application-properties");
+ if (appProps != null) {
+ if (appProps.containsKey("atlas_elasticsearch_username")) {
+ esUsername = (String) appProps.get("atlas_elasticsearch_username");
+ }
+ if (appProps.containsKey("atlas_elasticsearch_password")) {
+ esPassword = (String) appProps.get("atlas_elasticsearch_password");
+ }
+ }
+ } catch (Exception e) {
+ log.warn("Failed to load Elasticsearch params, ES may not be installed: {}", e.getMessage());
+ esHosts = "";
+ esHttpUrls = "";
+ }
+
+ atlasEnvMap.put("es_hosts", esHosts);
+ atlasEnvMap.put("es_http_urls", esHttpUrls);
+ }
+
+ private void loadKafkaParams() {
+ try {
+ List kafkaHosts = LocalSettings.componentHosts("kafka_broker");
+ if (kafkaHosts != null && !kafkaHosts.isEmpty()) {
+ String kafkaPort = "9092"; // Can also read from kafka-config.xml
+ kafkaBootstrapServers = kafkaHosts.stream()
+ .map(h -> h + ":" + kafkaPort)
+ .collect(Collectors.joining(","));
+ } else {
+ kafkaBootstrapServers = "";
+ }
+ } catch (Exception e) {
+ log.warn("Failed to load Kafka params, Kafka may not be installed: {}", e.getMessage());
+ kafkaBootstrapServers = "";
+ }
+ atlasEnvMap.put("kafka_bootstrap_servers", kafkaBootstrapServers);
+ }
+
+ @Override
+ public String confDir() {
+ return atlasConfDir;
+ }
+
+ @Override
+ public String getServiceName() {
+ return "atlas";
+ }
+}
\ No newline at end of file
diff --git a/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/main/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasSetup.java b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/main/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasSetup.java
new file mode 100644
index 000000000..483abb217
--- /dev/null
+++ b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/main/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasSetup.java
@@ -0,0 +1,82 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * https://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.bigtop.manager.stack.bigtop.v3_3_0.atlas;
+
+import lombok.AccessLevel;
+import lombok.NoArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.bigtop.manager.common.constants.Constants;
+import org.apache.bigtop.manager.common.shell.ShellResult;
+import org.apache.bigtop.manager.stack.core.spi.param.Params;
+import org.apache.bigtop.manager.stack.core.utils.LocalSettings;
+import org.apache.bigtop.manager.stack.core.utils.linux.LinuxFileUtils;
+
+import java.text.MessageFormat;
+import java.util.HashMap;
+import java.util.Map;
+
+@Slf4j
+@NoArgsConstructor(access = AccessLevel.PRIVATE)
+public class AtlasSetup {
+ public static ShellResult configure(Params params) {
+ log.info("Configuring Atlas");
+ AtlasParams atlasParams = (AtlasParams) params;
+
+ String confDir = atlasParams.confDir();
+ String user = atlasParams.user();
+ String group = atlasParams.group();
+
+ // Call atlasEnv() to initialize all dependencies first
+ Map atlasEnv = atlasParams.atlasEnv();
+ // Call applicationProperties() to populate global params
+ atlasParams.applicationProperties();
+
+ // Create log and pid directories
+ LinuxFileUtils.createDirectories(atlasParams.getAtlasLogDir(), user, group, Constants.PERMISSION_755, true);
+ LinuxFileUtils.createDirectories(atlasParams.getAtlasPidDir(), user, group, Constants.PERMISSION_755, true);
+
+ // Render atlas-env.sh
+ Map additional = new HashMap<>();
+ additional.put("zk_quorum", atlasEnv.get("zk_quorum"));
+ additional.put("host", atlasParams.hostname());
+
+ LinuxFileUtils.toFileByTemplate(
+ atlasEnv.get("content").toString(),
+ MessageFormat.format("{0}/atlas-env.sh", atlasParams.serviceHome() + "/bin"),
+ user,
+ group,
+ Constants.PERMISSION_755,
+ atlasParams.getGlobalParamsMap(),
+ additional);
+
+ // Render atlas-application.properties
+ Map appProps = LocalSettings.configurations(atlasParams.getServiceName(), "application-properties");
+ LinuxFileUtils.toFileByTemplate(
+ appProps.get("content").toString(),
+ MessageFormat.format("{0}/atlas-application.properties", confDir),
+ user,
+ group,
+ Constants.PERMISSION_755,
+ atlasParams.getGlobalParamsMap(),
+ additional);
+
+ log.info("Successfully configured Atlas");
+ return ShellResult.success();
+ }
+}
diff --git a/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/test/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasInstanceScriptTest.java b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/test/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasInstanceScriptTest.java
new file mode 100644
index 000000000..2f11a60d0
--- /dev/null
+++ b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/test/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasInstanceScriptTest.java
@@ -0,0 +1,66 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * https://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.bigtop.manager.stack.bigtop.v3_3_0.atlas;
+
+import org.apache.bigtop.manager.stack.core.spi.param.Params;
+
+import org.junit.jupiter.api.Test;
+
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertThrows;
+
+public class AtlasInstanceScriptTest {
+
+ private final AtlasInstanceScript atlasInstanceScript = new AtlasInstanceScript();
+
+ @Test
+ public void testGetComponentName() {
+ assertEquals("atlas_instance", atlasInstanceScript.getComponentName());
+ }
+
+ @Test
+ public void testAddParamsNull() {
+ Params params = null;
+ assertThrows(NullPointerException.class, () -> atlasInstanceScript.add(params));
+ }
+
+ @Test
+ public void testConfigureParamsNull() {
+ Params params = null;
+ assertThrows(NullPointerException.class, () -> atlasInstanceScript.configure(params));
+ }
+
+ @Test
+ public void testStartParamsNull() {
+ Params params = null;
+ assertThrows(NullPointerException.class, () -> atlasInstanceScript.start(params));
+ }
+
+ @Test
+ public void testStopParamsNull() {
+ Params params = null;
+ assertThrows(NullPointerException.class, () -> atlasInstanceScript.stop(params));
+ }
+
+ @Test
+ public void testStatusParamsNull() {
+ Params params = null;
+ assertThrows(NullPointerException.class, () -> atlasInstanceScript.status(params));
+ }
+}
diff --git a/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/test/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasParamsTest.java b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/test/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasParamsTest.java
new file mode 100644
index 000000000..2008e88f1
--- /dev/null
+++ b/bigtop-manager-stack/bigtop-manager-stack-bigtop/src/test/java/org/apache/bigtop/manager/stack/bigtop/v3_3_0/atlas/AtlasParamsTest.java
@@ -0,0 +1,55 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * https://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.bigtop.manager.stack.bigtop.v3_3_0.atlas;
+
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+
+public class AtlasParamsTest {
+
+ private AtlasParams atlasParams;
+
+ @BeforeEach
+ public void setUp() {
+ atlasParams = mock(AtlasParams.class);
+ when(atlasParams.stackHome()).thenReturn("/stack");
+ when(atlasParams.getServiceName()).thenCallRealMethod();
+ when(atlasParams.serviceHome()).thenCallRealMethod();
+ when(atlasParams.confDir()).thenCallRealMethod();
+ }
+
+ @Test
+ public void testServiceHome() {
+ assertEquals("/stack/atlas", atlasParams.serviceHome());
+ }
+
+ @Test
+ public void testConfDir() {
+ assertEquals("/stack/atlas/conf", atlasParams.confDir());
+ }
+
+ @Test
+ public void testGetServiceName() {
+ assertEquals("atlas", atlasParams.getServiceName());
+ }
+}