J'essaie de lancer le fichier jar de mon projet. Je travaille sur intelliJ et utilise des artefacts pour générer le fichier jar. Mais chaque fois que j'essaye de lancer mon fichier jar, cela me donne une exception.
Java.lang.SecurityException: Invalid signature file digest for Manifest main attributes
at Sun.security.util.SignatureFileVerifier.processImpl(SignatureFileVerifier.Java:284)
at Sun.security.util.SignatureFileVerifier.process(SignatureFileVerifier.Java:238)
at Java.util.jar.JarVerifier.processEntry(JarVerifier.Java:316)
at Java.util.jar.JarVerifier.update(JarVerifier.Java:228)
at Java.util.jar.JarFile.initializeVerifier(JarFile.Java:383)
at Java.util.jar.JarFile.getInputStream(JarFile.Java:450)
at Sun.misc.JarIndex.getJarIndex(JarIndex.Java:137)
at Sun.misc.URLClassPath$JarLoader$1.run(URLClassPath.Java:839)
at Sun.misc.URLClassPath$JarLoader$1.run(URLClassPath.Java:831)
at Java.security.AccessController.doPrivileged(Native Method)
at Sun.misc.URLClassPath$JarLoader.ensureOpen(URLClassPath.Java:830)
at Sun.misc.URLClassPath$JarLoader.<init>(URLClassPath.Java:803)
at Sun.misc.URLClassPath$3.run(URLClassPath.Java:530)
at Sun.misc.URLClassPath$3.run(URLClassPath.Java:520)
at Java.security.AccessController.doPrivileged(Native Method)
at Sun.misc.URLClassPath.getLoader(URLClassPath.Java:519)
at Sun.misc.URLClassPath.getLoader(URLClassPath.Java:492)
at Sun.misc.URLClassPath.getNextLoader(URLClassPath.Java:457)
at Sun.misc.URLClassPath.getResource(URLClassPath.Java:211)
at Java.net.URLClassLoader$1.run(URLClassLoader.Java:365)
at Java.net.URLClassLoader$1.run(URLClassLoader.Java:362)
at Java.security.AccessController.doPrivileged(Native Method)
at Java.net.URLClassLoader.findClass(URLClassLoader.Java:361)
at Java.lang.ClassLoader.loadClass(ClassLoader.Java:424)
at Sun.misc.Launcher$AppClassLoader.loadClass(Launcher.Java:331)
at Java.lang.ClassLoader.loadClass(ClassLoader.Java:357)
at Sun.launcher.LauncherHelper.checkAndLoadMain(LauncherHelper.Java:495)
Error: A JNI error has occurred, please check your installation and try again
Exception in thread "main"
Et voici mon fichier manifeste:
Manifest-Version: 1.0
Main-Class: Main
Puis les bibliothèques externes ajoutées à mon projet
Qu'est-ce que je fais mal??
Certains de vos fichiers JAR de dépendance sont des fichiers JAR signés. Par conséquent, lorsque vous combinez tous les fichiers dans un fichier JAR et que vous l'exécutez, la signature du fichier JAR signé ne correspond pas et vous obtenez donc l'exception de sécurité relative à la non correspondance des signatures.
Pour résoudre ce problème, vous devez d'abord identifier quels JAR de dépendance sont des JAR signés, puis les exclure. Selon que vous utilisiez MAVEN ou ANT, vous devez prendre la solution appropriée. Ci-dessous, vous pouvez en lire davantage ici , ici et ici .
Maven:
<plugin>
<groupId>org.Apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>2.6</version>
<executions>
<execution>
<id>unpack-dependencies</id>
<phase>package</phase>
<goals>
<goal>unpack-dependencies</goal>
</goals>
<configuration>
<excludeScope>system</excludeScope>
<excludes>META-INF/*.SF</excludes>
<excludes>META-INF/*.DSA</excludes>
<excludes>META-INF/*.RSA</excludes>
<excludeGroupIds>junit,org.mockito,org.hamcrest</excludeGroupIds>
<outputDirectory>${project.build.directory}/classes</outputDirectory>
</configuration>
</execution>
</executions>
</plugin>
ANT:
<jar destfile="app.jar" basedir="${classes.dir}">
<zipfileset excludes="META-INF/**/*" src="${lib.dir}/bcprov-jdk16-145.jar"></zipfileset>
<manifest>
<attribute name="Main-Class" value="app.Main"/>
</manifest>
</jar>
Mise à jour basée sur le commentaire d'OP:
"sqljdbc4.jar" était le JAR signé dans les bibliothèques externes de l'OP. Par conséquent, la méthode ci-dessus pour exclure systématiquement les fichiers liés à la signature tels que les fichiers .SF, .RSA ou .DES ou d’autres fichiers d’algorithmes est la meilleure façon de procéder.
Si ces fichiers de signature ne sont pas exclus, une exception de sécurité se produira en raison d'une incompatibilité de signature.
Comment savoir si un fichier JAR est signé ou non?: Si un fichier JAR contient des fichiers tels que des fichiers tels que .SF, .RSA ou .DES ou d'autres fichiers algorithmiques, il s'agit d'un fichier JAR signé.
Je mets l'extrait de plug-in dans pom.xml, mais le fichier jar généré contient toujours META-INF/BCKEY.DSA J'utilise Maven 3.6.0 et Java 1.8 build 191
Au lieu de supprimer le fichier META-INF, j'ai modifié la méthode dans la définition de l'artefact. J'ai supprimé la bibliothèque "extraite" de l'artefact et l'ai ajoutée à nouveau sous le nom "Mettre dans la racine de sortie".
De cette façon, la bibliothèque sera incorporée sans modification dans le nouveau fichier jar, ce qui, je suppose, est l’objectif de la signature de la bibliothèque ...
En passant, j'utilise aussi sqljdbc.jar.
Dans mon cas, je travaille avec un uber-jar via maven-shade-plugin et @ruhsuzbaykus answer ici était la solution. La stratégie semble très similaire à celle proposée par @hagrawal mais les exclusions sont ajoutées en tant que configuration de filtre de maven-shade-plugin.