Skip to content

Commit 1ac2932

Browse files
Improve xblock deserialization error handling
Wrap serializer.Deserialize in a try/catch to log deserialization errors (and inner exception) and safely return an empty entity list on failure. Add a mapId parameter to GetInstance so error messages include the source map/file name, and update unknown-property logging to include the model name and map id. Also pass the file name (or "XML Input" for string inputs) to GetInstance calls to provide better context when reporting issues.
1 parent ad4aacf commit 1ac2932

1 file changed

Lines changed: 16 additions & 5 deletions

File tree

Maple2.File.Parser/MapXBlock/XBlockParser.cs

Lines changed: 16 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -90,7 +90,18 @@ public static IEnumerable<string> CheckParseOrder(ICollection<Type> types) {
9090
}
9191

9292
private IEnumerable<IMapEntity> ParseEntities(PackFileEntry file) {
93-
if (serializer.Deserialize(reader.GetXmlReader(file)) is GameXBlock block) {
93+
GameXBlock block;
94+
try {
95+
block = serializer.Deserialize(reader.GetXmlReader(file)) as GameXBlock;
96+
} catch (Exception ex) {
97+
OnError?.Invoke($"Failed to deserialize xblock '{file.Name}': {ex.Message}");
98+
if (ex.InnerException != null) {
99+
OnError?.Invoke($" Inner: {ex.InnerException.Message}");
100+
}
101+
return Array.Empty<IMapEntity>();
102+
}
103+
104+
if (block != null) {
94105
var unknownModels = new HashSet<string>();
95106
return block.entitySet.entity
96107
.Where(entity => {
@@ -103,7 +114,7 @@ private IEnumerable<IMapEntity> ParseEntities(PackFileEntry file) {
103114
})
104115
.Select(entity => {
105116
try {
106-
return GetInstance(entity);
117+
return GetInstance(entity, file.Name);
107118
} catch (UnknownModelTypeException ex) {
108119
// Reduce noise from this exception to once per file
109120
if (unknownModels.Add(entity.modelName)) {
@@ -118,7 +129,7 @@ private IEnumerable<IMapEntity> ParseEntities(PackFileEntry file) {
118129
return Array.Empty<IMapEntity>();
119130
}
120131

121-
private IMapEntity GetInstance(Entity entity) {
132+
private IMapEntity GetInstance(Entity entity, string mapId) {
122133
Type entityType = lookup.GetClass(entity.modelName);
123134

124135
var mapEntity = (IMapEntity) Activator.CreateInstance(entityType);
@@ -141,7 +152,7 @@ private IMapEntity GetInstance(Entity entity) {
141152

142153
FlatProperty modelProperty = baseType.GetProperty(property.name);
143154
if (modelProperty == null) {
144-
OnError?.Invoke($"Ignoring unknown property {property.name}");
155+
OnError?.Invoke($"Ignoring unknown property {property.name} on {entity.modelName} from map {mapId}");
145156
continue;
146157
}
147158

@@ -187,7 +198,7 @@ public void ParseXml(XmlReader xmlReader, Action<IEnumerable<IMapEntity>> callba
187198
})
188199
.Select(entity => {
189200
try {
190-
return GetInstance(entity);
201+
return GetInstance(entity, "XML Input");
191202
} catch (UnknownModelTypeException ex) {
192203
if (unknownModels.Add(entity.modelName)) {
193204
OnError?.Invoke(ex.Message);

0 commit comments

Comments
 (0)