1 package org.apache.maven.scm.provider.clearcase.command.checkout;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 import java.io.File;
23 import java.io.FileWriter;
24 import java.io.IOException;
25 import java.net.InetAddress;
26 import java.net.UnknownHostException;
27
28 import org.apache.maven.scm.ScmException;
29 import org.apache.maven.scm.ScmFileSet;
30 import org.apache.maven.scm.ScmVersion;
31 import org.apache.maven.scm.command.checkout.AbstractCheckOutCommand;
32 import org.apache.maven.scm.command.checkout.CheckOutScmResult;
33 import org.apache.maven.scm.provider.ScmProviderRepository;
34 import org.apache.maven.scm.provider.clearcase.command.ClearCaseCommand;
35 import org.apache.maven.scm.provider.clearcase.repository.ClearCaseScmProviderRepository;
36 import org.apache.maven.scm.providers.clearcase.settings.Settings;
37 import org.codehaus.plexus.util.FileUtils;
38 import org.codehaus.plexus.util.StringUtils;
39 import org.codehaus.plexus.util.cli.CommandLineException;
40 import org.codehaus.plexus.util.cli.CommandLineUtils;
41 import org.codehaus.plexus.util.cli.Commandline;
42
43
44
45
46
47
48 public class ClearCaseCheckOutCommand
49 extends AbstractCheckOutCommand
50 implements ClearCaseCommand
51 {
52 private Settings settings = null;
53
54
55
56
57
58
59 protected CheckOutScmResult executeCheckOutCommand( ScmProviderRepository repository, ScmFileSet fileSet,
60 ScmVersion version, boolean recursive )
61 throws ScmException
62 {
63 if ( getLogger().isDebugEnabled() )
64 {
65 getLogger().debug( "executing checkout command..." );
66 }
67 ClearCaseScmProviderRepository repo = (ClearCaseScmProviderRepository) repository;
68 File workingDirectory = fileSet.getBasedir();
69
70 if ( version != null && getLogger().isDebugEnabled() )
71 {
72 getLogger().debug( version.getType() + ": " + version.getName() );
73 }
74
75 if ( getLogger().isDebugEnabled() )
76 {
77 getLogger().debug( "Running with CLEARCASE " + settings.getClearcaseType() );
78 }
79
80 ClearCaseCheckOutConsumer consumer = new ClearCaseCheckOutConsumer( getLogger() );
81
82 CommandLineUtils.StringStreamConsumer stderr = new CommandLineUtils.StringStreamConsumer();
83
84 int exitCode;
85
86 Commandline cl;
87 String projectDirectory = "";
88
89 try
90 {
91
92
93 FileUtils.deleteDirectory( workingDirectory );
94
95 String viewName = getUniqueViewName( repo, workingDirectory.getAbsolutePath() );
96 String streamIdentifier = getStreamIdentifier( repo.getStreamName(), repo.getVobName() );
97 cl = createCreateViewCommandLine( workingDirectory, viewName, streamIdentifier );
98 if ( getLogger().isInfoEnabled() )
99 {
100 getLogger().info( "Executing: " + cl.getWorkingDirectory().getAbsolutePath() + ">>" + cl.toString() );
101 }
102 exitCode =
103 CommandLineUtils.executeCommandLine( cl, new CommandLineUtils.StringStreamConsumer(), stderr );
104
105 if ( exitCode == 0 )
106 {
107 File configSpecLocation;
108
109 if ( !repo.isAutoConfigSpec() )
110 {
111 configSpecLocation = repo.getConfigSpec();
112 if ( version != null && StringUtils.isNotEmpty( version.getName() ) )
113 {
114
115
116
117
118
119
120
121
122 throw new UnsupportedOperationException(
123 "Building on a label not supported with user-specified config specs" );
124 }
125 }
126 else
127 {
128
129
130 String configSpec;
131 if ( !repo.hasElements() )
132 {
133 configSpec = createConfigSpec( repo.getLoadDirectory(), version );
134 }
135 else
136 {
137 configSpec = createConfigSpec( repo.getLoadDirectory(), repo.getElementName(), version );
138 }
139 if ( getLogger().isInfoEnabled() )
140 {
141 getLogger().info( "Created config spec for view '" + viewName + "':\n" + configSpec );
142 }
143 configSpecLocation = writeTemporaryConfigSpecFile( configSpec, viewName );
144
145
146
147
148
149 projectDirectory = repo.getLoadDirectory();
150
151 if ( projectDirectory.startsWith( "/" ) )
152 {
153 projectDirectory = projectDirectory.substring( 1 );
154 }
155 }
156
157 cl = createUpdateConfigSpecCommandLine( workingDirectory, configSpecLocation, viewName );
158
159 if ( getLogger().isInfoEnabled() )
160 {
161 getLogger().info( "Executing: " + cl.getWorkingDirectory().getAbsolutePath() + ">>" + cl.toString() );
162 }
163 exitCode = CommandLineUtils.executeCommandLine( cl, consumer, stderr );
164
165 }
166 }
167 catch ( CommandLineException ex )
168 {
169 throw new ScmException( "Error while executing clearcase command.", ex );
170 }
171 catch ( IOException ex )
172 {
173 throw new ScmException( "Error while deleting working directory.", ex );
174 }
175
176 if ( exitCode != 0 )
177 {
178 return new CheckOutScmResult( cl.toString(), "The cleartool command failed.", stderr.getOutput(), false );
179 }
180
181 return new CheckOutScmResult( cl.toString(), consumer.getCheckedOutFiles(), projectDirectory );
182 }
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197 protected File writeTemporaryConfigSpecFile( String configSpecContents, String viewName )
198 throws IOException
199 {
200 File configSpecLocation = File.createTempFile( "configspec-" + viewName, ".txt" );
201 FileWriter fw = new FileWriter( configSpecLocation );
202 try
203 {
204 fw.write( configSpecContents );
205 }
206 finally
207 {
208 try
209 {
210 fw.close();
211 }
212 catch ( IOException e )
213 {
214
215 }
216 }
217 configSpecLocation.deleteOnExit();
218 return configSpecLocation;
219 }
220
221
222
223
224
225
226
227
228
229
230 protected String createConfigSpec( String loadDirectory, ScmVersion version )
231 {
232
233 StringBuilder configSpec = new StringBuilder();
234 configSpec.append( "element * CHECKEDOUT\n" );
235 if ( version != null && StringUtils.isNotEmpty( version.getName() ) )
236 {
237 configSpec.append( "element * " + version.getName() + "\n" );
238 configSpec.append( "element -directory * /main/LATEST\n" );
239
240 }
241 else
242 {
243 configSpec.append( "element * /main/LATEST\n" );
244 }
245 configSpec.append( "load " + loadDirectory + "\n" );
246 return configSpec.toString();
247 }
248
249 protected String createConfigSpec( String loadDirectory, String elementName, ScmVersion version )
250 {
251
252 StringBuilder configSpec = new StringBuilder();
253 configSpec.append( "element * CHECKEDOUT\n" );
254 if ( version != null && StringUtils.isNotEmpty( version.getName() ) )
255 {
256 configSpec.append( "element * " + version.getName() + "\n" );
257 configSpec.append( "element * " + elementName + "\n" );
258 }
259 else
260 {
261 configSpec.append( "element * /main/LATEST\n" );
262 }
263 configSpec.append( "load " + loadDirectory + "\n" );
264 return configSpec.toString();
265 }
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291 protected Commandline createCreateViewCommandLine( File workingDirectory, String viewName, String streamIdentifier )
292 throws IOException
293 {
294 Commandline command = new Commandline();
295
296
297 command.setWorkingDirectory( workingDirectory.getParentFile().getAbsolutePath() );
298
299 command.setExecutable( "cleartool" );
300
301 command.createArg().setValue( "mkview" );
302 command.createArg().setValue( "-snapshot" );
303 command.createArg().setValue( "-tag" );
304 command.createArg().setValue( viewName );
305
306 if ( isClearCaseUCM() )
307 {
308 command.createArg().setValue( "-stream" );
309 command.createArg().setValue( streamIdentifier );
310 }
311
312 if ( !isClearCaseLT() )
313 {
314 if ( useVWS() )
315 {
316 command.createArg().setValue( "-vws" );
317 command.createArg().setValue( getViewStore() + viewName + ".vws" );
318 }
319 }
320
321 command.createArg().setValue( workingDirectory.getCanonicalPath() );
322
323 return command;
324 }
325
326
327
328
329
330
331
332 protected String getStreamIdentifier( String streamName, String vobName )
333 {
334 if ( streamName == null || vobName == null )
335 {
336 return null;
337 }
338 return "stream:" + streamName + "@" + vobName;
339 }
340
341 protected Commandline createUpdateConfigSpecCommandLine( File workingDirectory, File configSpecLocation,
342 String viewName )
343 {
344 Commandline command = new Commandline();
345
346 command.setWorkingDirectory( workingDirectory.getAbsolutePath() );
347
348 command.setExecutable( "cleartool" );
349
350 command.createArg().setValue( "setcs" );
351 command.createArg().setValue( "-tag" );
352 command.createArg().setValue( viewName );
353 command.createArg().setValue( configSpecLocation.getAbsolutePath() );
354
355 return command;
356
357 }
358
359 private String getUniqueViewName( ClearCaseScmProviderRepository repository, String absolutePath )
360 {
361 String uniqueId;
362 int lastIndexBack = absolutePath.lastIndexOf( '\\' );
363 int lastIndexForward = absolutePath.lastIndexOf( '/' );
364 if ( lastIndexBack != -1 )
365 {
366 uniqueId = absolutePath.substring( lastIndexBack + 1 );
367 }
368 else
369 {
370 uniqueId = absolutePath.substring( lastIndexForward + 1 );
371 }
372 return repository.getViewName( uniqueId );
373 }
374
375 protected String getViewStore()
376 {
377 String result = null;
378
379 if ( settings.getViewstore() != null )
380 {
381 result = settings.getViewstore();
382 }
383
384 if ( result == null )
385 {
386 result = "\\\\" + getHostName() + "\\viewstore\\";
387 }
388 else
389 {
390
391
392 if ( isClearCaseLT() )
393 {
394 result = result + getUserName() + "\\";
395 }
396 }
397 return result;
398 }
399
400 protected boolean isClearCaseLT()
401 {
402 return ClearCaseScmProviderRepository.CLEARCASE_LT.equals( settings.getClearcaseType() );
403 }
404
405 protected boolean isClearCaseUCM()
406 {
407 return ClearCaseScmProviderRepository.CLEARCASE_UCM.equals( settings.getClearcaseType() );
408 }
409
410
411
412
413 protected boolean useVWS()
414 {
415 return settings.isUseVWSParameter();
416 }
417
418 private String getHostName()
419 {
420 String hostname;
421 try
422 {
423 hostname = InetAddress.getLocalHost().getHostName();
424 }
425 catch ( UnknownHostException e )
426 {
427
428 throw new RuntimeException( e );
429 }
430 return hostname;
431 }
432
433 private String getUserName()
434 {
435 String username;
436 username = System.getProperty( "user.name" );
437 return username;
438 }
439
440 public void setSettings( Settings settings )
441 {
442 this.settings = settings;
443 }
444 }