Festlegen der Umgebung für ProcessBuilder
Ich habe ein seltsames problem mit der Einstellung der Linux-Umgebung von Java (1.6), speziell die variable "PATH".
Kurz gesagt, ich habe eine pipeline für das laufende native Prozesse, die verwendet java.lang.ProcessBuilder
. Der Benutzer kann Optional die environment-Variablen über eine HashMap
namens environment
:
ProcessBuilder pb = new ProcessBuilder(args);
Map<String, String> env = pb.environment();
if (environment != null)
env.putAll(environment);
Process process = pb.start();
Den env
variable wird richtig eingestellt, wenn ich dump es auf der Konsole, mit einem korrekten Wert für die variable PATH. Allerdings läuft der Prozess führt zu einer geworfen Exception
:
java.io.IOException: error=2, No such file or directory
Den gleichen Prozess gut läuft mit identischen Umgebungsvariablen, die in der terminal-shell. Um dies zu testen, lief ich Eclipse NACH der Einstellung der Umwelt in der Klemme. In diesem Fall ist der ProcessBuilder
Prozess korrekt läuft.
Also, was muss geschehen, dass die ProcessBuilder
ist nicht die Umgebung, die ich gesetzt, aber die aktuellen System-Umgebung statt.
Ich finde keine befriedigenden Antworten auf dieses problem online. Vielleicht ist dies ein OS-spezifisches Problem? Oder sonst etwas, das mir fehlt?
- Vielleicht versuchen sysout die variable PATH aus und poste es hier, vielleicht können wir Fleck etwas..
- Eine andere Sache zu beachten, der in Windows ist, dass, während der Fall von Umgebungsvariablen ist "in der Regel nicht wichtig" (Zitat der
System.getenv
javadoc), so dass Sie können callSystem.getenv("path")
oderSystem.getenv("PATH")
austauschbar mit ähnlichen Ergebnissen, dasselbe gilt nicht für das Feld der ProcessBuilder da dieMap
auf die direkt zugegriffen wird, anstatt durch eine spezielle getter, so dass Abweichungen in der groß-und Kleinschreibung führen Fehler... Hinweis: wenn Sie do wollen Sie den Weg von einem ProcessBuilder in Windows, verwendenenvironment.get("Path")
. - Den Tipp Gaben Sie sagen, verwenden des Path unter windows war erstaunlich !!! Ich verbrachte Wochen zusammen, da dieses problem in ProcessBuilder!! VIELEN DANK !!! 🙂 🙂
- gerne helfen... ich kann mich nicht erinnern, wie lange es vereitelt mich für: nicht ganz Wochen, aber lange genug, um frustrierend sein 🙂
Du musst angemeldet sein, um einen Kommentar abzugeben.
Ich glaube nicht, dass es ein bug ist, ich denke es ist ein problem mit Ihrem Verständnis für die Grenzen und Rollen der environment-Variablen im Spiel sind.
ProcessBuilder.environment()
enthält Umgebungsvariablen, werden "Prozess-lokalen", um die erzeugte Prozess. Sie sind nicht system-weit, - oder logon-breit, und Sie haben nicht einmal Einfluss auf die Umwelt, in die der ProcessBuilder ausgeführt wird.Den
ProcessBuilder.environment()
Karte enthält Prozess-lokale Variablen gesehen werden nur, indem der erzeugte Prozess. Offensichtlich eine Voraussetzung, um die erzeugte Verarbeitung sehen dieProcessBuilder.environment()
ist eine erfolgreiche laichen des Prozesses, das ist ein Punkt, den ich nicht denken, du bist immer noch zu.Soweit ich weiß, es ist nicht wirklich möglich (aus Java) zum ändern der aktuell laufende Prozess' WEG, der ist, was ich denke, Sie erwarten zu geschehen (oder in der Lage sein zu tun.) Also ich denke, man muss zeigen ProcessBuilder auf den vollständig qualifizierten Pfad zu der ausführbaren Datei, die Sie versuchen, zu starten (oder sicher sein, dass der PFAD richtig eingestellt wurde, bevor Sie selbst starten Sie die JVM, die Sie benutzen den ProcessBuilder, das ist, was du getan hast in Ihren 'Arbeits' - Szenario der Einstellung in das terminal vor dem Start der IDE).
ProcessBuilder
's-Prozess-lokalen Umgebungsvariablen, wenn es macht seine eigenen Anrufe zu anderen Prozessen? Das wäre eine geeignete Lösung für mich.Unter Linux:
In diesem Fall die
PATH
variable aktualisiert wird, als je die Notwendigkeit und die ausführbare Datei wird gesucht, im neuen$PATH
. Dieser arbeitete für mich auf Linux.Müssen Sie verstehen, dass die environment-Variablen sind lokal zu verarbeiten Kontexten. Einen neuen Prozess bekommt eine Kopie von der Eltern, die Umwelt, aber jede Kopie ist unabhängig. Veränderungen in der Eltern wirken sich nicht auf vorhandene Kinder (nur neue) und Veränderungen in der Kinder nicht auf die Eltern oder Kinder des Eltern.
In Ihrem Fall, den Java-Prozess erstellt child-Prozess und stellt eine modifizierte
PATH
variable in der untergeordneten Kontext. Dies hat keine Auswirkungen auf den Java-Prozess. Der Kind-Prozess ist nicht eine Schale, so wird es ignoriert diePATH
variable. Der Prozess wird direkt mit OS-services. Diese suchen Sie in den Kontext der Java-Prozess, der enthält die altenPATH
variable, es sei denn, Sie verändern die Umgebung, in der shell vor starten Sie den Java-Prozess.Zu beheben, haben Sie zwei Möglichkeiten:
Untersuchen die
PATH
variable in Java, die es aufgeteilt in Pfad-Elementen und suchen für die ausführbare Datei manuell. Sie können dann aufrufenProcessBuilder
mit dem absoluten Pfad und setzen Sie die neuePATH
in der Kind, Enkel den richtigen Weg.Rufen Sie eine shell zum starten des untergeordneten Prozesses. Die shell den Pfad (die Sie weitergeben können über die Umwelt).
Zweiten Fall funktioniert wie folgt:
PATH
."sh", "-c", "cmd args"
oder"cmd.exe", "/c", "cmd args"
)PATH
und führen Sie den entsprechenden Befehl.Den Nachteil, dass der zweite Fall ist, dass Sie haben, um richtig zu Flucht-und/oder Zitat die Argumente für den Befehl (
args
) oder Leerzeichen und andere Sonderzeichen zu Problemen führen kann.Eins ist klar, aus dem ProcessBuilder javadoc ist, dass man die Umgebungsvariablen mit der Umgebung () - Methode, und dann ändern der zurückgegebenen Karte. Alle nachfolgenden Prozess, der gestartet wird, dass ProcessBuilder Instanz müssen Sie Ihre änderungen.
Ich denke, du hast Recht. Die aktuell ausgeführte java-code wird nicht die Umgebungsvariablen, die Sie vorbereiten, für den untergeordneten Prozess ausgeführt werden. Sie könnte erstellen Sie eine temporäre ausführbare Datei oder Skript, das Sie übergeben können, die Variablen zu und haben Sie Ihr Programm auszuführen.
Dies scheint ein echtes Problem mit java und externe Prozesse
Folgendes auf windows 7 und java 7 (32bit)
produziert
was bedeutet, dass die Laufenden Programme Umwelt und die Teilprozesse Umgebung sollte eine path-variable, die hat genau den Wert "xbox" (z.B. Unsinn, es gibt kein Verzeichnis mit dem Namen xbox irgendwo auf meinem pc)
nur für das Protokoll:
ergibt genau das gleiche Ergebnis.
wenn ich
mit diesem process builder und Umgebung, die ich bekommen
dies ist die (Deutsche) Ausgabe von
Das gleiche passiert, wenn ich
Und beachten Sie, dass meine Umgebung ist so klein weil ich durch die native Umgebung. Das bedeutet, dass das ganze Programm hat genau die beiden environment-Variablen.