Gibt es ein Tool zu entdecken, wenn die gleiche Klasse in mehreren Gläsern in dem Classpath existiert?

StackOverflow https://stackoverflow.com/questions/135971

  •  02-07-2019
  •  | 
  •  

Frage

Wenn Sie zwei Gläser in Ihrem Classpath haben, die unterschiedliche Versionen derselben Klasse enthalten, die Classpath, um kritisch wird.

Ich bin auf der Suche nach einem Werkzeug, das und Flagge solcher potenziellen Konflikte in einem bestimmten Classpath oder einen Satz von Ordnern erfassen kann.

Auf jeden Fall ein Skript, das beginnt:

classes=`mktemp`
for i in `find . -name "*.jar"`
do
    echo "File: $i" > $classes
    jar tf $i > $classes
    ...
done

mit einigen cleveren Art / uniq / diff / grep / awk später hat Potenzial, aber ich frage mich, ob jemand von bestehenden Lösungen kennt.

War es hilfreich?

Lösung

Die Tattletale Tool von JBoss ist ein weiterer Kandidat: „Stelle, wenn eine Klasse / Paket in mehreren befindet JAR-Dateien "

Andere Tipps

Sieht aus wie jarfish wird tun, was Sie mit dem „Betrogene“ Befehl wollen .

Ich denke, es ist nicht zu hart wäre, ein Werkzeug für die Sie sich selbst zu schreiben.

Sie können die Classpath-Einträge mit System.getProperty ( "java.class.path") erhalten;

Und dann zu Fuß durch die Gläser, Reißverschlüsse oder Verzeichnisse dort aufgelistet und sammeln Sie alle Informationen über die Klassen und findout diejenigen, die Probleme verursachen könnten.

Diese Aufgabe würde 1 oder 2 Tage höchstens. Dann können Sie diese Klasse direkt in Ihrer Anwendung laden und einen Bericht erstellen.

Wahrscheinlich java.class.path Show Eigenschaft wird nicht alle Klassen, wenn Sie in irgendeiner Infrastruktur mit komplexen benutzerdefinierten Klasse Laden laufen (zum Beispiel einmal sah ich eine App, die die Klassen aus dem LDAP laden), aber es funktionieren würde sicherlich für die meisten die Fälle.

Hier ist ein Werkzeug, das Sie vielleicht nützlich finden, ich habe es nie meine selbst verwenden, aber es versuchen und lassen Sie uns wissen, das Ergebnis.

http://www.jgoodies.com/freeware/jpathreport/features.html

Wenn Sie vorhaben, Ihr eigenes Werkzeug zu schaffen, hier ist der Code, den ich für den gleichen Shell-Skript vor geschrieben verwenden, aber, dass ich auf meinem Windows-Rechner verwenden. Es läuft schneller, wenn es Tonnen von JAR-Dateien.

Sie können es es nutzen und verändern so statt rekursiv ein Verzeichnis gehen, den Klassenpfad lesen und das .class Zeitattribut vergleichen.

Es gibt eine Command Klasse Sie Unterklasse kann, wenn nötig, ich war in der -execute Option denken an „finden“

Das mein eigener Code, so dass es nicht beabsichtigt war „Produktion bereit“ zu sein, nur um die Arbeit zu tun.

import java.io.*;
import java.util.zip.*;


public class ListZipContent{
    public static void main( String [] args ) throws IOException {
        System.out.println( "start " + new java.util.Date() );
        String pattern = args.length == 1 ? args[0] : "OracleDriver.class";// Guess which class I was looking for :) 
        File file = new File(".");
        FileFilter fileFilter = new FileFilter(){
            public boolean accept( File file ){
                return file.isDirectory() || file.getName().endsWith( "jar" );
            }
        };
        Command command = new Command( pattern );
        executeRecursively( command, file, fileFilter );
        System.out.println( "finish  " + new java.util.Date() );
    }
    private static void executeRecursively( Command command, File dir , FileFilter filter ) throws IOException {
        if( !dir.isDirectory() ){
            System.out.println( "not a directory " + dir );
            return;
        }
        for( File file : dir.listFiles( filter ) ){
            if( file.isDirectory()){
                executeRecursively( command,file , filter );
            }else{
                command.executeOn( file );
            }
        }
    }
}
class Command {

    private String pattern;
    public Command( String pattern ){
        this.pattern = pattern;
    }

    public void executeOn( File file ) throws IOException {
        if( pattern == null ) { 
            System.out.println( "Pattern is null ");
            return;
        }

        String fileName = file.getName();
        boolean jarNameAlreadyPrinted = false;

        ZipInputStream zis = null;
        try{
            zis = new ZipInputStream( new FileInputStream( file ) );

            ZipEntry ze;
            while(( ze = zis.getNextEntry() ) != null ) {
                if( ze.getName().endsWith( pattern )){
                    if( !jarNameAlreadyPrinted ){
                        System.out.println("Contents of: " + file.getCanonicalPath()  );
                        jarNameAlreadyPrinted = true;
                    }
                    System.out.println( "    " + ze.getName() );
                }
                zis.closeEntry();
            }
        }finally{
            if( zis != null ) try {
                zis.close();
            }catch( Throwable t ){}
        }
    }
}

Ich hoffe, das hilft.

Classpath Helper ist ein Eclipse-Plug-in, das ein wenig hilft.

Wenn Sie nicht mögen das Herunterladen und die Installation von Sachen Sie können diese eine Zeile Befehl verwenden, um jar Konflikte mit Standard-GNU-Tools zu finden. Es ist rudimentär, aber man kann es erweitern, wie Sie werden.

ls *.jar | xargs -n1 -iFILE unzip -l FILE | grep class | sed "s,.* ,," | tr "/" "." | sort | uniq -d | xargs -n1 -iCLASS grep -l CLASS *.jar | sort -u

(es ist ein bisschen langsam zu laufen, wenn Sie eine Menge Gläser haben)

Erläuterung: Es listet alle Dateien in allen Gläsern, greps für Klassendateien, findet Betrogenen, dann die ursprünglichen Gläser greps zu sehen, wo sie erschienen. Es könnte mit einem komplizierteren Skript effizienter gemacht werden.

jarclassfinder ist eine weitere Eclipse-Plugin Option

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top