1 package org.sentrysoftware.winrm;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23 import java.io.IOException;
24 import java.nio.charset.Charset;
25 import java.nio.charset.StandardCharsets;
26 import java.nio.file.Files;
27 import java.nio.file.Path;
28 import java.nio.file.Paths;
29 import java.nio.file.StandardCopyOption;
30 import java.nio.file.attribute.FileTime;
31 import java.util.Collections;
32 import java.util.HashMap;
33 import java.util.List;
34 import java.util.Map;
35 import java.util.Objects;
36 import java.util.concurrent.TimeoutException;
37 import java.util.regex.Matcher;
38 import java.util.regex.Pattern;
39
40 import org.sentrysoftware.winrm.exceptions.WindowsRemoteException;
41 import org.sentrysoftware.winrm.exceptions.WqlQuerySyntaxException;
42
43 public class WindowsRemoteProcessUtils {
44
45 private WindowsRemoteProcessUtils() { }
46
47 private static final String DEFAULT_CODESET = "1252";
48 private static final Charset DEFAULT_CHARSET = Charset.forName("windows-1252");
49
50
51
52
53
54
55
56
57
58 private static final Map<String, Charset> CODESET_MAP;
59 static {
60 final Map<String, Charset> map = new HashMap<>();
61 map.put("1250", Charset.forName("windows-1250"));
62 map.put("1251", Charset.forName("windows-1251"));
63 map.put("1252", DEFAULT_CHARSET);
64 map.put("1253", Charset.forName("windows-1253"));
65 map.put("1254", Charset.forName("windows-1254"));
66 map.put("1255", Charset.forName("windows-1255"));
67 map.put("1256", Charset.forName("windows-1256"));
68 map.put("1257", Charset.forName("windows-1257"));
69 map.put("1258", Charset.forName("windows-1258"));
70 map.put("874", Charset.forName("x-windows-874"));
71 map.put("932", Charset.forName("Shift_JIS"));
72 map.put("936", Charset.forName("GBK"));
73 map.put("949", Charset.forName("EUC-KR"));
74 map.put("950", Charset.forName("Big5"));
75 map.put("951", Charset.forName("Big5-HKSCS"));
76 map.put("28591", StandardCharsets.ISO_8859_1);
77 map.put("20127", StandardCharsets.US_ASCII);
78 map.put("65001", StandardCharsets.UTF_8);
79 map.put("1200", StandardCharsets.UTF_16LE);
80 map.put("1201", StandardCharsets.UTF_16BE);
81
82 CODESET_MAP = Collections.unmodifiableMap(map);
83 }
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101 public static Charset getWindowsEncodingCharset(
102 final WindowsRemoteExecutor windowsRemoteExecutor,
103 final long timeout) throws TimeoutException, WqlQuerySyntaxException, WindowsRemoteException {
104
105 if (windowsRemoteExecutor == null || timeout < 1) {
106 return DEFAULT_CHARSET;
107 }
108
109 final List<Map<String, Object>> result = windowsRemoteExecutor.executeWql(
110 "SELECT CodeSet FROM Win32_OperatingSystem",
111 timeout);
112
113 final String codeSet = result.stream()
114 .map(row -> (String) row.get("CodeSet"))
115 .filter(Objects::nonNull)
116 .findFirst()
117 .orElse(DEFAULT_CODESET);
118
119 return CODESET_MAP.getOrDefault(codeSet, DEFAULT_CHARSET);
120 }
121
122
123
124
125
126
127
128
129 public static String buildNewOutputFileName() {
130 return String.format("SEN_%s_%d_%d",
131 Utils.getComputerName(),
132 Utils.getCurrentTimeMillis(),
133 (long) (Math.random() * 1000000));
134 }
135
136
137
138
139
140
141
142
143
144
145
146
147
148 public static String copyLocalFilesToShare(
149 final String command,
150 final List<String> localFiles,
151 final String uncSharePath,
152 final String remotePath) throws IOException {
153
154 Utils.checkNonNull(command, "command");
155
156 if (localFiles == null || localFiles.isEmpty()) {
157 return command;
158 }
159
160 Utils.checkNonNull(uncSharePath, "uncSharePath");
161 Utils.checkNonNull(remotePath, "remotePath");
162
163 try {
164 return localFiles.stream()
165 .reduce(
166 command,
167 (cmd, localFile) -> {
168 try {
169 final Path localFilePath = Paths.get(localFile);
170 final Path remoteFilePath = copyToShare(localFilePath, uncSharePath, remotePath);
171
172 return caseInsensitiveReplace(cmd, localFile, remoteFilePath.toString());
173
174 } catch (final IOException e) {
175 throw new RuntimeException(e);
176 }
177 });
178 } catch (final Exception e) {
179 if (e.getCause() instanceof IOException) {
180 throw (IOException) e.getCause();
181 }
182 throw e;
183 }
184 }
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201 static Path copyToShare(
202 final Path localFilePath,
203 final String uncSharePath,
204 final String remotePath) throws IOException {
205
206 final Path targetUncPath = Paths.get(uncSharePath, localFilePath.getFileName().toString());
207 final Path targetRemotePath = Paths.get(remotePath, localFilePath.getFileName().toString());
208
209 if (Files.exists(targetUncPath)) {
210 final FileTime sourceFileTime = Files.getLastModifiedTime(localFilePath);
211 final FileTime targetFileTime = Files.getLastModifiedTime(targetUncPath);
212 if (sourceFileTime.compareTo(targetFileTime) <= 0) {
213
214 return targetRemotePath;
215 }
216 }
217
218
219 Files.copy(
220 localFilePath,
221 targetUncPath,
222 StandardCopyOption.COPY_ATTRIBUTES,
223 StandardCopyOption.REPLACE_EXISTING);
224
225
226 return targetRemotePath;
227 }
228
229
230
231
232
233
234
235
236
237
238
239
240
241 static String caseInsensitiveReplace(final String string, final String target, final String replacement) {
242 return string == null || target == null ? string :
243 Pattern.compile(target, Pattern.LITERAL | Pattern.CASE_INSENSITIVE)
244 .matcher(string)
245 .replaceAll(Matcher.quoteReplacement(replacement == null ? Utils.EMPTY : replacement));
246 }
247 }