001    package org.apache.maven.scm.provider.vss.commands.update;
002    
003    /*
004     * Licensed to the Apache Software Foundation (ASF) under one
005     * or more contributor license agreements.  See the NOTICE file
006     * distributed with this work for additional information
007     * regarding copyright ownership.  The ASF licenses this file
008     * to you under the Apache License, Version 2.0 (the
009     * "License"); you may not use this file except in compliance
010     * with the License.  You may obtain a copy of the License at
011     *
012     * http://www.apache.org/licenses/LICENSE-2.0
013     *
014     * Unless required by applicable law or agreed to in writing,
015     * software distributed under the License is distributed on an
016     * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
017     * KIND, either express or implied.  See the License for the
018     * specific language governing permissions and limitations
019     * under the License.
020     */
021    
022    
023    import org.apache.maven.scm.ScmException;
024    import org.apache.maven.scm.ScmFileSet;
025    import org.apache.maven.scm.ScmVersion;
026    import org.apache.maven.scm.command.changelog.ChangeLogCommand;
027    import org.apache.maven.scm.command.update.AbstractUpdateCommand;
028    import org.apache.maven.scm.command.update.UpdateScmResult;
029    import org.apache.maven.scm.provider.ScmProviderRepository;
030    import org.apache.maven.scm.provider.vss.commands.VssCommandLineUtils;
031    import org.apache.maven.scm.provider.vss.commands.VssConstants;
032    import org.apache.maven.scm.provider.vss.commands.changelog.VssHistoryCommand;
033    import org.apache.maven.scm.provider.vss.repository.VssScmProviderRepository;
034    import org.codehaus.plexus.util.cli.CommandLineUtils;
035    import org.codehaus.plexus.util.cli.Commandline;
036    
037    /**
038     * @author <a href="mailto:triek@thrx.de">Thorsten Riek</a>
039     * @version $Id: VssUpdateCommand.java 885129 2009-11-28 19:13:15Z olamy $
040     */
041    public class VssUpdateCommand
042        extends AbstractUpdateCommand
043    {
044        // TODO handle deleted files from VSS
045        /** {@inheritDoc} */
046        protected UpdateScmResult executeUpdateCommand( ScmProviderRepository repository, ScmFileSet fileSet,
047                                                        ScmVersion version )
048            throws ScmException
049        {
050            if ( getLogger().isDebugEnabled() )
051            {
052                getLogger().debug( "executing update command..." );
053            }
054    
055            VssScmProviderRepository repo = (VssScmProviderRepository) repository;
056    
057            Commandline cl = buildCmdLine( repo, fileSet, version );
058    
059            VssUpdateConsumer consumer = new VssUpdateConsumer( repo, getLogger() );
060    
061            // TODO handle deleted files from VSS
062            // TODO identify local files
063            CommandLineUtils.StringStreamConsumer stderr = new CommandLineUtils.StringStreamConsumer();
064    
065            int exitCode;
066    
067            if ( getLogger().isDebugEnabled() )
068            {
069                getLogger().debug( "Executing: " + cl.getWorkingDirectory().getAbsolutePath() + ">>" + cl.toString() );
070            }
071    
072            exitCode = VssCommandLineUtils.executeCommandline( cl, consumer, stderr, getLogger() );
073    
074            if ( exitCode != 0 )
075            {
076                String error = stderr.getOutput();
077    
078                if ( getLogger().isDebugEnabled() )
079                {
080                    getLogger().debug( "VSS returns error: [" + error + "] return code: [" + exitCode + "]" );
081                }
082                if ( error.indexOf( "A writable copy of" ) < 0 )
083                {
084                    return new UpdateScmResult( cl.toString(), "The vss command failed.", error, false );
085                }
086                // print out the writable copy for manual handling
087                if ( getLogger().isWarnEnabled() )
088                {
089                    getLogger().warn( error );
090                }
091            }
092    
093            return new UpdateScmResult( cl.toString(), consumer.getUpdatedFiles() );
094        }
095    
096        public Commandline buildCmdLine( VssScmProviderRepository repo, ScmFileSet fileSet, ScmVersion version )
097            throws ScmException
098        {
099    
100            Commandline command = new Commandline();
101    
102            command.setWorkingDirectory( fileSet.getBasedir().getAbsolutePath() );
103    
104            try
105            {
106                command.addSystemEnvironment();
107            }
108            catch ( Exception e )
109            {
110                throw new ScmException( "Can't add system environment.", e );
111            }
112    
113            command.addEnvironment( "SSDIR", repo.getVssdir() );
114    
115            String ssDir = VssCommandLineUtils.getSsDir();
116    
117            command.setExecutable( ssDir + VssConstants.SS_EXE );
118    
119            command.createArg().setValue( VssConstants.COMMAND_GET );
120    
121            command.createArg().setValue( VssConstants.PROJECT_PREFIX + repo.getProject() );
122    
123            //User identification to get access to vss repository
124            if ( repo.getUserPassword() != null )
125            {
126                command.createArg().setValue( VssConstants.FLAG_LOGIN + repo.getUserPassword() );
127            }
128    
129            //Display the history of an entire project list
130            command.createArg().setValue( VssConstants.FLAG_RECURSION );
131    
132            //Ignore: Do not ask for input under any circumstances.
133            command.createArg().setValue( VssConstants.FLAG_AUTORESPONSE_DEF );
134    
135            // FIXME Update command only works if there is no file checked out
136            // or no file is dirty locally. It's better than overwriting
137            // checked out files
138            //Ignore: Do not touch local writable files.
139            command.createArg().setValue( VssConstants.FLAG_SKIP_WRITABLE );
140    
141            if ( version != null )
142            {
143                command.createArg().setValue( VssConstants.FLAG_VERSION_LABEL + version );
144            }
145    
146            return command;
147        }
148    
149        /** {@inheritDoc} */
150        protected ChangeLogCommand getChangeLogCommand()
151        {
152            VssHistoryCommand command = new VssHistoryCommand();
153    
154            command.setLogger( getLogger() );
155    
156            return command;
157        }
158    
159    }