1 package org.apache.maven.shared.utils.cli.shell;
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.File;
24 import java.util.ArrayList;
25 import java.util.Arrays;
26 import java.util.List;
27 import org.apache.maven.shared.utils.StringUtils;
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42 public class Shell
43 implements Cloneable
44 {
45 private static final char[] DEFAULT_QUOTING_TRIGGER_CHARS = { ' ' };
46
47 private String shellCommand;
48
49 private final List<String> shellArgs = new ArrayList<String>();
50
51 private boolean quotedArgumentsEnabled = true;
52
53 private String executable;
54
55 private String workingDir;
56
57 private boolean quotedExecutableEnabled = true;
58
59 private boolean singleQuotedArgumentEscaped = false;
60
61 private boolean singleQuotedExecutableEscaped = false;
62
63 private char argQuoteDelimiter = '\"';
64
65 private char exeQuoteDelimiter = '\"';
66
67
68
69
70
71
72 void setShellCommand( String shellCommand )
73 {
74 this.shellCommand = shellCommand;
75 }
76
77
78
79
80
81
82 String getShellCommand()
83 {
84 return shellCommand;
85 }
86
87
88
89
90
91
92
93 void setShellArgs( String[] shellArgs )
94 {
95 this.shellArgs.clear();
96 this.shellArgs.addAll( Arrays.asList( shellArgs ) );
97 }
98
99
100
101
102
103
104 String[] getShellArgs()
105 {
106 if ( ( shellArgs == null ) || shellArgs.isEmpty() )
107 {
108 return null;
109 }
110 else
111 {
112 return shellArgs.toArray( new String[shellArgs.size()] );
113 }
114 }
115
116
117
118
119
120
121
122
123 List<String> getCommandLine( String executableParameter, String... argumentsParameter )
124 {
125 return getRawCommandLine( executableParameter, argumentsParameter );
126 }
127
128
129
130
131
132
133 List<String> getRawCommandLine( String executableParameter, String... argumentsParameter )
134 {
135 List<String> commandLine = new ArrayList<String>();
136 StringBuilder sb = new StringBuilder();
137
138 if ( executableParameter != null )
139 {
140 String preamble = getExecutionPreamble();
141 if ( preamble != null )
142 {
143 sb.append( preamble );
144 }
145
146 if ( isQuotedExecutableEnabled() )
147 {
148 char[] escapeChars =
149 getEscapeChars( isSingleQuotedExecutableEscaped(), isDoubleQuotedExecutableEscaped() );
150
151 sb.append( StringUtils.quoteAndEscape( getExecutable(), getExecutableQuoteDelimiter(), escapeChars,
152 getQuotingTriggerChars(), '\\', false ) );
153 }
154 else
155 {
156 sb.append( getExecutable() );
157 }
158 }
159 for ( String argument : argumentsParameter )
160 {
161 if ( sb.length() > 0 )
162 {
163 sb.append( ' ' );
164 }
165
166 if ( isQuotedArgumentsEnabled() )
167 {
168 char[] escapeChars = getEscapeChars( isSingleQuotedArgumentEscaped(), isDoubleQuotedArgumentEscaped() );
169
170 sb.append( StringUtils.quoteAndEscape( argument, getArgumentQuoteDelimiter(), escapeChars,
171 getQuotingTriggerChars(), '\\', false ) );
172 }
173 else
174 {
175 sb.append( argument );
176 }
177 }
178
179 commandLine.add( sb.toString() );
180
181 return commandLine;
182 }
183
184 char[] getQuotingTriggerChars()
185 {
186 return DEFAULT_QUOTING_TRIGGER_CHARS;
187 }
188
189 String getExecutionPreamble()
190 {
191 return null;
192 }
193
194 char[] getEscapeChars( boolean includeSingleQuote, boolean includeDoubleQuote )
195 {
196 StringBuilder buf = new StringBuilder( 2 );
197 if ( includeSingleQuote )
198 {
199 buf.append( '\'' );
200 }
201
202 if ( includeDoubleQuote )
203 {
204 buf.append( '\"' );
205 }
206
207 char[] result = new char[buf.length()];
208 buf.getChars( 0, buf.length(), result, 0 );
209
210 return result;
211 }
212
213
214
215
216 protected boolean isDoubleQuotedArgumentEscaped()
217 {
218 return false;
219 }
220
221
222
223
224 protected boolean isSingleQuotedArgumentEscaped()
225 {
226 return singleQuotedArgumentEscaped;
227 }
228
229 boolean isDoubleQuotedExecutableEscaped()
230 {
231 return false;
232 }
233
234 boolean isSingleQuotedExecutableEscaped()
235 {
236 return singleQuotedExecutableEscaped;
237 }
238
239
240
241
242 void setArgumentQuoteDelimiter( char argQuoteDelimiterParameter )
243 {
244 this.argQuoteDelimiter = argQuoteDelimiterParameter;
245 }
246
247 char getArgumentQuoteDelimiter()
248 {
249 return argQuoteDelimiter;
250 }
251
252
253
254
255 void setExecutableQuoteDelimiter( char exeQuoteDelimiterParameter )
256 {
257 this.exeQuoteDelimiter = exeQuoteDelimiterParameter;
258 }
259
260 char getExecutableQuoteDelimiter()
261 {
262 return exeQuoteDelimiter;
263 }
264
265
266
267
268
269
270
271
272
273 public List<String> getShellCommandLine( String... arguments )
274 {
275
276 List<String> commandLine = new ArrayList<String>();
277
278 if ( getShellCommand() != null )
279 {
280 commandLine.add( getShellCommand() );
281 }
282
283 if ( getShellArgs() != null )
284 {
285 commandLine.addAll( getShellArgsList() );
286 }
287
288 commandLine.addAll( getCommandLine( getExecutable(), arguments ) );
289
290 return commandLine;
291
292 }
293
294 List<String> getShellArgsList()
295 {
296 return shellArgs;
297 }
298
299
300
301
302 public void setQuotedArgumentsEnabled( boolean quotedArgumentsEnabled )
303 {
304 this.quotedArgumentsEnabled = quotedArgumentsEnabled;
305 }
306
307 boolean isQuotedArgumentsEnabled()
308 {
309 return quotedArgumentsEnabled;
310 }
311
312 void setQuotedExecutableEnabled( boolean quotedExecutableEnabled )
313 {
314 this.quotedExecutableEnabled = quotedExecutableEnabled;
315 }
316
317 boolean isQuotedExecutableEnabled()
318 {
319 return quotedExecutableEnabled;
320 }
321
322
323
324
325
326 public void setExecutable( String executable )
327 {
328 if ( ( executable == null ) || ( executable.length() == 0 ) )
329 {
330 return;
331 }
332 this.executable = executable.replace( '/', File.separatorChar ).replace( '\\', File.separatorChar );
333 }
334
335
336
337
338 public String getExecutable()
339 {
340 return executable;
341 }
342
343
344
345
346
347 public void setWorkingDirectory( String path )
348 {
349 if ( path != null )
350 {
351 this.workingDir = path;
352 }
353 }
354
355
356
357
358
359 public void setWorkingDirectory( File workingDirectory )
360 {
361 if ( workingDirectory != null )
362 {
363 this.workingDir = workingDirectory.getAbsolutePath();
364 }
365 }
366
367
368
369
370 public File getWorkingDirectory()
371 {
372 return workingDir == null ? null : new File( workingDir );
373 }
374
375 String getWorkingDirectoryAsString()
376 {
377 return workingDir;
378 }
379
380
381 public Object clone()
382 {
383 throw new RuntimeException( "Do we ever clone this?" );
384
385
386
387
388
389 }
390
391 void setSingleQuotedArgumentEscaped( boolean singleQuotedArgumentEscaped )
392 {
393 this.singleQuotedArgumentEscaped = singleQuotedArgumentEscaped;
394 }
395
396 void setSingleQuotedExecutableEscaped( boolean singleQuotedExecutableEscaped )
397 {
398 this.singleQuotedExecutableEscaped = singleQuotedExecutableEscaped;
399 }
400
401 }