Using Groovy to update KPhotoAlbum database

Since some time now KPhotoAlbum crashes on my Linux Mint Debian Edition, when new images are searched (and some other actions). As this is really annoying I looked for solutions. Updating to a newer version than 4.1.1 was not possible. Compiling from source was also out due to library version conflicts. All I really needed was a way to add new files to the index.xml file, which is KPhotoAlbums database. Due to the XML nature of the problem, I gave Groovy a shot.

Basically there are three tasks to be performed:

  • Retrieve the list of files already in the XML database
  • Compare that list with the files on the system
  • Add the missing files to the XML database
package ch.sahits.image.cmd

import groovy.xml.XmlUtil

import java.security.MessageDigest

def baseDirName = args[0]

// Copy files
copy = { File src,File dest->

   def input = src.newDataInputStream()
   def output = dest.newDataOutputStream()

   output << input

   input.close()
   output.close()
}

// Generate md5 hash as a 32 char String for 'obj'
// 'obj' can be a File, InputStream or URL
def md5( obj ) {
	def hash = MessageDigest.getInstance( 'MD5' ).with {
		obj.eachByte( 8192 ) { bfr, num ->
			update bfr, 0, num
		}
		it.digest()
	}
	new BigInteger( 1, hash ).toString( 16 ).padLeft( 32, '0' )
}

def inputXMLFile = new File(baseDirName+'/index.xml')
def inputXMLBackupFile = new File(baseDirName+'/index.xml.backup')

// make a backup
copy(inputXMLFile, inputXMLBackupFile)

def baseDirectory = new File(baseDirName)

def fileListBase = baseDirectory.listFiles()
def fileList = fileListBase.findAll {
	!it.isDirectory()
}

def root = new XmlParser().parse(inputXMLFile)

// Filter out all files that are not yet in the XML
for (Iterator<File> iterator = fileList.iterator(); iterator.hasNext();) {
	File file = iterator.next();
	def fileName = file.name
	root.images.image.each {
		if (it.'@file'.equals(fileName) ) {
			iterator.remove()
		}
	}
}

// Add the entries of the missing files to the XML
fileList.each {
	def label = it.name
	if (it.name.indexOf('.') > 0) {
		label = it.name.substring(0, it.name.lastIndexOf('.'))
	}
	def file = new File(baseDirName+'/'+it.name)
	def md5 = md5(file)
	def imagesNode = root.images[0]
	imagesNode.appendNode('image', [md5sum:md5, startDate:'', height:'-1', file:it.name, width:'-1', endDate:'', label:label, angle:'0'])
}

XmlUtil.serialize(root, System.out)

Schreibe einen Kommentar