Comment redémarrer une application Java AWT? J'ai un bouton auquel j'ai attaché un gestionnaire d'événements. Quel code dois-je utiliser pour redémarrer l'application?
Je veux faire la même chose que Application.Restart()
dans une application C #.
java
restart
application-restart
Azfar Niaz
la source
la source
Réponses:
Bien entendu, il est possible de redémarrer une application Java.
La méthode suivante montre un moyen de redémarrer une application Java:
En gros, il fait ce qui suit:
MyClassInTheJar
classe pour trouver l'emplacement du pot lui-même)la source
System.exit(0)
termine le processus enfant a la même réponse que si cette réponse fonctionne vraiment et pourquoi. Si vous ne pouvez pas fournir une explication raisonnable avec votre réponse, vous avez fait un mauvais travail. Une réponse qui fournit plus de questions qu'elle ne répond n'est pas un exemple de réponse approfondie. Les bonnes réponses ne montrent pas seulement le code, mais expliquent également comment et pourquoi ils fonctionnent, quels sont les inconvénients et quelles sont les alternatives. Vous n'avez même pas essayé de couvrir ces choses.Dédié à tous ceux qui disent que c'est impossible.
Ce programme collecte toutes les informations disponibles pour reconstruire la ligne de commande d'origine. Ensuite, il le lance et comme il s'agit de la même commande, votre application démarre une seconde fois. Ensuite, nous quittons le programme d'origine, le programme enfant reste en cours d'exécution (même sous Linux) et fait exactement la même chose.
AVERTISSEMENT : si vous exécutez ceci, sachez qu'il ne s'arrête jamais de créer de nouveaux processus, similaires à une bombe à fourche .
la source
ManagementFactory.getRuntimeMXBean().getInputArguments()
ne vous donnera que les arguments d'entrée passés à la JVM. Il manque les paramètres passés à votre application. par exemplejava -jar start.jar -MISSED_PARAM=true
. Sur un jvm oracle, vous pouvez récupérer ces paramètres à l'aide deSystem.getProperty("sun.java.command")
.ProcessBuilder
etinheritIO()
, la machine virtuelle enfant peut être démarrée de manière à ce que la machine virtuelle parente se termine.En gros, vous ne pouvez pas. Du moins pas de manière fiable. Cependant, vous ne devriez pas en avoir besoin.
Le ne peut pas se séparer
Pour redémarrer un programme Java, vous devez redémarrer la JVM. Pour redémarrer la JVM, vous devez
Localisez le
java
lanceur utilisé. Vous pouvez essayer avecSystem.getProperty("java.home")
mais il n'y a aucune garantie que cela pointera réellement vers le lanceur qui a été utilisé pour lancer votre application. (La valeur renvoyée peut ne pas pointer vers le JRE utilisé pour lancer l'application ou elle peut avoir été remplacée par-Djava.home
.)Vous voulez sans doute pour honorer la mémoire des paramètres d' origine etc (
-Xmx
,-Xms
...) de sorte que vous devez déterminer les paramètres où utilisé pour démarrer la première machine virtuelle Java. Vous pouvez essayer d'utiliser,ManagementFactory.getRuntimeMXBean().getInputArguments()
mais rien ne garantit que cela reflétera les paramètres utilisés. Ceci est même précisé dans la documentation de cette méthode:Si votre programme lit l'entrée du
Standard.in
stdin d'origine, il sera perdu lors du redémarrage.Beaucoup de ces astuces et hacks échoueront en présence d'un fichier
SecurityManager
.La partie ne devrait pas avoir besoin
Je vous recommande de concevoir votre application de manière à ce qu'il soit facile de tout nettoyer et ensuite de créer une nouvelle instance de votre classe "principale".
De nombreuses applications sont conçues pour ne rien faire d'autre que créer une instance dans la méthode main:
En utilisant ce modèle, il devrait être assez facile de faire quelque chose comme:
et laissez
launch()
return true si et seulement si l'application a été arrêtée de telle sorte qu'elle doit être redémarrée.la source
java
! Vous oubliez que Java est une spécification de langage, pas un programme. Et si j'exécute votre programme en utilisant un autre jvm, comme kaffe par exemple? Mis à jour ma réponse de toute façon :-)À proprement parler, un programme Java ne peut pas redémarrer lui-même car pour ce faire, il doit tuer la JVM dans laquelle il est en cours d'exécution, puis la redémarrer, mais une fois que la JVM n'est plus en cours d'exécution (tuée), aucune action ne peut être entreprise.
Vous pouvez faire quelques astuces avec des chargeurs de classes personnalisés pour charger, emballer et redémarrer les composants AWT, mais cela causera probablement beaucoup de maux de tête en ce qui concerne la boucle d'événements de l'interface graphique.
En fonction de la façon dont l'application est lancée, vous pouvez démarrer la JVM dans un script wrapper qui contient une boucle do / while, qui se poursuit pendant que la JVM se ferme avec un code particulier, puis l'application AWT devra appeler
System.exit(RESTART_CODE)
. Par exemple, dans le pseudocode de script:L'application AWT doit quitter la JVM avec autre chose que RESTART_CODE lors d'une terminaison "normale" qui ne nécessite pas de redémarrage.
la source
JavaApplicationStub
... Je ne sais pas s'il existe un moyen facile de contourner cela.Eclipse redémarre généralement après l'installation d'un plugin. Ils le font à l'aide d'un wrapper eclipse.exe (application de lancement) pour Windows. Cette application exécute le jar principal de l'exécuteur eclipse et si l'application java eclipse se termine par un code de relance, eclipse.exe redémarre l'atelier. Vous pouvez créer un morceau similaire de code natif, de script shell ou d'un autre wrapper de code java pour effectuer le redémarrage.
la source
les fenêtres
/ min pour démarrer le script dans la fenêtre réduite
^ & quitter pour fermer la fenêtre cmd après avoir terminé
un exemple de script cmd pourrait être
dormir 10 dormir pendant 10 secondes
la source
Si vous avez vraiment besoin de redémarrer votre application, vous pouvez écrire une application distincte pour la démarrer ...
Cette page fournit de nombreux exemples différents pour différents scénarios:
http://www.rgagnon.com/javadetails/java-0014.html
la source
Bien que cette question soit ancienne et répondue, je suis tombé sur un problème avec certaines des solutions et j'ai décidé d'ajouter ma suggestion dans le mélange.
Le problème avec certaines des solutions est qu'elles créent une seule chaîne de commande. Cela crée des problèmes lorsque certains paramètres contiennent des espaces, en particulier java.home .
Par exemple, sur Windows, la ligne
Peut renvoyer quelque chose comme ceci:
C:\Program Files\Java\jre7\bin\java
Cette chaîne doit être placée entre guillemets ou échappée en raison de l'espace dans
Program Files
. Pas un gros problème, mais quelque peu ennuyeux et sujet aux erreurs, en particulier dans les applications multiplateformes.Par conséquent, ma solution construit la commande comme un tableau de commandes:
la source
Je faisais moi-même des recherches sur le sujet lorsque je suis tombé sur cette question.
Indépendamment du fait que la réponse est déjà acceptée, je voudrais toujours proposer une approche alternative pour l'exhaustivité. Plus précisément, Apache Ant a servi de solution très flexible.
Fondamentalement, tout se résume à un fichier de script Ant avec une seule tâche d'exécution Java (voir ici et ici ) appelée à partir d'un code Java (voir ici ). Ce code Java, qui peut être un lancement de méthode , pourrait faire partie de l'application qui doit être redémarrée. L'application doit avoir une dépendance sur la bibliothèque Apache Ant (jar).
Chaque fois que l'application doit être redémarrée, elle doit appeler le lancement de méthode et quitter la machine virtuelle. La tâche Ant java doit avoir les options fork et spawn définies sur true.
Voici un exemple de script Ant:
Le code de la méthode de lancement peut ressembler à ceci:
}
Une chose très pratique ici est que le même script est utilisé pour le démarrage initial de l'application ainsi que pour les redémarrages.
la source
Il suffit d'ajouter des informations qui ne sont pas présentes dans d'autres réponses.
Si procfs
/proc/self/cmdline
est disponibleSi vous exécutez dans un environnement qui fournit procfs et que le
/proc
système de fichiers est donc disponible (ce qui signifie que ce n'est pas une solution portable), vous pouvez faire lire Java/proc/self/cmdline
afin de redémarrer lui-même, comme ceci:Sur les systèmes avec
/proc/self/cmdline
disponibles, c'est probablement la manière la plus élégante de "redémarrer" le processus Java actuel à partir de Java. Aucun JNI impliqué, et aucune estimation des chemins et des choses requises. Cela prendra également en charge toutes les options JVM transmises aujava
binaire. La ligne de commande sera exactement identique à celle du processus JVM actuel.De nombreux systèmes UNIX, y compris GNU / Linux (y compris Android) ont de nos jours des procfs. Cependant, sur certains comme FreeBSD, il est obsolète et est en cours de suppression. Mac OS X est une exception dans le sens où il n'a pas de procfs . Windows n'a pas non plus procfs . Cygwin a procfs mais il est invisible pour Java car il n'est visible que pour les applications utilisant les DLL Cygwin au lieu des appels système Windows, et Java ne connaît pas Cygwin.
N'oubliez pas d'utiliser
ProcessBuilder.inheritIO()
La valeur par défaut est que
stdin
/stdout
/stderr
(en Java appeléSystem.in
/System.out
/System.err
) du processus démarré est défini sur des canaux qui permettent au processus en cours d'exécution de communiquer avec le processus nouvellement démarré. Si vous souhaitez redémarrer le processus en cours, ce n'est probablement pas ce que vous souhaitez . Au lieu de cela, vous voudriez questdin
/stdout
/stderr
soient les mêmes que ceux de la VM actuelle. C'est ce qu'on appelle hérité . Vous pouvez le faire en appelantinheritIO()
votreProcessBuilder
instance.Pitfall sur Windows
Un cas d'utilisation fréquent d'une
restart()
fonction est de redémarrer l'application après une mise à jour. La dernière fois que j'ai essayé cela sous Windows, c'était problématique. Lorsqu'elle a remplacé le.jar
fichier de l'application par la nouvelle version, l'application a commencé à se comporter mal et à donner des exceptions au.jar
fichier. Je dis juste, au cas où ce serait votre cas d'utilisation. À l'époque, j'ai résolu le problème en enveloppant l'application dans un fichier de commandes et en utilisant une valeur de retour magique à partir deSystem.exit()
laquelle j'ai interrogé dans le fichier de commandes et que le fichier de commandes redémarre l'application à la place.la source
Ancienne question et tout ça. Mais c'est encore une autre façon qui offre certains avantages.
Sous Windows, vous pouvez demander au planificateur de tâches de redémarrer votre application pour vous. Cela présente l'avantage d'attendre un laps de temps spécifique avant de redémarrer l'application. Vous pouvez accéder au gestionnaire de tâches et supprimer la tâche et elle cesse de se répéter.
la source
Similaire à la réponse ` ` améliorée ' ' de Yoda , mais avec de nouvelles améliorations (à la fois fonctionnelles, lisibles et testables). Il est maintenant sûr de s'exécuter et redémarre autant de fois que le nombre d'arguments du programme donné.
JAVA_TOOL_OPTIONS
options.V1.1 Bugfix: pointeur nul si JAVA_TOOL_OPTIONS n'est pas défini
Exemple:
la source
Je suppose que vous ne voulez pas vraiment arrêter l'application, mais la "redémarrer". Pour cela, vous pouvez utiliser ceci et ajouter votre "Reset" avant le sommeil et après la fenêtre invisible.
la source