blob: adf555423258a10ee3d1ca2b43ca73f2792a0884 [file] [log] [blame]
/*
* 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
*
* http://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.ignite.yarn;
import java.io.FileInputStream;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.regex.Pattern;
import java.util.regex.PatternSyntaxException;
/**
* Cluster settings.
*/
public class ClusterProperties {
/** */
private static final Logger log = Logger.getLogger(ClusterProperties.class.getSimpleName());
/** */
public static final String EMPTY_STRING = "";
/** */
public static final String IGNITE_CLUSTER_NAME = "IGNITE_CLUSTER_NAME";
/** */
public static final String DEFAULT_CLUSTER_NAME = "ignite-cluster";
/** */
public static final double DEFAULT_CPU_PER_NODE = 2;
/** */
public static final double DEFAULT_MEM_PER_NODE = 2048;
/**
* The minimum memory overhead: overhead is by default 0.1* MEMORY_PER_NODE,
* with a minimum of DEFAULT_MINIMUM_MEM_OVERHEAD_PER_NODE.
*/
public static final double DEFAULT_MINIMUM_MEM_OVERHEAD_PER_NODE = 384;
/** Cluster name. */
private String clusterName = DEFAULT_CLUSTER_NAME;
/** */
public static final String IGNITE_RUN_CPU_PER_NODE = "IGNITE_RUN_CPU_PER_NODE";
/** CPU limit. */
private double cpuPerNode = DEFAULT_CPU_PER_NODE;
/** */
public static final String IGNITE_MEMORY_PER_NODE = "IGNITE_MEMORY_PER_NODE";
/** Memory limit. */
private double memPerNode = DEFAULT_MEM_PER_NODE;
/** */
public static final String IGNITE_MEMORY_OVERHEAD_PER_NODE = "IGNITE_MEMORY_OVERHEAD_PER_NODE";
/** Memory over head to request yarn. */
private double memOverHeadPerNode = 0;
/** */
public static final String IGNITE_NODE_COUNT = "IGNITE_NODE_COUNT";
/** */
public static final double DEFAULT_IGNITE_NODE_COUNT = 3;
/** Node count limit. */
private double nodeCnt = DEFAULT_IGNITE_NODE_COUNT;
/** */
public static final String IGNITE_URL = "IGNITE_URL";
/** Ignite version. */
private String igniteUrl = null;
/** */
public static final String IGNITE_WORKING_DIR = "IGNITE_WORKING_DIR";
/** */
public static final String DEFAULT_IGNITE_WORK_DIR = "/ignite/workdir/";
/** Ignite work directory. */
private String igniteWorkDir = DEFAULT_IGNITE_WORK_DIR;
/** */
public static final String IGNITE_PATH = "IGNITE_PATH";
/** Ignite path. */
private String ignitePath = null;
/** */
public static final String LICENCE_PATH = "LICENCE_PATH";
/** Licence path. */
private String licencePath = null;
/** */
public static final String IGNITE_JVM_OPTS = "IGNITE_JVM_OPTS";
/** JVM opts. */
private String jvmOpts = null;
/** */
public static final String IGNITE_LOCAL_WORK_DIR = "IGNITE_LOCAL_WORK_DIR";
/** */
public static final String DEFAULT_IGNITE_LOCAL_WORK_DIR = "./ignite-releases/";
/** Ignite local work directory. */
private String igniteLocalWorkDir = DEFAULT_IGNITE_LOCAL_WORK_DIR;
/** */
public static final String IGNITE_RELEASES_DIR = "IGNITE_RELEASES_DIR";
/** */
public static final String DEFAULT_IGNITE_RELEASES_DIR = "/ignite/releases/";
/** Ignite local work directory. */
private String igniteReleasesDir = DEFAULT_IGNITE_RELEASES_DIR;
/** */
public static final String IGNITE_USERS_LIBS = "IGNITE_USERS_LIBS";
/** Path to users libs. */
private String userLibs = null;
/** */
public static final String IGNITE_CONFIG_XML = "IGNITE_XML_CONFIG";
/** Ignite config. */
private String igniteCfg = null;
/** */
public static final String IGNITE_HOSTNAME_CONSTRAINT = "IGNITE_HOSTNAME_CONSTRAINT";
/** Url to ignite config. */
private Pattern hostnameConstraint = null;
/** Ignite Yarn Queue */
public static final String IGNITE_YARN_QUEUE = "IGNITE_YARN_QUEUE";
/** Ignite Yarn default Queue */
public static final String DEFAULT_IGNITE_YARN_QUEUE = "default";
/** Path to users libs. */
private String yarnQueue = DEFAULT_IGNITE_YARN_QUEUE;
/** */
public ClusterProperties() {
// No-op.
}
/**
* @return Cluster name.
*/
public String clusterName() {
return clusterName;
}
/**
* @return CPU count limit.
*/
public double cpusPerNode() {
return cpuPerNode;
}
/**
* Sets CPU count limit.
*
* @param cpu CPU per node count limit.
*/
public void cpusPerNode(double cpu) {
this.cpuPerNode = cpu;
}
/**
* @return mem limit.
*/
public double memoryPerNode() {
return memPerNode;
}
/**
* Sets mem limit.
*
* @param mem Memory.
*/
public void memoryPerNode(double mem) {
this.memPerNode = mem;
}
/**
* @return Memory overhead for requested memory.
*/
public double memoryOverHeadPerNode() {
return memOverHeadPerNode;
}
/**
* Sets memory overhead requested to YARN.
*
* @param memOverHeadPerNode Memory over head per node.
*/
public void memoryOverHeadPerNode(double memOverHeadPerNode) {
this.memOverHeadPerNode = memOverHeadPerNode;
}
/**
* @return Provide the total memory requested to ResourceManagers (memoryPerNode + memoryOverheadPerNode).
*/
public double totalMemoryPerNode() {
return memoryPerNode() + memoryOverHeadPerNode();
}
/**
* @return Instance count limit.
*/
public double instances() {
return nodeCnt;
}
/**
* Sets instance count limit.
*
* @param nodeCnt Node instance count limit.
*/
public void instances(int nodeCnt) {
this.nodeCnt = nodeCnt;
}
/**
* Sets hostname constraint.
*
* @param pattern Hostname pattern.
*/
public void hostnameConstraint(Pattern pattern) {
this.hostnameConstraint = pattern;
}
/**
* Sets Yarn Queue
*
* @param queue queue name.
*/
public void yarnQueue(String queue) {
this.yarnQueue = queue;
}
/**
* @return Ignite version.
*/
public String igniteUrl() {
return igniteUrl;
}
/**
* @return Working directory.
*/
public String igniteWorkDir() {
return igniteWorkDir;
}
/**
* @return Local working directory.
*/
public String igniteLocalWorkDir() {
return igniteLocalWorkDir;
}
/**
* @return Ignite releases dir.
*/
public String igniteReleasesDir() {
return igniteReleasesDir;
}
/**
* @return User's libs.
*/
public String userLibs() {
return userLibs;
}
/**
* @return Ignite configuration.
*/
public String igniteCfg() {
return igniteCfg;
}
/**
* @return Licence path.
*/
public String licencePath() {
return licencePath;
}
/**
* @return Ignite hdfs path.
*/
public String ignitePath() {
return ignitePath;
}
/**
* @return Jvm opts.
*/
public String jvmOpts() {
return jvmOpts;
}
/**
* @return Host name constraint.
*/
public Pattern hostnameConstraint() {
return hostnameConstraint;
}
/**
* @return Yarn Queue
*/
public String yarnQueue() { return yarnQueue; }
/**
* Instantiate a ClusterProperties from a set of properties.
*
* @param props If {@code null} will be used system properties.
* @return Cluster properties.
*/
private static ClusterProperties fromProperties(Properties props) {
ClusterProperties prop = new ClusterProperties();
prop.clusterName = getStringProperty(IGNITE_CLUSTER_NAME, props, DEFAULT_CLUSTER_NAME);
prop.cpuPerNode = getDoubleProperty(IGNITE_RUN_CPU_PER_NODE, props, DEFAULT_CPU_PER_NODE);
prop.memPerNode = getDoubleProperty(IGNITE_MEMORY_PER_NODE, props, DEFAULT_MEM_PER_NODE);
// The minimum memory overhead: overhead is by default 0.1* MEMORY_PER_NODE,
// with a minimum of DEFAULT_MINIMUM_MEM_OVERHEAD_PER_NODE
prop.memOverHeadPerNode = getDoubleProperty(IGNITE_MEMORY_OVERHEAD_PER_NODE, props,
Math.max( 0.1 * prop.memPerNode, DEFAULT_MINIMUM_MEM_OVERHEAD_PER_NODE));
prop.nodeCnt = getDoubleProperty(IGNITE_NODE_COUNT, props, DEFAULT_IGNITE_NODE_COUNT);
prop.igniteUrl = getStringProperty(IGNITE_URL, props, null);
prop.ignitePath = getStringProperty(IGNITE_PATH, props, null);
prop.licencePath = getStringProperty(LICENCE_PATH, props, null);
prop.jvmOpts = getStringProperty(IGNITE_JVM_OPTS, props, null);
prop.igniteWorkDir = getStringProperty(IGNITE_WORKING_DIR, props, DEFAULT_IGNITE_WORK_DIR);
prop.igniteLocalWorkDir = getStringProperty(IGNITE_LOCAL_WORK_DIR, props, DEFAULT_IGNITE_LOCAL_WORK_DIR);
prop.igniteReleasesDir = getStringProperty(IGNITE_RELEASES_DIR, props, DEFAULT_IGNITE_RELEASES_DIR);
prop.igniteCfg = getStringProperty(IGNITE_CONFIG_XML, props, null);
prop.userLibs = getStringProperty(IGNITE_USERS_LIBS, props, null);
prop.yarnQueue = getStringProperty(IGNITE_YARN_QUEUE, props, DEFAULT_IGNITE_YARN_QUEUE);
String pattern = getStringProperty(IGNITE_HOSTNAME_CONSTRAINT, props, null);
if (pattern != null) {
try {
prop.hostnameConstraint = Pattern.compile(pattern);
}
catch (PatternSyntaxException e) {
log.log(Level.WARNING, "IGNITE_HOSTNAME_CONSTRAINT has invalid pattern. It will be ignore.", e);
}
}
return prop;
}
/**
* @param config Path to config file.
* @return Cluster configuration.
*/
public static ClusterProperties from(String config) {
try {
Properties props = null;
if (config != null) {
props = new Properties();
props.load(new FileInputStream(config));
}
return fromProperties(props);
}
catch (IOException e) {
throw new RuntimeException(e);
}
}
/**
* @return Cluster configuration.
*/
public static ClusterProperties from() {
return fromProperties(null);
}
/**
* Convert to properties to map.
*
* @return Key-value map.
*/
public Map<String, String> toEnvs() {
Map<String, String> envs = new HashMap<>();
envs.put(IGNITE_CLUSTER_NAME, toEnvVal(clusterName));
envs.put(IGNITE_RUN_CPU_PER_NODE, toEnvVal(cpuPerNode));
envs.put(IGNITE_MEMORY_PER_NODE, toEnvVal(memPerNode));
envs.put(IGNITE_MEMORY_OVERHEAD_PER_NODE, toEnvVal(memOverHeadPerNode));
envs.put(IGNITE_NODE_COUNT, toEnvVal(nodeCnt));
envs.put(IGNITE_URL, toEnvVal(igniteUrl));
envs.put(IGNITE_PATH, toEnvVal(ignitePath));
envs.put(LICENCE_PATH, toEnvVal(licencePath));
envs.put(IGNITE_JVM_OPTS, toEnvVal(jvmOpts));
envs.put(IGNITE_WORKING_DIR, toEnvVal(igniteWorkDir));
envs.put(IGNITE_LOCAL_WORK_DIR, toEnvVal(igniteLocalWorkDir));
envs.put(IGNITE_RELEASES_DIR, toEnvVal(igniteReleasesDir));
envs.put(IGNITE_CONFIG_XML, toEnvVal(igniteCfg));
envs.put(IGNITE_USERS_LIBS, toEnvVal(userLibs));
envs.put(IGNITE_YARN_QUEUE, toEnvVal(yarnQueue));
if (hostnameConstraint != null)
envs.put(IGNITE_HOSTNAME_CONSTRAINT, toEnvVal(hostnameConstraint.pattern()));
return envs;
}
/**
* @param name Property name.
* @param fileProps Property file.
* @return Property value.
*/
private static double getDoubleProperty(String name, Properties fileProps, Double defaultVal) {
if (fileProps != null && fileProps.containsKey(name))
return Double.valueOf(fileProps.getProperty(name));
String property = System.getProperty(name);
if (property == null)
property = System.getenv(name);
return property == null || property.isEmpty() ? defaultVal : Double.valueOf(property);
}
/**
* @param name Property name.
* @param fileProps Property file.
* @return Property value.
*/
private static String getStringProperty(String name, Properties fileProps, String defaultVal) {
if (fileProps != null && fileProps.containsKey(name))
return fileProps.getProperty(name);
String property = System.getProperty(name);
if (property == null)
property = System.getenv(name);
return property == null || property.isEmpty() ? defaultVal : property;
}
/**
* @param val Value.
* @return If val is null {@code EMPTY_STRING} else to string.
*/
private String toEnvVal(Object val) {
return val == null ? EMPTY_STRING : val.toString();
}
}