1
1
from pathlib import Path
2
2
from xml .etree import ElementTree
3
+
3
4
from pydantic import validate_arguments
4
5
5
6
import kmm
@@ -18,8 +19,8 @@ def from_path(path: Path):
18
19
"""
19
20
try :
20
21
tree = ElementTree .parse (path )
21
- except ElementTree .ParseError as e :
22
- raise ValueError ( "Unable to parse header file, invalid XML." ) from e
22
+ except ElementTree .ParseError :
23
+ tree = attempt_to_patch_xml ( path )
23
24
24
25
position , sync = kmm .header .position_sync (tree )
25
26
return Header (
@@ -29,6 +30,33 @@ def from_path(path: Path):
29
30
)
30
31
31
32
33
+ def attempt_to_patch_xml (path : Path ):
34
+ """
35
+ Attempts to patch a broken header file by adding missing end tags.
36
+ """
37
+ lines = path .read_text ().splitlines ()
38
+ start_tags = []
39
+ for line in lines :
40
+ if line .startswith ("</" ) and line .endswith (">" ):
41
+ try :
42
+ index = max (
43
+ i
44
+ for i , start_tag in enumerate (start_tags )
45
+ if start_tag == line [2 :- 1 ]
46
+ )
47
+ except ValueError :
48
+ raise ElementTree .ParseError (f"Missing start tag for { line } " )
49
+ start_tags .pop (index )
50
+ elif line .startswith ("<" ) and line .endswith (">" ) and not line .startswith ("<?" ):
51
+ start_tags .append (line [1 :- 1 ])
52
+ for start_tag in start_tags [::- 1 ]:
53
+ lines .append (f"</{ start_tag } >" )
54
+ try :
55
+ return ElementTree .ElementTree (ElementTree .fromstring ("\n " .join (lines )))
56
+ except ElementTree .ParseError as e :
57
+ raise ValueError ("Unable to parse header file, invalid XML." ) from e
58
+
59
+
32
60
def test_header ():
33
61
Header .from_path ("tests/ascending_B.hdr" )
34
62
0 commit comments