blob: 3ba35f66a4fb519494e9e69fb6f91ec97f7fcc3e [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.netbeans.modules.maven.indexer;
import java.io.IOException;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.WeakHashMap;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.apache.lucene.document.Document;
import org.apache.lucene.document.Field.Index;
import org.apache.lucene.document.Field.Store;
import org.apache.lucene.index.Term;
import org.apache.lucene.search.BooleanClause;
import org.apache.lucene.search.BooleanQuery;
import org.apache.lucene.search.Query;
import org.apache.lucene.search.TermQuery;
import org.apache.maven.artifact.Artifact;
import org.apache.maven.artifact.InvalidArtifactRTException;
import org.apache.maven.artifact.repository.ArtifactRepository;
import org.apache.maven.index.ArtifactContext;
import org.apache.maven.index.ArtifactInfo;
import org.apache.maven.index.Field;
import org.apache.maven.index.IndexerField;
import org.apache.maven.index.IndexerFieldVersion;
import org.apache.maven.index.creator.AbstractIndexCreator;
import org.apache.maven.index.creator.MinimalArtifactInfoIndexCreator;
import org.apache.maven.model.Dependency;
import org.apache.maven.model.building.ModelBuildingRequest;
import org.apache.maven.project.MavenProject;
import org.apache.maven.project.ProjectBuildingException;
import org.apache.maven.project.ProjectBuildingRequest;
import org.apache.maven.project.ProjectBuildingResult;
import org.netbeans.modules.maven.embedder.EmbedderFactory;
import org.netbeans.modules.maven.embedder.MavenEmbedder;
import org.netbeans.modules.maven.indexer.api.RepositoryPreferences;
class ArtifactDependencyIndexCreator extends AbstractIndexCreator {
private static final Logger LOG = Logger.getLogger(ArtifactDependencyIndexCreator.class.getName());
private static final String NS = "urn:NbIndexCreator";
private static final String NB_DEPENDENCY_GROUP = "nbdg";
private static final String NB_DEPENDENCY_ARTIFACT = "nbda";
private static final String NB_DEPENDENCY_VERSION = "nbdv";
private static IndexerField FLD_NB_DEPENDENCY_GROUP = new IndexerField(new Field(null, NS, NB_DEPENDENCY_GROUP, "Dependency group"), IndexerFieldVersion.V3, NB_DEPENDENCY_GROUP, "Dependency group", Store.NO, Index.NOT_ANALYZED);
private static IndexerField FLD_NB_DEPENDENCY_ARTIFACT = new IndexerField(new Field(null, NS, NB_DEPENDENCY_ARTIFACT, "Dependency artifact"), IndexerFieldVersion.V3, NB_DEPENDENCY_ARTIFACT, "Dependency artifact", Store.NO, Index.NOT_ANALYZED);
private static IndexerField FLD_NB_DEPENDENCY_VERSION = new IndexerField(new Field(null, NS, NB_DEPENDENCY_VERSION, "Dependency version"), IndexerFieldVersion.V3, NB_DEPENDENCY_VERSION, "Dependency version", Store.NO, Index.NOT_ANALYZED);
private final List<ArtifactRepository> remoteRepos;
private final Map<ArtifactInfo, List<Dependency>> dependenciesByArtifact = new WeakHashMap<ArtifactInfo, List<Dependency>>();
private final MavenEmbedder embedder;
ArtifactDependencyIndexCreator() {
super(ArtifactDependencyIndexCreator.class.getName(), Arrays.asList(MinimalArtifactInfoIndexCreator.ID));
embedder = EmbedderFactory.getProjectEmbedder();
remoteRepos = RepositoryPreferences.getInstance().remoteRepositories(embedder);
}
@Override public void populateArtifactInfo(ArtifactContext context) throws IOException {
ArtifactInfo ai = context.getArtifactInfo();
if (ai.getClassifier() != null) {
return;
}
try {
MavenProject mp = load(ai);
if (mp != null) {
List<Dependency> dependencies = mp.getDependencies();
LOG.log(Level.FINER, "Successfully loaded project model from repository for {0} with {1} dependencies", new Object[] {ai, dependencies.size()});
dependenciesByArtifact.put(ai, dependencies);
}
} catch (InvalidArtifactRTException ex) {
ex.printStackTrace();
}
}
@Override public void updateDocument(ArtifactInfo ai, Document doc) {
List<Dependency> dependencies = dependenciesByArtifact.get(ai);
if (dependencies != null) {
for (Dependency d : dependencies) {
doc.add(FLD_NB_DEPENDENCY_GROUP.toField(d.getGroupId()));
doc.add(FLD_NB_DEPENDENCY_ARTIFACT.toField(d.getArtifactId()));
doc.add(FLD_NB_DEPENDENCY_VERSION.toField(d.getVersion()));
}
}
}
static Query query(String groupId, String artifactId, String version) {
final BooleanQuery q = new BooleanQuery();
q.add(new BooleanClause(new TermQuery(new Term(NB_DEPENDENCY_GROUP, groupId)), BooleanClause.Occur.MUST));
q.add(new BooleanClause(new TermQuery(new Term(NB_DEPENDENCY_ARTIFACT, artifactId)), BooleanClause.Occur.MUST));
q.add(new BooleanClause(new TermQuery(new Term(NB_DEPENDENCY_VERSION, version)), BooleanClause.Occur.MUST));
return q;
}
@Override public Collection<IndexerField> getIndexerFields() {
return Arrays.asList(FLD_NB_DEPENDENCY_GROUP, FLD_NB_DEPENDENCY_ARTIFACT, FLD_NB_DEPENDENCY_VERSION);
}
private MavenProject load(ArtifactInfo ai) {
try {
Artifact projectArtifact = embedder.createArtifact(ai.getGroupId(), ai.getArtifactId(), ai.getVersion(), ai.getPackaging() != null ? ai.getPackaging() : "jar");
ProjectBuildingRequest dpbr = embedder.createMavenExecutionRequest().getProjectBuildingRequest();
//mkleint: remote repositories don't matter we use project embedder.
dpbr.setRemoteRepositories(remoteRepos);
dpbr.setProcessPlugins(false);
dpbr.setValidationLevel(ModelBuildingRequest.VALIDATION_LEVEL_MINIMAL);
ProjectBuildingResult res = embedder.buildProject(projectArtifact, dpbr);
if (res.getProject() != null) {
return res.getProject();
} else {
LOG.log(Level.FINER, "No project model from repository for {0}: {1}", new Object[] {ai, res.getProblems()});
}
} catch (ProjectBuildingException ex) {
LOG.log(Level.FINER, "Failed to load project model from repository for {0}: {1}", new Object[] {ai, ex});
} catch (Exception exception) {
LOG.log(Level.FINER, "Failed to load project model from repository for " + ai, exception);
}
return null;
}
@Override public boolean updateArtifactInfo(Document doc, ArtifactInfo ai) {
return false;
}
}