patternbashMinor
Extracting the classpath entries from a jar file's manifest
Viewed 0 times
thefilejarmanifestclasspathextractingfromentries
Problem
Sometimes I need to search for dependencies in the classpath entries in the manifest of jar files. A jar manifest with classpaths looks like this:
Searching for jars in a manifest is troublesome:
Step 2 is necessary, because of the line breaks. For example, I won't find "struts" in the above, because the word is broken in the middle.
I use this shell script to make this process easier, I call it
For a jar file with the manifest as above, this will output:
`spring-aop-3.2.0.jar
spring-aspects-3.2.0.jar
spring-beans-3.2.0.jar
spring-context-3.2.0.jar
spring-context-support-3.2.0.jar
spring-core-3.2.0.jar
spring-expression-3.2.0.jar
spring-instrum
Manifest-Version: 1.0
Created-By: 1.6.0_29 (Sun Microsystems Inc.)
Class-Path: spring-aop-3.2.0.jar spring-aspects-3.2.0.jar spring-beans
-3.2.0.jar spring-context-3.2.0.jar spring-context-support-3.2.0.jar
spring-core-3.2.0.jar spring-expression-3.2.0.jar spring-instrument-3
.2.0.jar spring-instrument-tomcat-3.2.0.jar spring-jdbc-3.2.0.jar spr
ing-jms-3.2.0.jar spring-orm-3.2.0.jar spring-oxm-3.2.0.jar spring-st
ruts-3.2.0.jar spring-test-3.2.0.jar spring-tx-3.2.0.jar spring-web-3
.2.0.jar spring-webmvc-3.2.0.jar spring-webmvc-portlet-3.2.0.jar
Searching for jars in a manifest is troublesome:
- Extract the
META-INF/MANIFEST.MFfile from the jar
- Re-join the split lines to make searching humanely possible
Step 2 is necessary, because of the line breaks. For example, I won't find "struts" in the above, because the word is broken in the middle.
I use this shell script to make this process easier, I call it
jar-manifest-classpath.sh:#!/bin/bash
if test -d "$TMPDIR"; then
:
elif test -d "$TMP"; then
TMPDIR=$TMP
elif test -d /var/tmp; then
TMPDIR=/var/tmp
else
TMPDIR=/tmp
fi
workdir=$TMPDIR/$(basename "$0")-work-$$
cleanup() {
rm -fr "$workdir"
}
mkdir -p "$workdir"
trap 'cleanup' 1 2 3 15
for jar; do
if ! test -f $jar; then
echo warning: not a file: $jar
continue
fi
[[ $jar = /* ]] || jar=$PWD/$jar
(
cd "$workdir" || exit 1
jar xf "$jar"
sed -ne '/^Class-Path:/,$p' META-INF/MANIFEST.MF | sed -e 's/^Class-Path: //' -e 's/^ //' | tr -d '\n' | tr ' ' '\n'
)
done
cleanup
For a jar file with the manifest as above, this will output:
`spring-aop-3.2.0.jar
spring-aspects-3.2.0.jar
spring-beans-3.2.0.jar
spring-context-3.2.0.jar
spring-context-support-3.2.0.jar
spring-core-3.2.0.jar
spring-expression-3.2.0.jar
spring-instrum
Solution
I would create the trap for cleanup before an action is done that needs cleanup, so change the sequence of commands. Also I would prefer signal names instead of numbers. If you add EXIT to the signal list then cleanup is called when the shell is exited, so you can remove the last line of your script (
If the script is called without argument or with
Warnings and error messages should be written to stderr(2) and not to stdout(1). This is Unix standard behaviour for a program. Otherwise you will not see the error message if you pipe the output through a
cleanup)trap 'cleanup' EXIT SIGHUP SIGINT SIGQUIT SIGTERM
mkdir -p "$workdir"If the script is called without argument or with
-? a usage message should be displayed.Warnings and error messages should be written to stderr(2) and not to stdout(1). This is Unix standard behaviour for a program. Otherwise you will not see the error message if you pipe the output through a
grep command.Code Snippets
trap 'cleanup' EXIT SIGHUP SIGINT SIGQUIT SIGTERM
mkdir -p "$workdir"Context
StackExchange Code Review Q#74087, answer score: 8
Revisions (0)
No revisions yet.