Wie füge ich Gläser in ein Groovy-Skript ein?[Duplikat]
Frage
Auf diese Frage gibt es hier bereits eine Antwort:
Ich habe ein tolles Skript, das eine Bibliothek in einem Glas benötigt.Wie füge ich das zum Klassenpfad hinzu?Ich möchte, dass das Skript ausführbar ist, also verwende ich #!/usr/bin/env groovy
ganz oben in meinem Skript.
Lösung
Wenn Sie wirklich haben Sie können auch eine JAR zur Laufzeit laden mit:
this.getClass().classLoader.rootLoader.addURL(new File("file.jar").toURL())
Andere Tipps
ein starkes Skript mit #!/usr/bin/env groovy
Start hat eine sehr wichtige Einschränkung - keine zusätzlichen Argumente hinzugefügt werden können, Nein Classpath konfiguriert werden kann, kein fließendes groovy mit definiert oder in debug.. Dies ist kein groovy Problem, aber eine Einschränkung, wie die shebang (#!
) arbeitet -. alle weiteren Argumente als einziges Argument behandelt werden, so #!/usr/bin/env groovy -d
/usr/bin/env
sagt den Befehl groovy -d
Rathen dann groovy
mit einem Argument von d
ausführen
Es gibt eine Abhilfe für das Problem, das Bootstrapping groovy mit bash im groovy Skript handelt.
#!/bin/bash
//usr/bin/env groovy -cp extra.jar:spring.jar:etc.jar -d -Dlog4j.configuration=file:/etc/myapp/log4j.xml "$0" $@; exit $?
import org.springframework.class.from.jar
//other groovy code
println 'Hello'
die Magie passiert in den ersten beiden Zeilen All. Die erste Zeile sagt uns, dass dies ein bash
Skript. bash
beginnt zu laufen und sieht die erste Zeile. In bash
ist #
für Kommentare und //
kollabiert /
welches das Root-Verzeichnis. So wird bash
/usr/bin/env groovy -cp extra.jar:spring.jar:etc.jar -d -Dlog4j.configuration=file:/etc/myapp/log4j.xml "$0" $@
laufen, die mit allen gewünschten Argumente groovy beginnt. Der "$0"
ist der Weg zu unserem Skript und $@
sind die Argumente. Jetzt groovy läuft und es ignoriert die ersten beiden Zeilen und sieht unsere groovy Skript und tritt dann zurück zu bash
. bash
dann beendet (exit $?1
) mit dem Statuscode von groovy.
Sie können die Gläser zu $HOME/.groovy/lib hinzufügen
My Favorite Art und Weise, dies zu tun ist mit Groovy Trauben. Diese greifen die Maven Zentrales Repository, laden Sie die referenzierten Glas, und es dann auf dem Classpath setzen. Dann können Sie die Bibliothek wie jede andere Bibliothek verwenden. Die Syntax ist wirklich einfach:
@Grab(group='com.google.collections', module='google-collections', version='1.0')
Sie können weitere Details lesen Sie hier . Ein großer Vorteil ist, dass Sie nicht brauchen, um Ihre Abhängigkeiten zu verteilen, wenn Sie Ihr Skript zu verteilen. Der einzige Nachteil dieser Methode ist, dass das Glas in der Maven-Repository sein muss.
Sie können auch Groovy Grape ausprobieren. Damit können Sie Anmerkungen verwenden, um die Classpath zu ändern. Seine experimentellen gerade jetzt, aber ziemlich cool. Siehe docs.groovy-lang.org/.../grape
Das gleiche, wie Sie es in Java.
Dies ist ein Beispiel einer MySQL-Statusüberwachung Skript ausgeführt wird. mysql.jar enthält den MySQL-Anschluss, die ich von Skript status.groovy nennen.
groovy -cp mysql.jar status.groovy CT1
Im Folgenden finden Sie eine Kombination aus Patrick Lösung , Maarteen Boekhold Lösung und Kommentar des foozbar, die mit Linux und Cygwin funktioniert:
#!/bin/bash
// 2>/dev/null; SCRIPT_DIR="$( cd "$( dirname "$0" )" && pwd )"
// 2>/dev/null; OPTS="-cp $SCRIPT_DIR/lib/extra.jar:$SCRIPT_DIR/lib/spring.jar"
// 2>/dev/null; OPTS="$OPTS -d"
// 2>/dev/null; OPTS="$OPTS -Dlog4j.configuration=file:/etc/myapp/log4j.xml"
// 2>/dev/null; exec groovy $OPTS "$0" "$@"; exit $?
import org.springframework.class.from.jar
//other groovy code
println 'Hello'
Wie es funktioniert:
-
//
ist ein gültiger groovy Kommentar, so der bash alle Befehle werden von Groovy ignoriert. -
//
einen Fehler zurück, aber der Fehlerausgang wird umgeleitet/dev/null
und wird deshalb nicht angezeigt. - bash führt Befehle nach einem Semikolon, obwohl der vorherige Befehl fehlgeschlagen.
-
exec
ersetzt das aktuelle Programm im aktuellen Prozess ohne einen neuen Prozess gabeln. So groovy Läufe innerhalb des ursprünglichen Skript-Prozesses (ps
zeigt den Prozess als das Skript anstatt die groovy ausführbaren) - Die
exit $?
Anweisung nachexec groovy
bash verhindert versuchen, den Rest des Skripts als Bash-Skript zu interpretieren, und bewahrt auch den Return-Code aus dem groovy Skript.
Das oben gezeigte bash Trick ist bequemer in einigen Fällen als href="https://stackoverflow.com/a/306168/106189">, weil Sie regelmäßig Import-Anweisungen innerhalb der verwenden können Skript. Mit dem RootLoader Trick zwingen Sie alle Klassen mit Reflexion zu laden. Das ist in Ordnung in einigen Situationen (zB wenn Sie benötigen einen JDBC-Treiber laden), aber unbequem in anderen.
Wenn Sie wissen, dass Ihr Skript wird nie auf Cygwin ausgeführt werden, dann Patrick oder Maarteen-Lösung verwendet, wird in eine etwas bessere Leistung wahrscheinlich dazu führen, weil sie den Aufwand für die Erzeugung und das Wegwerfen einen Fehler zu vermeiden.
Hinzufügen von seiner Antwort auf @Patrick, die mir sehr geholfen, ich einen anderen Trick vor kurzem entdeckt.
Wenn Sie viele Gläser auf dem Classpath hinzufügen alle auf einer Linie, können die Dinge ziemlich unlesbar werden. Aber Sie können die folgende tun!
#!/bin/bash
//bin/true && OPTS="-cp blah.jar -Dmyopt=value"
//bin/true && OPTS="$OPTS -Dmoreopts=value2"
//usr/bin/env groovy $OPTS "$0" $@; exit $?
println "inside my groovy script"
Lassen Sie Ihrer Fantasie freien Lauf, wie komplex eine Befehlszeile Sie auf diese Weise in handliche Stücke zerlegen kann
Maarten
Wenn Sie wollen, es zu benutzen direkt vor den import
Erklärungen ist es möglich, wie diese :):
// printEmployees.groovy
this.class.classLoader.rootLoader.addURL(
new URL("file:///C:/app/Dustin/product/11.1.0/db_1/jdbc/lib/ojdbc6.jar"))
import groovy.sql.Sql
sql = Sql.newInstance("jdbc:oracle:thin:@localhost:1521:orcl", "hr", "hr",
"oracle.jdbc.pool.OracleDataSource")
sql.eachRow("SELECT employee_id, last_name, first_name FROM employees")
{
println "The employee's name is ${it.first_name} ${it.last_name}."
}
Genommen von diesem javaworld.com Artikel .