View Javadoc
1   /**
2    * Copyright 2010-2014 The Kuali Foundation
3    *
4    * Licensed under the Educational Community License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    * http://www.opensource.org/licenses/ecl2.php
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   * See the License for the specific language governing permissions and
14   * limitations under the License.
15   */
16  package org.kuali.common.util.secure;
17  
18  import java.io.File;
19  import java.util.ArrayList;
20  import java.util.Arrays;
21  import java.util.Collections;
22  import java.util.List;
23  import java.util.Properties;
24  
25  import org.apache.commons.io.FileUtils;
26  import org.apache.commons.lang3.StringUtils;
27  import org.kuali.common.util.LocationUtils;
28  import org.kuali.common.util.PropertyUtils;
29  import org.slf4j.Logger;
30  import org.slf4j.LoggerFactory;
31  import org.springframework.util.Assert;
32  
33  /**
34   * @deprecated
35   */
36  @Deprecated
37  public class SSHUtils {
38  
39  	private static final Logger logger = LoggerFactory.getLogger(SSHUtils.class);
40  
41  	private static final String FS = File.separator;
42  	private static final String IDENTITY_FILE = "IdentityFile";
43  	private static final String TILDE = "~";
44  	private static final String USER_HOME = FileUtils.getUserDirectoryPath();
45  	private static final String SSHDIR = USER_HOME + FS + ".ssh";
46  	private static final String IDENTITY = SSHDIR + FS + "identity";
47  	private static final String ID_DSA = SSHDIR + FS + "id_dsa";
48  	private static final String ID_RSA = SSHDIR + FS + "id_rsa";
49  	private static final String ID_ECDSA = SSHDIR + FS + "id_ecdsa";
50  	private static final int PORT_NUMBER_LOWEST = 1;
51  	private static final int PORT_NUMBER_HIGHEST = 65535;
52  
53  	public static final String STRICT_HOST_KEY_CHECKING = "StrictHostKeyChecking";
54  	public static final String NO = "no";
55  	public static final List<String> PRIVATE_KEY_DEFAULTS = Arrays.asList(IDENTITY, ID_DSA, ID_RSA, ID_ECDSA);
56  	public static final File DEFAULT_CONFIG_FILE = new File(SSHDIR + FS + "config");
57  	public static final int DEFAULT_PORT = 22;
58  	public static final File DEFAULT_KNOWN_HOSTS = new File(SSHDIR + FS + "known_hosts");
59  
60  	/**
61  	 * Return true if <code>port &gt;= 1</code> and <code>port &lt;= 65535</code>, false otherwise.
62  	 */
63  	public static final boolean isValidPort(int port) {
64  		return port >= PORT_NUMBER_LOWEST && port <= PORT_NUMBER_HIGHEST;
65  	}
66  
67  	public static final void addPort(List<String> args, String portOption, int port, int defaultPort) {
68  		if (port != defaultPort) {
69  			Assert.isTrue(SSHUtils.isValidPort(port));
70  			logger.debug("port={}", port);
71  			args.add(portOption);
72  			args.add(Integer.toString(port));
73  		}
74  	}
75  
76  	public static final void addOptions(List<String> args, Properties options) {
77  		if (options == null) {
78  			return;
79  		}
80  		List<String> keys = PropertyUtils.getSortedKeys(options);
81  		for (String key : keys) {
82  			String value = options.getProperty(key);
83  			logger.debug("Adding option [-o {}={}]", key, value);
84  			args.add("-o");
85  			args.add(key + "=" + value);
86  		}
87  	}
88  
89  	public static final void addConfigFile(List<String> args, File configFile, File defaultConfigFile) {
90  		if (configFile == null) {
91  			return;
92  		}
93  		String defaultPath = LocationUtils.getCanonicalPath(defaultConfigFile);
94  		String configFilePath = LocationUtils.getCanonicalPath(configFile);
95  		if (!StringUtils.equals(defaultPath, configFilePath)) {
96  			logger.debug("SSH config=[{}]", configFilePath);
97  			args.add("-F");
98  			args.add(configFilePath);
99  		}
100 	}
101 
102 	public static final void addIdentityFile(List<String> args, File identityFile) {
103 		if (identityFile != null) {
104 			String path = LocationUtils.getCanonicalPath(identityFile);
105 			logger.debug("Private key=[{}]", path);
106 			args.add("-i");
107 			args.add(path);
108 		}
109 	}
110 
111 	/**
112 	 * Return a non-null list containing any private keys found by examining default private key locations in <code>~/.ssh</code> and
113 	 * parsing <code>config</code>. Any files returned by this method are guaranteed to exist and be readable.
114 	 */
115 	public static final List<File> getPrivateKeys(File config) {
116 		List<String> paths = getFilenames(config);
117 		return getExistingAndReadable(paths);
118 	}
119 
120 	/**
121 	 * Return a non-null list containing any private keys found by examining default private key locations in <code>~/.ssh</code> and
122 	 * parsing <code>~/.ssh/config</code>. Any files returned by this method are guaranteed to exist and be readable.
123 	 */
124 	public static final List<File> getDefaultPrivateKeys() {
125 		return getPrivateKeys(DEFAULT_CONFIG_FILE);
126 	}
127 
128 	public static final Properties getDefaultOptions() {
129 		Properties options = new Properties();
130 		options.setProperty(STRICT_HOST_KEY_CHECKING, NO);
131 		return options;
132 	}
133 
134 	public static final List<File> getExistingAndReadable(List<String> filenames) {
135 		List<File> files = new ArrayList<File>();
136 		for (String filename : filenames) {
137 			File file = new File(filename);
138 			if (file.exists() && file.canRead()) {
139 				files.add(file);
140 			}
141 		}
142 		return files;
143 	}
144 
145 	public static final List<String> getFilenames(File config) {
146 		if (config.exists() && config.canRead()) {
147 			List<String> lines = LocationUtils.readLines(config);
148 			List<String> identityFileLines = getIdentityFileLines(lines);
149 			return getFilenames(identityFileLines);
150 		} else {
151 			return Collections.<String> emptyList();
152 		}
153 	}
154 
155 	public static final List<String> getIdentityFileLines(List<String> lines) {
156 		List<String> identityFileLines = new ArrayList<String>();
157 		for (String line : lines) {
158 			String trimmed = StringUtils.trim(line);
159 			if (StringUtils.startsWith(trimmed, IDENTITY_FILE)) {
160 				identityFileLines.add(trimmed);
161 			}
162 		}
163 		return identityFileLines;
164 	}
165 
166 	public static final List<String> getFilenames(List<String> identityFileLines) {
167 		List<String> filenames = new ArrayList<String>();
168 		for (String identityFileLine : identityFileLines) {
169 			String originalFilename = StringUtils.substring(identityFileLine, IDENTITY_FILE.length());
170 			String resolvedFilename = StringUtils.replace(originalFilename, TILDE, USER_HOME);
171 			String trimmed = StringUtils.trim(resolvedFilename);
172 			filenames.add(trimmed);
173 		}
174 		return filenames;
175 	}
176 }