public SylkTable Parse(Stream input, bool leaveOpen = false) { using var reader = new StreamReader(input, Encoding.UTF8, true, 1024, leaveOpen); var isOnFirstLine = true; while (true) { var line = reader.ReadLine(); var fields = line.Split(';'); var recordType = fields[0]; string GetField(string fieldName, bool mandatory) { foreach (var field in fields) { if (field.StartsWith(fieldName)) { return(field.Substring(fieldName.Length)); } } if (mandatory) { throw new InvalidDataException($"Record does not contain mandatory field of type '{fieldName}'."); } return(null); } if (isOnFirstLine) { isOnFirstLine = false; if (recordType != "ID") { throw new InvalidDataException("SYLK file must start with 'ID'."); } GetField("P", true); } else { switch (recordType) { case "ID": throw new InvalidDataException("Record type 'ID' can only occur on the first line."); case "B": if (_table != null) { throw new InvalidDataException("Only one record of type 'B' may be present."); } _table = new SylkTable(int.Parse(GetField("X", true)), int.Parse(GetField("Y", true))); break; case "C": if (_table == null) { throw new InvalidDataException("Unable to parse record of type 'C' before encountering a record of type 'B'."); } SetCellContent(GetField("X", true), GetField("Y", false), GetField("K", false)); break; case "E": return(_table); default: throw new NotSupportedException($"Support for record type '{recordType}' is not implemented. Only records of type 'ID', 'B', 'C', and 'E' are supported."); } } } }
public SylkSerializer(SylkTable table) { _table = table; }