001package org.eclipse.aether.internal.impl;
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
022import static org.junit.Assert.*;
023
024import java.io.File;
025import java.io.IOException;
026import java.io.UnsupportedEncodingException;
027import java.util.List;
028
029import org.eclipse.aether.DefaultRepositorySystemSession;
030import org.eclipse.aether.RepositoryEvent;
031import org.eclipse.aether.RepositoryEvent.EventType;
032import org.eclipse.aether.artifact.Artifact;
033import org.eclipse.aether.artifact.DefaultArtifact;
034import org.eclipse.aether.installation.InstallRequest;
035import org.eclipse.aether.installation.InstallResult;
036import org.eclipse.aether.installation.InstallationException;
037import org.eclipse.aether.internal.impl.DefaultFileProcessor;
038import org.eclipse.aether.internal.impl.DefaultInstaller;
039import org.eclipse.aether.internal.test.util.TestFileProcessor;
040import org.eclipse.aether.internal.test.util.TestFileUtils;
041import org.eclipse.aether.internal.test.util.TestLocalRepositoryManager;
042import org.eclipse.aether.internal.test.util.TestUtils;
043import org.eclipse.aether.metadata.DefaultMetadata;
044import org.eclipse.aether.metadata.Metadata;
045import org.eclipse.aether.metadata.Metadata.Nature;
046import org.junit.After;
047import org.junit.Before;
048import org.junit.Test;
049
050public class DefaultInstallerTest
051{
052
053    private Artifact artifact;
054
055    private Metadata metadata;
056
057    private DefaultRepositorySystemSession session;
058
059    private String localArtifactPath;
060
061    private String localMetadataPath;
062
063    private DefaultInstaller installer;
064
065    private InstallRequest request;
066
067    private RecordingRepositoryListener listener;
068
069    private File localArtifactFile;
070
071    private TestLocalRepositoryManager lrm;
072
073    @Before
074    public void setup()
075        throws IOException
076    {
077        artifact = new DefaultArtifact( "gid", "aid", "jar", "ver" );
078        artifact = artifact.setFile( TestFileUtils.createTempFile( "artifact".getBytes(), 1 ) );
079        metadata =
080            new DefaultMetadata( "gid", "aid", "ver", "type", Nature.RELEASE_OR_SNAPSHOT,
081                                 TestFileUtils.createTempFile( "metadata".getBytes(), 1 ) );
082
083        session = TestUtils.newSession();
084        localArtifactPath = session.getLocalRepositoryManager().getPathForLocalArtifact( artifact );
085        localMetadataPath = session.getLocalRepositoryManager().getPathForLocalMetadata( metadata );
086
087        localArtifactFile = new File( session.getLocalRepository().getBasedir(), localArtifactPath );
088
089        installer = new DefaultInstaller();
090        installer.setFileProcessor( new TestFileProcessor() );
091        installer.setRepositoryEventDispatcher( new StubRepositoryEventDispatcher() );
092        installer.setSyncContextFactory( new StubSyncContextFactory() );
093        request = new InstallRequest();
094        listener = new RecordingRepositoryListener();
095        session.setRepositoryListener( listener );
096
097        lrm = (TestLocalRepositoryManager) session.getLocalRepositoryManager();
098
099        TestFileUtils.deleteFile( session.getLocalRepository().getBasedir() );
100    }
101
102    @After
103    public void teardown()
104        throws Exception
105    {
106        TestFileUtils.deleteFile( session.getLocalRepository().getBasedir() );
107    }
108
109    @Test
110    public void testSuccessfulInstall()
111        throws InstallationException, UnsupportedEncodingException, IOException
112    {
113        File artifactFile =
114            new File( session.getLocalRepositoryManager().getRepository().getBasedir(), localArtifactPath );
115        File metadataFile =
116            new File( session.getLocalRepositoryManager().getRepository().getBasedir(), localMetadataPath );
117
118        artifactFile.delete();
119        metadataFile.delete();
120
121        request.addArtifact( artifact );
122        request.addMetadata( metadata );
123
124        InstallResult result = installer.install( session, request );
125
126        assertTrue( artifactFile.exists() );
127        assertEquals( "artifact", TestFileUtils.readString( artifactFile ) );
128
129        assertTrue( metadataFile.exists() );
130        assertEquals( "metadata", TestFileUtils.readString( metadataFile ) );
131
132        assertEquals( result.getRequest(), request );
133
134        assertEquals( result.getArtifacts().size(), 1 );
135        assertTrue( result.getArtifacts().contains( artifact ) );
136
137        assertEquals( result.getMetadata().size(), 1 );
138        assertTrue( result.getMetadata().contains( metadata ) );
139
140        assertEquals( 1, lrm.getMetadataRegistration().size() );
141        assertTrue( lrm.getMetadataRegistration().contains( metadata ) );
142        assertEquals( 1, lrm.getArtifactRegistration().size() );
143        assertTrue( lrm.getArtifactRegistration().contains( artifact ) );
144    }
145
146    @Test( expected = InstallationException.class )
147    public void testNullArtifactFile()
148        throws InstallationException
149    {
150        InstallRequest request = new InstallRequest();
151        request.addArtifact( artifact.setFile( null ) );
152
153        installer.install( session, request );
154    }
155
156    @Test( expected = InstallationException.class )
157    public void testNullMetadataFile()
158        throws InstallationException
159    {
160        InstallRequest request = new InstallRequest();
161        request.addMetadata( metadata.setFile( null ) );
162
163        installer.install( session, request );
164    }
165
166    @Test( expected = InstallationException.class )
167    public void testNonExistentArtifactFile()
168        throws InstallationException
169    {
170        InstallRequest request = new InstallRequest();
171        request.addArtifact( artifact.setFile( new File( "missing.txt" ) ) );
172
173        installer.install( session, request );
174    }
175
176    @Test( expected = InstallationException.class )
177    public void testNonExistentMetadataFile()
178        throws InstallationException
179    {
180        InstallRequest request = new InstallRequest();
181        request.addMetadata( metadata.setFile( new File( "missing.xml" ) ) );
182
183        installer.install( session, request );
184    }
185
186    @Test( expected = InstallationException.class )
187    public void testArtifactExistsAsDir()
188        throws InstallationException
189    {
190        String path = session.getLocalRepositoryManager().getPathForLocalArtifact( artifact );
191        File file = new File( session.getLocalRepository().getBasedir(), path );
192        assertFalse( file.getAbsolutePath() + " is a file, not directory", file.isFile() );
193        assertFalse( file.getAbsolutePath() + " already exists", file.exists() );
194        assertTrue( "failed to setup test: could not create " + file.getAbsolutePath(),
195                    file.mkdirs() || file.isDirectory() );
196
197        request.addArtifact( artifact );
198        installer.install( session, request );
199    }
200
201    @Test( expected = InstallationException.class )
202    public void testMetadataExistsAsDir()
203        throws InstallationException
204    {
205        String path = session.getLocalRepositoryManager().getPathForLocalMetadata( metadata );
206        assertTrue( "failed to setup test: could not create " + path,
207                    new File( session.getLocalRepository().getBasedir(), path ).mkdirs() );
208
209        request.addMetadata( metadata );
210        installer.install( session, request );
211    }
212
213    @Test( expected = InstallationException.class )
214    public void testArtifactDestinationEqualsSource()
215        throws Exception
216    {
217        String path = session.getLocalRepositoryManager().getPathForLocalArtifact( artifact );
218        File file = new File( session.getLocalRepository().getBasedir(), path );
219        artifact = artifact.setFile( file );
220        TestFileUtils.writeString( file, "test" );
221
222        request.addArtifact( artifact );
223        installer.install( session, request );
224    }
225
226    @Test( expected = InstallationException.class )
227    public void testMetadataDestinationEqualsSource()
228        throws Exception
229    {
230        String path = session.getLocalRepositoryManager().getPathForLocalMetadata( metadata );
231        File file = new File( session.getLocalRepository().getBasedir(), path );
232        metadata = metadata.setFile( file );
233        TestFileUtils.writeString( file, "test" );
234
235        request.addMetadata( metadata );
236        installer.install( session, request );
237    }
238
239    @Test
240    public void testSuccessfulArtifactEvents()
241        throws InstallationException
242    {
243        InstallRequest request = new InstallRequest();
244        request.addArtifact( artifact );
245
246        installer.install( session, request );
247        checkEvents( "Repository Event problem", artifact, false );
248    }
249
250    @Test
251    public void testSuccessfulMetadataEvents()
252        throws InstallationException
253    {
254        InstallRequest request = new InstallRequest();
255        request.addMetadata( metadata );
256
257        installer.install( session, request );
258        checkEvents( "Repository Event problem", metadata, false );
259    }
260
261    @Test
262    public void testFailingEventsNullArtifactFile()
263    {
264        checkFailedEvents( "null artifact file", this.artifact.setFile( null ) );
265    }
266
267    @Test
268    public void testFailingEventsNullMetadataFile()
269    {
270        checkFailedEvents( "null metadata file", this.metadata.setFile( null ) );
271    }
272
273    @Test
274    public void testFailingEventsArtifactExistsAsDir()
275    {
276        String path = session.getLocalRepositoryManager().getPathForLocalArtifact( artifact );
277        assertTrue( "failed to setup test: could not create " + path,
278                    new File( session.getLocalRepository().getBasedir(), path ).mkdirs() );
279        checkFailedEvents( "target exists as dir", artifact );
280    }
281
282    @Test
283    public void testFailingEventsMetadataExistsAsDir()
284    {
285        String path = session.getLocalRepositoryManager().getPathForLocalMetadata( metadata );
286        assertTrue( "failed to setup test: could not create " + path,
287                    new File( session.getLocalRepository().getBasedir(), path ).mkdirs() );
288        checkFailedEvents( "target exists as dir", metadata );
289    }
290
291    private void checkFailedEvents( String msg, Metadata metadata )
292    {
293        InstallRequest request = new InstallRequest().addMetadata( metadata );
294        msg = "Repository events problem (case: " + msg + ")";
295
296        try
297        {
298            installer.install( session, request );
299            fail( "expected exception" );
300        }
301        catch ( InstallationException e )
302        {
303            checkEvents( msg, metadata, true );
304        }
305
306    }
307
308    private void checkEvents( String msg, Metadata metadata, boolean failed )
309    {
310        List<RepositoryEvent> events = listener.getEvents();
311        assertEquals( msg, 2, events.size() );
312        RepositoryEvent event = events.get( 0 );
313        assertEquals( msg, EventType.METADATA_INSTALLING, event.getType() );
314        assertEquals( msg, metadata, event.getMetadata() );
315        assertNull( msg, event.getException() );
316
317        event = events.get( 1 );
318        assertEquals( msg, EventType.METADATA_INSTALLED, event.getType() );
319        assertEquals( msg, metadata, event.getMetadata() );
320        if ( failed )
321        {
322            assertNotNull( msg, event.getException() );
323        }
324        else
325        {
326            assertNull( msg, event.getException() );
327        }
328    }
329
330    private void checkFailedEvents( String msg, Artifact artifact )
331    {
332        InstallRequest request = new InstallRequest().addArtifact( artifact );
333        msg = "Repository events problem (case: " + msg + ")";
334
335        try
336        {
337            installer.install( session, request );
338            fail( "expected exception" );
339        }
340        catch ( InstallationException e )
341        {
342            checkEvents( msg, artifact, true );
343        }
344    }
345
346    private void checkEvents( String msg, Artifact artifact, boolean failed )
347    {
348        List<RepositoryEvent> events = listener.getEvents();
349        assertEquals( msg, 2, events.size() );
350        RepositoryEvent event = events.get( 0 );
351        assertEquals( msg, EventType.ARTIFACT_INSTALLING, event.getType() );
352        assertEquals( msg, artifact, event.getArtifact() );
353        assertNull( msg, event.getException() );
354        
355        event = events.get( 1 );
356        assertEquals( msg, EventType.ARTIFACT_INSTALLED, event.getType() );
357        assertEquals( msg, artifact, event.getArtifact() );
358        if ( failed )
359        {
360            assertNotNull( msg + " > expected exception", event.getException() );
361        }
362        else
363        {
364            assertNull( msg + " > " + event.getException(), event.getException() );
365        }
366    }
367
368    @Test
369    public void testDoNotUpdateUnchangedArtifact()
370        throws InstallationException
371    {
372        request.addArtifact( artifact );
373        installer.install( session, request );
374
375        installer.setFileProcessor( new DefaultFileProcessor()
376        {
377            @Override
378            public long copy( File src, File target, ProgressListener listener )
379                throws IOException
380            {
381                throw new IOException( "copy called" );
382            }
383        } );
384
385        request = new InstallRequest();
386        request.addArtifact( artifact );
387        installer.install( session, request );
388    }
389
390    @Test
391    public void testSetArtifactTimestamps()
392        throws InstallationException
393    {
394        artifact.getFile().setLastModified( artifact.getFile().lastModified() - 60000 );
395
396        request.addArtifact( artifact );
397
398        installer.install( session, request );
399
400        assertEquals( "artifact timestamp was not set to src file", artifact.getFile().lastModified(),
401                      localArtifactFile.lastModified() );
402
403        request = new InstallRequest();
404
405        request.addArtifact( artifact );
406
407        artifact.getFile().setLastModified( artifact.getFile().lastModified() - 60000 );
408
409        installer.install( session, request );
410
411        assertEquals( "artifact timestamp was not set to src file", artifact.getFile().lastModified(),
412                      localArtifactFile.lastModified() );
413    }
414}