From 30b3b0c1e785f2d5abd0517e04a7c6f6746cc6e8 Mon Sep 17 00:00:00 2001 From: Moritz Eysholdt Date: Thu, 6 Aug 2015 10:29:15 +0200 Subject: [PATCH] [473612] [serializer] don't loose causing exception Signed-off-by: Moritz Eysholdt --- .../junit4/serializer/SerializerTester.java | 4 +- .../diagnostic/ISerializationDiagnostic.java | 62 +++++++++++++++---- .../diagnostic/SerializationDiagnostic.java | 28 +++++++-- .../diagnostic/TokenDiagnosticProvider.java | 18 +++++- 4 files changed, 93 insertions(+), 19 deletions(-) diff --git a/plugins/org.eclipse.xtext.junit4/src/org/eclipse/xtext/junit4/serializer/SerializerTester.java b/plugins/org.eclipse.xtext.junit4/src/org/eclipse/xtext/junit4/serializer/SerializerTester.java index 5ef538d29..3d7bbcb25 100644 --- a/plugins/org.eclipse.xtext.junit4/src/org/eclipse/xtext/junit4/serializer/SerializerTester.java +++ b/plugins/org.eclipse.xtext.junit4/src/org/eclipse/xtext/junit4/serializer/SerializerTester.java @@ -36,6 +36,7 @@ import org.eclipse.xtext.util.EmfFormatter; import org.eclipse.xtext.util.ITextRegion; import org.eclipse.xtext.util.Pair; import org.eclipse.xtext.util.Tuples; +import org.eclipse.xtext.xbase.lib.Exceptions; import org.junit.Assert; import com.google.common.base.Joiner; @@ -222,7 +223,8 @@ public class SerializerTester { System.out.println("Serializer debug output:"); System.out.println(debug.toString()); } - throw new RuntimeException(t); + Exceptions.sneakyThrow(t); + return ""; } } diff --git a/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/ISerializationDiagnostic.java b/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/ISerializationDiagnostic.java index c3ef13467..c2d5fef58 100644 --- a/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/ISerializationDiagnostic.java +++ b/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/ISerializationDiagnostic.java @@ -7,17 +7,25 @@ *******************************************************************************/ package org.eclipse.xtext.serializer.diagnostic; +import java.util.List; + +import org.eclipse.emf.ecore.EClass; import org.eclipse.emf.ecore.EObject; +import org.eclipse.emf.ecore.EStructuralFeature; import org.eclipse.xtext.serializer.analysis.Context2NameFunction; import org.eclipse.xtext.util.EmfFormatter; +import com.google.common.base.Joiner; +import com.google.common.base.Strings; +import com.google.common.collect.Lists; + /** * @author Moritz Eysholdt - Initial contribution and API */ public interface ISerializationDiagnostic { String EXCEPTION_DIAGNOSTIC = "exception diagnostic"; - + public interface Acceptor { void accept(ISerializationDiagnostic diagnostic); } @@ -59,22 +67,52 @@ public interface ISerializationDiagnostic { public String getId() { return EXCEPTION_DIAGNOSTIC; } + + @Override + public EStructuralFeature getEStructuralFeature() { + return null; + } + } + + public class ToString { + public String toString(ISerializationDiagnostic diagnostic) { + List result = Lists.newArrayList(); + String msg = diagnostic.getMessage(); + EObject eObject = diagnostic.getSemanticObject(); + Throwable exception = diagnostic.getException(); + if (!Strings.isNullOrEmpty(msg)) + result.add(msg); + if (exception != null && exception.getMessage() != null && !exception.getMessage().equals(msg)) + result.add("Caused By: " + exception.getClass().getName() + ": " + exception.getMessage()); + if (eObject != null) { + result.add("Semantic Object: " + EmfFormatter.objPath(eObject)); + if (eObject.eResource() != null && eObject.eResource().getURI() != null) + result.add("URI: " + eObject.eResource().getURI()); + } + if (diagnostic.getContext() != null) + result.add("Context: " + new Context2NameFunction().getContextName(diagnostic.getContext())); + if (diagnostic.getEStructuralFeature() != null) { + EStructuralFeature feature = diagnostic.getEStructuralFeature(); + EClass eClass = feature.getEContainingClass(); + String nsPrefix = eClass.getEPackage().getNsPrefix(); + result.add("EStructuralFeature: " + nsPrefix + "::" + eClass.getName() + "." + feature.getName()); + } + return Joiner.on("\n").join(result); + } } public class ExceptionThrowingAcceptor implements Acceptor { @Override public void accept(ISerializationDiagnostic diagnostic) { - if (diagnostic == null || diagnostic.getMessage() == null) + if (diagnostic == null) throw new RuntimeException("Something went wrong during serialization"); - else if (diagnostic.getException() != null) - throw new RuntimeException(diagnostic.getException()); else { - String msg = diagnostic.getMessage(); - if (diagnostic.getSemanticObject() != null) - msg += "\nSemantic Object: " + EmfFormatter.objPath(diagnostic.getSemanticObject()); - if (diagnostic.getContext() != null) - msg += "\nContext: " + new Context2NameFunction().getContextName(diagnostic.getContext()); - throw new RuntimeException(msg); + String msg = new ToString().toString(diagnostic); + Throwable exception = diagnostic.getException(); + if (exception != null) + throw new RuntimeException(msg, exception); + else + throw new RuntimeException(msg); } } } @@ -102,6 +140,8 @@ public interface ISerializationDiagnostic { EObject getSemanticObject(); EObject getContext(); - + String getId(); + + EStructuralFeature getEStructuralFeature(); } diff --git a/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/SerializationDiagnostic.java b/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/SerializationDiagnostic.java index d61a4d15a..880944d70 100644 --- a/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/SerializationDiagnostic.java +++ b/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/SerializationDiagnostic.java @@ -7,10 +7,11 @@ *******************************************************************************/ package org.eclipse.xtext.serializer.diagnostic; +import static org.eclipse.xtext.serializer.impl.FeatureFinderUtil.*; + import org.eclipse.emf.ecore.EObject; import org.eclipse.emf.ecore.EStructuralFeature; import org.eclipse.xtext.AbstractElement; -import org.eclipse.xtext.serializer.impl.FeatureFinderUtil; /** * @author Moritz Eysholdt - Initial contribution and API @@ -26,10 +27,15 @@ public class SerializationDiagnostic implements ISerializationDiagnostic { protected EObject context; private String id; + + private Throwable throwable; + + public SerializationDiagnostic(String id, EObject semantic, AbstractElement element, String msg, Throwable exc) { + this(id, semantic, semantic != null ? getFeature(element, semantic.eClass()) : null, msg, exc); + } public SerializationDiagnostic(String id, EObject semanticObject, AbstractElement element, String message) { - this(id, semanticObject, semanticObject != null ? FeatureFinderUtil.getFeature(element, semanticObject.eClass()) - : null, message); + this(id, semanticObject, semanticObject != null ? getFeature(element, semanticObject.eClass()) : null, message); } public SerializationDiagnostic(String id, EObject semanticObject, EStructuralFeature feature, String message) { @@ -39,6 +45,15 @@ public class SerializationDiagnostic implements ISerializationDiagnostic { this.message = message; this.feature = feature; } + + public SerializationDiagnostic(String id, EObject semanticObject, EStructuralFeature feature, String message, Throwable throwable) { + super(); + this.id = id; + this.semanticObject = semanticObject; + this.throwable = throwable; + this.feature = feature; + this.message = message; + } public SerializationDiagnostic(String id, EObject semanticObject, EObject context, String message) { super(); @@ -59,7 +74,7 @@ public class SerializationDiagnostic implements ISerializationDiagnostic { @Override public Throwable getException() { - return null; + return throwable; } @Override @@ -81,4 +96,9 @@ public class SerializationDiagnostic implements ISerializationDiagnostic { public String getId() { return id; } + + @Override + public EStructuralFeature getEStructuralFeature() { + return feature; + } } diff --git a/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/TokenDiagnosticProvider.java b/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/TokenDiagnosticProvider.java index aac684223..cb94c91c1 100644 --- a/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/TokenDiagnosticProvider.java +++ b/plugins/org.eclipse.xtext/src/org/eclipse/xtext/serializer/diagnostic/TokenDiagnosticProvider.java @@ -16,17 +16,22 @@ import org.eclipse.xtext.CrossReference; import org.eclipse.xtext.EnumLiteralDeclaration; import org.eclipse.xtext.GrammarUtil; import org.eclipse.xtext.RuleCall; +import org.eclipse.xtext.linking.impl.LinkingHelper; import org.eclipse.xtext.scoping.IScope; import org.eclipse.xtext.util.EmfFormatter; import com.google.common.base.Joiner; import com.google.common.collect.Lists; +import com.google.inject.Inject; /** * @author Moritz Eysholdt - Initial contribution and API */ public class TokenDiagnosticProvider implements ITokenDiagnosticProvider { + @Inject + private LinkingHelper linkingHelper; + protected String getFullReferenceName(EObject semanticObject, CrossReference reference) { EReference ref = GrammarUtil.getReference(reference); String clazz = semanticObject.eClass().getName(); @@ -68,9 +73,16 @@ public class TokenDiagnosticProvider implements ITokenDiagnosticProvider { } @Override - public ISerializationDiagnostic getValueConversionExceptionDiagnostic(EObject semanticObject, - AbstractElement element, Object value, Throwable exception) { - return new SerializationDiagnostic(VALUE_CONVERSION_EXCEPTION, semanticObject, element, exception.getMessage()); + public ISerializationDiagnostic getValueConversionExceptionDiagnostic(EObject semantic, AbstractElement element, + Object value, Throwable exception) { + String ruleName = linkingHelper.getRuleNameFrom(element); + StringBuilder msg = new StringBuilder(); + msg.append("Error while converting value '"); + msg.append(value); + msg.append("' for grammar rule '"); + msg.append(ruleName); + msg.append("' to string via ValueConverter."); + return new SerializationDiagnostic(VALUE_CONVERSION_EXCEPTION, semantic, element, msg.toString(), exception); } }