Skip to main content

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [List Home]
[higgins-dev] build file

Hi

Before I discovered the auto build system for Higgins, I wrote a Gant (http://gant.codehaus.org) script for building the Higgins projects. The single build file can build any of the plugins and the necessary dependencies, based on the Eclipse settings. It can also build war files and execute junit tests. The Higgins build system can probably do a lot of things which this script cannot, but I find it easier to work with, and there's no risk of getting out of sync with the Eclipse settings. So, if anybody wants to use it, go ahead.

Btw, use it like this:


cd org.eclipse.higgins.sts.binding.axis1x.service/
gant -f ../build.gant build (to build a jar file)
gant -f ../build.gant war (to build a war file)
gant -f ../build.gant test (to execute junit tests)

The variable searchPatterns in the beginning of the script must be modified to reflect your local Eclipse installation. Any required Higgins plugins must have been checkout before running the script.


Regards,
--
Joakim Recht

Trifork A/S, Margrethepladsen 4, 8000 Aarhus C, Denmark
Phone: +45 8732 8787 /  Mobile: +45 2021 6257
http://www.trifork.com - E-mail: jre@xxxxxxxxxxx
includeTargets << gant.targets.Clean

cleanDirectory << ['target', 'lib/build', 'lib/test', 'lib/dist']
cleanPattern << [ '**/*~' , '**/*.bak' ]

searchPaths = ['..', '/home/recht/projekt/eclipse']

locatePlugin = { name, dest, jarFiles, seen ->
	if (seen.contains(name)) {
		ant.echo (level: 'debug', message: "Already found " + name)
		return
	}
	ant.echo (level: 'verbose', message: "Locating plugin " + name)
	searchPaths.each {
		def dir = new File(it)
		dir.eachDir { pluginDir ->
			def mf = new File(pluginDir, "META-INF/MANIFEST.MF") 
			if (mf.exists()) {
				def m = new java.util.jar.Manifest(mf.newInputStream())
				if (m.mainAttributes.getValue("Bundle-SymbolicName").split(";")[0] == name) {
					ant.echo (level: 'debug', message: "Found " + name + " in " + pluginDir)
					
					if (new File(pluginDir, '.project').exists()) {
						buildEclipse pluginDir.absolutePath, dest, jarFiles, seen
					} else {
						// assume unzipped plugin with jar files
						m.mainAttributes.getValue("Bundle-Classpath").split(",").each {
							jarFiles << new File(pluginDir, it).absolutePath
						}
						
						def req = parseRequired(m)
						req && req.each {
							locatePlugin it, dest, jarFiles, seen
						}
					}
				}
			}
		}
		dir.eachFileMatch (~".*.jar") {
			def jar = new java.util.jar.JarFile(it)
			if (jar.manifest.mainAttributes.getValue("Bundle-SymbolicName").split(";")[0] == name) {
				def req = parseRequired(jar.manifest)
				ant.echo (level: 'debug', message: "Required plugins from " + it + ": " + req)
				seen << name
				jarFiles << it.absolutePath

				req && req.each {
						locatePlugin it, dest, jarFiles, seen
				}
			
			}
		}
		
	}
}

parseRequired = { manifest ->
	def req = manifest.mainAttributes.getValue("Require-Bundle")
	if (!req) return
	
	return req.replaceAll('"[^"]+"', "").split(",").collect {
		it.split(";")[0]
	}
}

buildEclipse = { path, dest, jarFiles = [], seen = [] ->
	def cp = new XmlParser().parseText(new File(path + '/.classpath').getText())
	def project = new XmlParser().parseText(new File("${path}/.project").getText()).name.text()
	
	if (seen.contains(project)) {
		return
	}
	println "Building project ${project}"

	ant.echo (level: 'verbose', message: "Building Eclipse project from " + path)
	seen << project
	
	cp.classpathentry.each { entry ->
		if (entry.'@kind' == 'con' && entry.'@path' == 'org.eclipse.pde.core.requiredPlugins') {
			def mf = new java.util.jar.Manifest(new File(path + '/META-INF/MANIFEST.MF').newInputStream())
			def req = parseRequired(mf)
			ant.echo (level: 'debug', message: "Required plugins from " + path + ": " + req)
			req && req.each {
					locatePlugin it, dest, jarFiles, seen
			}
		}
		if (entry.'@kind' == 'src' && entry.'@path'.startsWith('/')) {
			buildEclipse path + '/..' + entry.'@path', dest, jarFiles, seen
		}
	}

	def buildDir = "${dest}/${project}"
	ant.mkdir (dir: "${buildDir}/build")
	
	def srcs = cp.classpathentry.findAll { it.'@kind' == 'src' && !it.'@path'.startsWith("/") }
	if (!srcs.empty) {
		ant.javac (destdir: "${buildDir}/build", debug: true, source: '1.4', target: '1.4') {
			src {
				srcs.each {
					pathelement(location: path + "/" + it.'@path')
				}
			}
			classpath {
				jarFiles.each {
					pathelement (location: it)
				}
			}
		}
		
		def mfPath
		if (new File(path + '/META-INF/MANIFEST.MF').exists()) {
			mfPath = path + '/META-INF/MANIFEST.MF'
		} else {
			ant.manifest (file: "${buildDir}/MANIFEST.MF") {
				attribute (name: 'Implementation-Title', value: project)
			}
			mfPath = "${buildDir}/MANIFEST.MF"
		}
		
		ant.jar (destfile: "${buildDir}/${project}.jar", defaultexcludes: true, filesetmanifest: "merge", manifest: mfPath) {
			zipfileset (dir: "${buildDir}/build")
			srcs.each {
				fileset (dir: path + "/" + it.'@path', excludes: '**/*.java')
			}
			
			manifest {
				attribute (name: 'Built-By', value: System.getProperty("user.name"))
			}
		} 
		jarFiles << "${buildDir}/${project}.jar"
		
	}
	
	cp.classpathentry.findAll { it.'@kind' == 'lib' }.each {
		jarFiles << path + '/' + it.'@path'
	}
}

target (init: 'Initialize') {
	['target', 'target/build', 'target/plugins'].each {
		ant.mkdir(dir: it)
	}
}

target(build: 'Build project') { jarFiles = [] ->
	depends(init)
	
	buildEclipse('.', 'target/plugins', jarFiles)
	
	def project = new XmlParser().parseText(new File(".project").getText()).name.text()
	println "Built jar file to target/plugins/${project}/${project}.jar"
}

target (war: 'Build war file') {
	def jarFiles = []
	depends(init)
	build(jarFiles)
	
	ant.war (destfile: 'target/file.war', webxml: 'WebContent/WEB-INF/web.xml', defaultexcludes: true) {
		jarFiles.unique().each {
			lib (file: it)
		}
	}	
}


target (test: 'Run unit tests') {
	def jarFiles = []
	build(jarFiles)

	testBuildDir = "target/build-test"
	testReports = "target/reports"
	[testBuildDir, testReports, "${testReports}/html"].each {
		ant.mkdir (dir: it)
	}
	

	ant.javac (destdir: "${testBuildDir}", debug: true, source: '1.4', target: '1.4') {
		src {
			pathelement (location: 'test')
		}
		classpath {
			jarFiles.each {
				pathelement (location: it)
			}
		}
	}
		
	junit (forkmode: 'once', fork: true, failureproperty: 'tests.failed', printsummary: true) {
		formatter (type: 'plain')
		formatter (type: 'xml')
		classpath {
			pathelement(location: testBuildDir)
			jarFiles.each {
				pathelement (location: it)
			}
		}
		batchtest(todir: testReports, fork: true) {
			fileset (dir: testBuildDir, includes: '**/*Test.class')
		}
	}
	ant.junitreport (todir: "${testReports}/html") {
		fileset (dir: testReports, includes: 'TEST-*.xml')
		report (format: 'frames', todir: "${testReports}/html")
	}
	fail(if: 'tests.failed', message: 'There were test failures')
	
}

Back to the top