Transformation von Metadaten in komplexe XML-Formate mit OpenRefine




Lightning Talk von Felix Lohmeier

Workshop DINI AG KIM
5.5.2017, Mannheim

Problemstellung


  • Die Templating-Funktion von OpenRefine wird von einigen Anwendern erfolgreich genutzt, um einfache XML-Formate wie MODS zu generieren.
  • Komplexe XML-Formate (wie z.B. die Findbuch-Struktur von EAD) erfordern die Zusammenführung von Bestandsinformationen und zugehörigen Objekten in einen Zieldatensatz. Teilbestände, Konvolute und Objekte müssen ggf. verschachtelt werden.
  • Bedingt durch die zeilenbasierte Verarbeitung der Templating-Funktion müssten dazu alle für einen Zieldatensatz benötigten Daten in einer Zeile stehen.

Struktur EAD XML




  ...
  
    ...
    
      
        
          ...
          
            ...
            ...
            ...
          
          ...
        
        ...
      
    
  

Lösungsansatz


  • Sortieren, damit Bestandsinformationen und zugehörige Objekte direkt aufeinanderfolgen
  • If-Funktion im Template, um verschiedene Fälle abbilden zu können
  • Kommentar zu Beginn jedes neuen Zieldatensatzes, damit daraufhin später der Gesamtexport gesplittet werden kann
  • Berechnung und Ausgabe des Hierarchielevels, damit anhand dessen mit XSLT die XML-Struktur nachträglich "verschachtelt" werden kann

Demo mit Beispieldaten



Gewünschter Output

Kalliope Musterdatensatz "Dokumentation EAD des Kalliope-Verbundes, Anhang: Minimale Anforderungen"




    
    
    
    
    
    	
    		Titel des Findbuchs
    	
    
    
    
    
    	
    		
    			Landesarchiv Berlin
    		
    		Titel des Nachlasses
    	
    	
    		
                
	                
	                    Landesarchiv Berlin
	                
	                Titel des Teilnachlasses
				
				
					
                        
                            Landesarchiv Berlin
                        
						Titel des Systematikpunktes
					
					
						
                            
                                Landesarchiv Berlin
                            
							Titel einer Verzeichnungseinheit (Konvolut)
						
					
					
						
                            
                                Landesarchiv Berlin
                            
							Titel einer Verzeichniseinheit (Konvolut)
						
						
							
                                
                                    Landesarchiv Berlin
                                
								Titel eines Einzeldokuments
							
						
						
							
                                
                                    Landesarchiv Berlin
                                
								Titel eines Einzeldokuments
							
						
						
							
                                
                                    Landesarchiv Berlin
                                
								Titel eines Einzeldokuments
							
						
					
				
			
		
	

Input

fiktive CSV-Daten aus Kalliope Musterdatensatz abgeleitet


id,level,title,parent
4901,collection,Titel des Nachlasses,
4901-1,fonds,Titel des Teilnachlasses,4901
4901-2,class,Titel des Systematikpunktes,4901-1
4901-3,file,Titel einer Verzeichniseinheit (Konvolut),4901-2
4901-4,file,Titel einer Verzeichniseinheit (Konvolut),4901-2
4901-5,item,Titel eines Einzeldokuments,4901-4
4901-6,item,Titel eines Einzeldokuments,4901-4
4901-7,item,Titel eines Einzeldokuments,4901-4

OpenRefine

Transformationen

  • add new column parent2/parent3/parent4 based on column parent/parent2/parent3:
    cell.cross("ead","id")[0].cells["parent"].value)
  • add new column hierarchy based on column parent4:
    join(filter(forEach(["parent4","parent3","parent2","parent","id"],cn,if(isNull(cells[cn]),"",cells[cn].value)),v,isNonBlank(v)),",")
  • add column hierarchy_top based on hierarchy:
    split(value,",")[0]
  • add column hierarchy_level based on hierarchy:
    hierarchy_level length(split(value,","))
  • Row Template

    
    {{if(cells["level"].value == "collection",'
    
    
        
        
            
                '+cells["title"].value.escape("xml")+'
            
        
    
    
        
            
                Landesarchiv Berlin
            
            '+cells["title"].value.escape("xml")+'
        
        
    ',"")}}{{if(cells["level"].value == "fonds",'        
                
                    
    		            Landesarchiv Berlin
                    
                    '+cells["title"].value.escape("xml")+'
                
            
    ',"")}}{{if(cells["level"].value == "class",'        
                
                    
    		            Landesarchiv Berlin
                    
                    '+cells["title"].value.escape("xml")+'
                
            
    ',"")}}{{if(cells["level"].value == "file",'        
                
                    
    		            Landesarchiv Berlin
                    
                    '+cells["title"].value.escape("xml")+'
                
            
    ',"")}}{{if(cells["level"].value == "item",'        
                
                    
    		            Landesarchiv Berlin
                    
                    '+cells["title"].value.escape("xml")+'
                
            
    ',"")}}
    

    Nachbearbeitung mit XSLT

    Vorverarbeitung


  • Gesamtexport aufsplitten:
    csplit --prefix=ead- --suffix-format=%03d.xml --suppress-matched ead.txt '//' {*}
    rm -f ead-000.xml
  • Prefix und Suffix ergänzen:
  • for i in *.xml; do printf '%s\n%s\n%s\n' '    </dsc>' '</archdesc>' '</ead>' >> $i; sed -i '1 s/^/\n/' $i; done

    XSL Stylesheet

    Leicht abgewandelt auf Basis von Vorlage auf Stackoverflow

    
    
        
        
            
                
            
        
        
            
            
                
                    
                    
                
        
        
        
            
            
            
                
                    
                    
                    
                        
                        
                    
                
            
        
    
    

    Prozessierung

    Über Webseite http://xsltransform.net oder auf der Kommandozeile mit Saxon-HE:

    
    wget -O Saxon-HE.jar http://central.maven.org/maven2/net/sf/saxon/Saxon-HE/9.7.0-18/Saxon-HE-9.7.0-18.jar
    mkdir input
    mv *.xml input/
    mkdir output
    java -jar Saxon-HE.jar -s:input -xsl:ead.xsl -o:output
    

    Fragen ans Plenum



    • Hat jemand Erfahrungen mit der Templating-Funktion?
    • Kennt jemand klügere Lösungsansätze?

    Credits / Lizenz