jps: CompiledClass accepts multiple source files

This commit is contained in:
Dmitry Batkovich
2016-08-23 11:49:47 +03:00
parent b9a3e8be5a
commit fc8b03c7ab
7 changed files with 113 additions and 20 deletions
@@ -78,7 +78,7 @@ class ChunkBuildOutputConsumerImpl implements ModuleLevelBuilder.OutputConsumer
}
}
if (target != null) {
registerOutputFile(target, compiled.getOutputFile(), Collections.<String>singleton(compiled.getSourceFile().getPath()));
registerOutputFile(target, compiled.getOutputFile(), compiled.getSourceFilesPaths());
}
}
@@ -15,23 +15,30 @@
*/
package org.jetbrains.jps.incremental;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.util.UserDataHolderBase;
import com.intellij.openapi.util.io.FileUtil;
import com.intellij.util.Function;
import com.intellij.util.containers.ContainerUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.io.File;
import java.io.IOException;
import java.util.Collection;
import java.util.Collections;
/**
* @author Eugene Zhuravlev
* Date: 11/18/12
*/
public class CompiledClass extends UserDataHolderBase{
private final static Logger LOG = Logger.getInstance(CompiledClass.class);
@NotNull
private final File myOutputFile;
@NotNull
private final File mySourceFile;
private final Collection<File> mySourceFiles;
@Nullable
private final String myClassName;
@NotNull
@@ -39,11 +46,16 @@ public class CompiledClass extends UserDataHolderBase{
private boolean myIsDirty = false;
public CompiledClass(@NotNull File outputFile, @NotNull File sourceFile, @Nullable String className, @NotNull BinaryContent content) {
public CompiledClass(@NotNull File outputFile, @NotNull Collection<File> sourceFiles, @Nullable String className, @NotNull BinaryContent content) {
myOutputFile = outputFile;
mySourceFile = sourceFile;
mySourceFiles = sourceFiles;
myClassName = className;
myContent = content;
LOG.assertTrue(!mySourceFiles.isEmpty());
}
public CompiledClass(@NotNull File outputFile, @NotNull File sourceFile, @Nullable String className, @NotNull BinaryContent content) {
this(outputFile, Collections.singleton(sourceFile), className, content);
}
public void save() throws IOException {
@@ -56,9 +68,29 @@ public class CompiledClass extends UserDataHolderBase{
return myOutputFile;
}
@NotNull
public Collection<File> getSourceFiles() {
return mySourceFiles;
}
@NotNull
public Collection<String> getSourceFilesPaths() {
return ContainerUtil.map(mySourceFiles, new Function<File, String>() {
@Override
public String fun(File file) {
return file.getPath();
}
});
}
/**
* @deprecated use {@link CompiledClass#getSourceFiles()} or {{@link CompiledClass#getSourceFilesPaths()}
*/
@Deprecated
@NotNull
public File getSourceFile() {
return mySourceFile;
//noinspection ConstantConditions
return ContainerUtil.getFirstItem(getSourceFiles());
}
@Nullable
@@ -101,7 +133,7 @@ public class CompiledClass extends UserDataHolderBase{
public String toString() {
return "CompiledClass{" +
"myOutputFile=" + myOutputFile +
", mySourceFile=" + mySourceFile +
", mySourceFiles=" + mySourceFiles +
", myIsDirty=" + myIsDirty +
'}';
}
@@ -72,7 +72,7 @@ public abstract class BaseInstrumentingBuilder extends ClassProcessingBuilder {
LOG.info(e);
final String message = e.getMessage();
if (message != null) {
context.processMessage(new CompilerMessage(getPresentableName(), BuildMessage.Kind.ERROR, message, compiledClass.getSourceFile().getPath()));
context.processMessage(new CompilerMessage(getPresentableName(), message, compiledClass.getSourceFilesPaths(), BuildMessage.Kind.ERROR));
}
else {
context.processMessage(new CompilerMessage(getPresentableName(), e));
@@ -19,6 +19,8 @@ import com.intellij.compiler.instrumentation.FailSafeClassReader;
import com.intellij.compiler.instrumentation.InstrumentationClassFinder;
import com.intellij.compiler.notNullVerification.NotNullVerifyingInstrumenter;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.util.Function;
import com.intellij.util.containers.ContainerUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.jps.ModuleChunk;
@@ -34,6 +36,7 @@ import org.jetbrains.org.objectweb.asm.ClassWriter;
import org.jetbrains.org.objectweb.asm.Opcodes;
import java.io.File;
import java.util.Collection;
/**
* @author Eugene Zhuravlev
@@ -82,9 +85,17 @@ public class NotNullInstrumentingBuilder extends BaseInstrumentingBuilder{
}
catch (Throwable e) {
LOG.error(e);
final File sourceFile = compiledClass.getSourceFile();
String msg = "Cannot instrument " + sourceFile.getName() + ": " + e.getMessage();
context.processMessage(new CompilerMessage(getPresentableName(), BuildMessage.Kind.ERROR, msg, sourceFile.getPath()));
final Collection<File> sourceFiles = compiledClass.getSourceFiles();
String msg = "Cannot instrument " + ContainerUtil.map(sourceFiles, new Function<File, String>() {
@Override
public String fun(File file) {
return file.getName();
}
}) + ": " + e.getMessage();
context.processMessage(new CompilerMessage(getPresentableName(),
msg,
compiledClass.getSourceFilesPaths(),
BuildMessage.Kind.ERROR));
}
return null;
}
@@ -200,7 +200,7 @@ public class RmiStubsGenerator extends ClassProcessingBuilder {
}
final Collection<File> files = item.selectGeneratedFiles(children);
if (!files.isEmpty()) {
final Collection<String> sources = Collections.singleton(item.compiledClass.getSourceFile().getPath());
final Collection<String> sources = item.compiledClass.getSourceFilesPaths();
for (File generated : files) {
try {
outputConsumer.registerOutputFile(target, generated, sources);
@@ -16,12 +16,16 @@
package org.jetbrains.jps.incremental.messages;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.util.Function;
import com.intellij.util.containers.ContainerUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.PrintStream;
import java.util.Collection;
import java.util.Collections;
/**
* @author Eugene Zhuravlev
@@ -33,24 +37,28 @@ public class CompilerMessage extends BuildMessage {
private final long myProblemBeginOffset;
private final long myProblemEndOffset;
private final long myProblemLocationOffset;
private final String mySourcePath;
private final Collection<String> mySourcePaths;
private final long myLine;
private final long myColumn;
public CompilerMessage(@NotNull String compilerName, @NotNull Throwable internalError) {
this(compilerName, Kind.ERROR, getTextFromThrowable(internalError), null, -1L, -1L, -1L, -1L, -1L);
this(compilerName, Kind.ERROR, getTextFromThrowable(internalError));
}
public CompilerMessage(@NotNull String compilerName, Kind kind, String messageText) {
this(compilerName, kind, messageText, null, -1L, -1L, -1L, -1L, -1L);
this(compilerName, kind, messageText, (String)null, -1L, -1L, -1L, -1L, -1L);
}
public CompilerMessage(@NotNull String compilerName, String messageText, Collection<String> sourcePaths, Kind kind) {
this(compilerName, kind, messageText, sourcePaths, -1L, -1L, -1L, -1L, -1L);
}
public CompilerMessage(@NotNull String compilerName, Kind kind, String messageText, String sourcePath) {
this(compilerName, kind, messageText, sourcePath, -1L, -1L, -1L, -1L, -1L);
this(compilerName, messageText, Collections.singleton(sourcePath), kind);
}
public CompilerMessage(@NotNull String compilerName, Kind kind, String messageText,
@Nullable String sourcePath,
@NotNull Collection<String> sourcePaths,
long problemBeginOffset,
long problemEndOffset,
long problemLocationOffset,
@@ -61,11 +69,34 @@ public class CompilerMessage extends BuildMessage {
myProblemBeginOffset = problemBeginOffset;
myProblemEndOffset = problemEndOffset;
myProblemLocationOffset = problemLocationOffset;
mySourcePath = sourcePath != null && !sourcePath.isEmpty()? sourcePath.replace(File.separatorChar, '/') : null;
mySourcePaths = ContainerUtil.map(sourcePaths, new Function<String, String>() {
@Override
public String fun(String s) {
return s.replace(File.separatorChar, '/');
}
});
myLine = locationLine;
myColumn = locationColumn;
}
public CompilerMessage(@NotNull String compilerName, Kind kind, String messageText,
@Nullable String sourcePath,
long problemBeginOffset,
long problemEndOffset,
long problemLocationOffset,
long locationLine,
long locationColumn) {
this(compilerName,
kind,
messageText,
sourcePath == null ? Collections.<String>emptyList() : Collections.singleton(sourcePath),
problemBeginOffset,
problemEndOffset,
problemLocationOffset,
locationLine,
locationColumn);
}
@NotNull
public String getCompilerName() {
return myCompilerName;
@@ -73,7 +104,14 @@ public class CompilerMessage extends BuildMessage {
@Nullable
public String getSourcePath() {
return mySourcePath;
if (mySourcePaths.isEmpty()) {
return null;
}
else if (mySourcePaths.size() == 1) {
return ContainerUtil.getFirstItem(mySourcePaths);
} else {
return mySourcePaths.toString();
}
}
public long getLine() {
@@ -99,7 +137,16 @@ public class CompilerMessage extends BuildMessage {
public String toString() {
final StringBuilder builder = new StringBuilder();
builder.append(getCompilerName()).append(":").append(getKind().name()).append(":").append(super.toString());
final String path = getSourcePath();
String result;
if (mySourcePaths.isEmpty()) {
result = null;
}
else if (mySourcePaths.size() == 1) {
result = ContainerUtil.getFirstItem(mySourcePaths);
} else {
result = mySourcePaths.toString();
}
final String path = result;
if (path != null) {
builder.append("; file: ").append(path);
final long line = getLine();
@@ -197,7 +197,10 @@ public class FormsInstrumenter extends FormsBuilder {
}
class2form.put(classToBind, formFile);
addBinding(compiled.getSourceFile(), formFile, instrumented);
for (File file : compiled.getSourceFiles()) {
addBinding(file, formFile, instrumented);
}
try {
context.processMessage(new ProgressMessage("Instrumenting forms... [" + chunk.getPresentableShortName() + "]"));