You are viewing a plain text version of this content. The canonical link for it is here.
Posted to oak-commits@jackrabbit.apache.org by md...@apache.org on 2016/01/08 15:39:47 UTC
svn commit: r1723730 -
/jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/segment/SegmentGraph.java
Author: mduerig
Date: Fri Jan 8 14:39:47 2016
New Revision: 1723730
URL: http://svn.apache.org/viewvc?rev=1723730&view=rev
Log:
OAK-3853: Improve SegmentGraph resilience
Include errors during parsing as error nodes in the graphs
Modified:
jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/segment/SegmentGraph.java
Modified: jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/segment/SegmentGraph.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/segment/SegmentGraph.java?rev=1723730&r1=1723729&r2=1723730&view=diff
==============================================================================
--- jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/segment/SegmentGraph.java (original)
+++ jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/segment/SegmentGraph.java Fri Jan 8 14:39:47 2016
@@ -23,11 +23,16 @@ import static com.google.common.base.Pre
import static com.google.common.base.Preconditions.checkNotNull;
import static com.google.common.collect.Maps.newHashMap;
import static com.google.common.collect.Sets.newHashSet;
+import static java.util.Collections.singletonMap;
+import static org.apache.jackrabbit.oak.commons.IOUtils.closeQuietly;
import static org.apache.jackrabbit.oak.plugins.segment.SegmentId.isDataSegmentId;
+import java.io.BufferedReader;
import java.io.IOException;
import java.io.OutputStream;
import java.io.PrintWriter;
+import java.io.StringReader;
+import java.io.StringWriter;
import java.util.Date;
import java.util.HashSet;
import java.util.Map;
@@ -244,7 +249,12 @@ public final class SegmentGraph {
public String apply(UUID segmentId) {
Map<String, String> info = getSegmentInfo(segmentId, fileStore.getTracker());
if (info != null) {
- return info.get("gc");
+ String error = info.get("error");
+ if (error != null) {
+ return "Error";
+ } else {
+ return info.get("gc");
+ }
} else {
return "";
}
@@ -296,73 +306,89 @@ public final class SegmentGraph {
public static Graph<UUID> parseHeadGraph(@Nonnull RecordId root) {
final Graph<UUID> graph = new Graph<UUID>();
- new SegmentParser() {
- private void addEdge(RecordId from, RecordId to) {
- graph.addVertex(from.asUUID());
- graph.addVertex(to.asUUID());
- graph.addEdge(from.asUUID(), to.asUUID());
- }
- @Override
- protected void onNode(RecordId parentId, RecordId nodeId) {
- super.onNode(parentId, nodeId);
- addEdge(parentId, nodeId);
- }
- @Override
- protected void onTemplate(RecordId parentId, RecordId templateId) {
- super.onTemplate(parentId, templateId);
- addEdge(parentId, templateId);
- }
- @Override
- protected void onMap(RecordId parentId, RecordId mapId, MapRecord map) {
- super.onMap(parentId, mapId, map);
- addEdge(parentId, mapId);
- }
- @Override
- protected void onMapDiff(RecordId parentId, RecordId mapId, MapRecord map) {
- super.onMapDiff(parentId, mapId, map);
- addEdge(parentId, mapId);
- }
- @Override
- protected void onMapLeaf(RecordId parentId, RecordId mapId, MapRecord map) {
- super.onMapLeaf(parentId, mapId, map);
- addEdge(parentId, mapId);
- }
- @Override
- protected void onMapBranch(RecordId parentId, RecordId mapId, MapRecord map) {
- super.onMapBranch(parentId, mapId, map);
- addEdge(parentId, mapId);
- }
- @Override
- protected void onProperty(RecordId parentId, RecordId propertyId, PropertyTemplate template) {
- super.onProperty(parentId, propertyId, template);
- addEdge(parentId, propertyId);
- }
- @Override
- protected void onValue(RecordId parentId, RecordId valueId, Type<?> type) {
- super.onValue(parentId, valueId, type);
- addEdge(parentId, valueId);
- }
- @Override
- protected void onBlob(RecordId parentId, RecordId blobId) {
- super.onBlob(parentId, blobId);
- addEdge(parentId, blobId);
- }
- @Override
- protected void onString(RecordId parentId, RecordId stringId) {
- super.onString(parentId, stringId);
- addEdge(parentId, stringId);
- }
- @Override
- protected void onList(RecordId parentId, RecordId listId, int count) {
- super.onList(parentId, listId, count);
- addEdge(parentId, listId);
- }
- @Override
- protected void onListBucket(RecordId parentId, RecordId listId, int index, int count, int capacity) {
- super.onListBucket(parentId, listId, index, count, capacity);
- addEdge(parentId, listId);
- }
- }.parseNode(checkNotNull(root));
+ try {
+ new SegmentParser() {
+ private void addEdge(RecordId from, RecordId to) {
+ graph.addVertex(from.asUUID());
+ graph.addVertex(to.asUUID());
+ graph.addEdge(from.asUUID(), to.asUUID());
+ }
+
+ @Override
+ protected void onNode(RecordId parentId, RecordId nodeId) {
+ super.onNode(parentId, nodeId);
+ addEdge(parentId, nodeId);
+ }
+
+ @Override
+ protected void onTemplate(RecordId parentId, RecordId templateId) {
+ super.onTemplate(parentId, templateId);
+ addEdge(parentId, templateId);
+ }
+
+ @Override
+ protected void onMap(RecordId parentId, RecordId mapId, MapRecord map) {
+ super.onMap(parentId, mapId, map);
+ addEdge(parentId, mapId);
+ }
+
+ @Override
+ protected void onMapDiff(RecordId parentId, RecordId mapId, MapRecord map) {
+ super.onMapDiff(parentId, mapId, map);
+ addEdge(parentId, mapId);
+ }
+
+ @Override
+ protected void onMapLeaf(RecordId parentId, RecordId mapId, MapRecord map) {
+ super.onMapLeaf(parentId, mapId, map);
+ addEdge(parentId, mapId);
+ }
+
+ @Override
+ protected void onMapBranch(RecordId parentId, RecordId mapId, MapRecord map) {
+ super.onMapBranch(parentId, mapId, map);
+ addEdge(parentId, mapId);
+ }
+
+ @Override
+ protected void onProperty(RecordId parentId, RecordId propertyId, PropertyTemplate template) {
+ super.onProperty(parentId, propertyId, template);
+ addEdge(parentId, propertyId);
+ }
+
+ @Override
+ protected void onValue(RecordId parentId, RecordId valueId, Type<?> type) {
+ super.onValue(parentId, valueId, type);
+ addEdge(parentId, valueId);
+ }
+
+ @Override
+ protected void onBlob(RecordId parentId, RecordId blobId) {
+ super.onBlob(parentId, blobId);
+ addEdge(parentId, blobId);
+ }
+
+ @Override
+ protected void onString(RecordId parentId, RecordId stringId) {
+ super.onString(parentId, stringId);
+ addEdge(parentId, stringId);
+ }
+
+ @Override
+ protected void onList(RecordId parentId, RecordId listId, int count) {
+ super.onList(parentId, listId, count);
+ addEdge(parentId, listId);
+ }
+
+ @Override
+ protected void onListBucket(RecordId parentId, RecordId listId, int index, int count, int capacity) {
+ super.onListBucket(parentId, listId, index, count, capacity);
+ addEdge(parentId, listId);
+ }
+ }.parseNode(checkNotNull(root));
+ } catch (SegmentNotFoundException e) {
+ System.err.println("Error head graph parsing: " + e);
+ }
return graph;
}
@@ -371,19 +397,37 @@ public final class SegmentGraph {
if (sInfo == null) {
writer.write(node + ",b,bulk,b,-1,-1," + inHead + "\n");
} else {
- long t = asLong(sInfo.get("t"));
- long ts = t - epoch.getTime();
- checkArgument(ts >= Integer.MIN_VALUE && ts <= Integer.MAX_VALUE,
+ String error = sInfo.get("error");
+ if (error != null) {
+ writer.write(node +
+ "," + firstLine(error) +
+ ",error,e,-1,-1," + inHead + "\n");
+ } else {
+ long t = asLong(sInfo.get("t"));
+ long ts = t - epoch.getTime();
+ checkArgument(ts >= Integer.MIN_VALUE && ts <= Integer.MAX_VALUE,
"Time stamp (" + new Date(t) + ") not in epoch (" +
- new Date(epoch.getTime() + Integer.MIN_VALUE) + " - " +
- new Date(epoch.getTime() + Integer.MAX_VALUE) + ")");
- writer.write(node +
+ new Date(epoch.getTime() + Integer.MIN_VALUE) + " - " +
+ new Date(epoch.getTime() + Integer.MAX_VALUE) + ")");
+ writer.write(node +
"," + sInfo.get("sno") +
",data" +
"," + sInfo.get("wid") +
"," + sInfo.get("gc") +
"," + ts +
"," + inHead + "\n");
+ }
+ }
+ }
+
+ private static String firstLine(String string) {
+ BufferedReader reader = new BufferedReader(new StringReader(string));
+ try {
+ return reader.readLine();
+ } catch (IOException e) {
+ return string;
+ } finally {
+ closeQuietly(reader);
}
}
@@ -394,17 +438,32 @@ public final class SegmentGraph {
private static Map<String, String> getSegmentInfo(UUID node, SegmentTracker tracker) {
if (isDataSegmentId(node.getLeastSignificantBits())) {
SegmentId id = tracker.getSegmentId(node.getMostSignificantBits(), node.getLeastSignificantBits());
- String info = id.getSegment().getSegmentInfo();
- if (info != null) {
- JsopTokenizer tokenizer = new JsopTokenizer(info);
- tokenizer.read('{');
- return JsonObject.create(tokenizer).getProperties();
- } else {
- return null;
+ try {
+ String info = id.getSegment().getSegmentInfo();
+ if (info != null) {
+ JsopTokenizer tokenizer = new JsopTokenizer(info);
+ tokenizer.read('{');
+ return JsonObject.create(tokenizer).getProperties();
+ } else {
+ return null;
+ }
+ } catch (SegmentNotFoundException e) {
+ return singletonMap("error", toString(e));
}
} else {
return null;
}
}
+ private static String toString(Throwable e) {
+ StringWriter sw = new StringWriter();
+ PrintWriter pw = new PrintWriter(sw, true);
+ try {
+ e.printStackTrace(pw);
+ return sw.toString();
+ } finally {
+ pw.close();
+ }
+ }
+
}