DatastoreMetadataRebuilder extends AbstractMetadataRebuilder { @Transactional @Override public boolean rebuild( final Repository repository, final boolean update, final boolean rebuildChecksums, @Nullable final String groupId, @Nullable final String artifactId, @Nullable final String baseVersion) { checkNotNull(repository); return rebuildInTransaction(repository, update, rebuildChecksums, groupId, artifactId, baseVersion); } @Inject  DatastoreMetadataRebuilder(
      @Named("${nexus.maven.metadata.rebuild.bufferSize:-1000}") final int bufferSize,
      @Named("${nexus.maven.metadata.rebuild.timeoutSeconds:-60}") final int timeoutSeconds); @Transactional @Override boolean rebuild(
      final Repository repository,
      final boolean update,
      final boolean rebuildChecksums,
      @Nullable final String groupId,
      @Nullable final String artifactId,
      @Nullable final String baseVersion); @Override boolean rebuildInTransaction(
      final Repository repository,
      final boolean update,
      final boolean rebuildChecksums,
      @Nullable final String groupId,
      @Nullable final String artifactId,
      @Nullable final String baseVersion); @Override boolean exists(final Repository repository, final MavenPath mavenPath); @Override void deleteMetadata(final Repository repository, final List<String[]> gavs);  }
@Test public void rebuildIsCancelable() throws Exception { Component component = mock(Component.class); Asset asset = mock(Asset.class); doReturn(infiniteContinuation(component)).when(components).browse(anyInt(), anyString()); doReturn(infiniteContinuation(asset)).when(assets).browse(anyInt(), anyString()); final AtomicBoolean canceled = new AtomicBoolean(false); final List<Throwable> uncaught = new ArrayList<>(); Thread taskThread = new Thread(() -> { CancelableHelper.set(canceled); new DatastoreMetadataRebuilder(10, 20).rebuild(repository, true, false, "group", "artifact", "version"); }); taskThread.setUncaughtExceptionHandler((t, e) -> { if (e instanceof TaskInterruptedException) { return; } uncaught.add(e); }); taskThread.start(); sleep((long) (Math.random() * 1000)); canceled.set(true); taskThread.join(5000); if (taskThread.isAlive()) { fail("Task did not cancel"); } if (uncaught.size() > 0) { throw new MultipleFailureException(uncaught); } }
@Test public void rebuildDoesntFailOnException() throws Exception { final String group1 = "group1"; final String artifact1 = "artifact1"; final String version1 = "1.0-SNAPSHOT"; final String path1_noSlash = "group1/artifact1/1.0-SNAPSHOT/artifact1-1.0-SNAPSHOT.jar"; final String path1 = "/" + path1_noSlash; final String group2 = "group2"; final String artifact2 = "artifact2"; final String version2 = "2.0-SNAPSHOT"; final String path2_noSlash = "/group1/artifact1/2.0-SNAPSHOT/artifact1-2.0-SNAPSHOT.jar"; final String path2 = "/" + path2_noSlash; when(components.namespaces()).thenReturn(Arrays.asList(group1, group2)); when(components.names(group1)).thenReturn(Collections.singletonList(artifact1)); when(components.names(group2)).thenReturn(Collections.singletonList(artifact2)); when(components.versions(group1, artifact1)).thenReturn(Collections.singletonList(version1)); when(components.versions(group2, artifact2)).thenReturn(Collections.singletonList(version2)); NestedAttributesMap attributesMap1 = new NestedAttributesMap(P_ATTRIBUTES, ImmutableMap.of(P_PACKAGING, "jar", P_BASE_VERSION, version1)); FluentComponentBuilder componentBuilder1 = mock(FluentComponentBuilder.class); when(components.name(artifact1)).thenReturn(componentBuilder1); when(componentBuilder1.namespace(group1)).thenReturn(componentBuilder1); when(componentBuilder1.version(version1)).thenReturn(componentBuilder1); FluentComponent component1 = mock(FluentComponent.class); when(component1.attributes(Maven2Format.NAME)).thenReturn(attributesMap1); when(componentBuilder1.find()).thenReturn(Optional.of(component1)); FluentAsset asset1 = mock(FluentAsset.class); when(asset1.path()).thenReturn(path1); when(asset1.blob()).thenReturn(Optional.of(mock(AssetBlob.class))); when(component1.assets()).thenReturn(Collections.singletonList(asset1)); when(asset1.component()).thenReturn(Optional.of(component1)); AssetBlob assetBlob1 = mock(AssetBlob.class); when(assetBlob1.checksums()).thenReturn(Collections.emptyMap()); when(asset1.blob()).thenReturn(Optional.of(assetBlob1)); NestedAttributesMap attributesMap2 = new NestedAttributesMap(P_ATTRIBUTES, ImmutableMap.of(P_PACKAGING, "jar", P_BASE_VERSION, version2)); FluentComponentBuilder componentBuilder2 = mock(FluentComponentBuilder.class); when(components.name(artifact2)).thenReturn(componentBuilder2); when(componentBuilder2.namespace(group2)).thenReturn(componentBuilder2); when(componentBuilder2.version(version2)).thenReturn(componentBuilder2); FluentComponent component2 = mock(FluentComponent.class); when(component2.attributes(Maven2Format.NAME)).thenReturn(attributesMap2); when(componentBuilder2.find()).thenReturn(Optional.of(component2)); FluentAsset asset2 = mock(FluentAsset.class); when(asset2.path()).thenReturn(path2); when(asset2.blob()).thenReturn(Optional.of(mock(AssetBlob.class))); when(component2.assets()).thenReturn(Collections.singletonList(asset2)); when(asset2.component()).thenReturn(Optional.of(component2)); AssetBlob assetBlob2 = mock(AssetBlob.class); when(assetBlob2.checksums()).thenReturn(Collections.emptyMap()); when(asset2.blob()).thenReturn(Optional.of(assetBlob2)); MavenPath mavenPath1 = mock(MavenPath.class); when(mavenPath1.getPath()).thenReturn(path1_noSlash); when(mavenPath1.hash(Matchers.any())).thenCallRealMethod(); MavenPath mavenPath2 = mock(MavenPath.class); when(mavenPath2.getPath()).thenReturn(path2_noSlash); when(mavenPath2.hash(Matchers.any())).thenCallRealMethod(); FluentAssetBuilder assetBuilder1 = mock(FluentAssetBuilder.class); when(assetBuilder1.find()).thenReturn(Optional.of(asset1)); when(assets.path(path1)).thenReturn(assetBuilder1); when(mavenPathParser.parsePath(path1)).thenReturn(mavenPath1); FluentAssetBuilder assetBuilder2 = mock(FluentAssetBuilder.class); when(assetBuilder2.find()).thenReturn(Optional.of(asset2)); when(assets.path(path2)).thenReturn(assetBuilder2); when(mavenPathParser.parsePath(path2)).thenReturn(mavenPath2); Content content = mock(Content.class); when(mavenContentFacet.get(Matchers.any(MavenPath.class))).thenReturn(Optional.of(content)); when(content.openInputStream()).thenThrow(new IOException()).thenReturn(mock(InputStream.class)); new DatastoreMetadataRebuilder(10, 20).rebuild(repository, true, true, null, null, null); verify(content, times(2)).openInputStream(); ArgumentCaptor<LoggingEvent> logCaptor = ArgumentCaptor.forClass(LoggingEvent.class); verify(mockAppender, atLeastOnce()).doAppend(logCaptor.capture()); List<LoggingEvent> allValues = logCaptor.getAllValues(); assertThat(allValues.stream() .filter(e -> e.getLevel() == Level.WARN) .filter(e -> e.getMessage().equals("Errors encountered during metadata rebuild:")) .count(), is(1L)); }