59 votes

Masquer l'entrée sur la ligne de commande

Je sais que les interfaces de ligne de commande comme Git et d'autres sont capables de masquer les entrées d'un utilisateur (utile pour les mots de passe). Existe-t-il un moyen de programmer cela en Java ? Je prends le mot de passe d'un utilisateur et je voudrais que son entrée soit "cachée" sur cette ligne particulière (mais pas sur toutes les autres). Voici mon code (bien que je doute qu'il soit utile...)

try (Scanner input = new Scanner(System.in)) {
  //I'm guessing it'd probably be some property you set on the scanner or System.in right here...
  System.out.print("Please input the password for " + name + ": ");
  password = input.nextLine();
}

87voto

adarshr Points 25912

Essayez java.io.Console.readPassword . Vous devrez cependant utiliser au moins Java 6.

   /**
    * Reads a password or passphrase from the console with echoing disabled
    *
    * @throws IOError
    *         If an I/O error occurs.
    *
    * @return  A character array containing the password or passphrase read
    *          from the console, not including any line-termination characters,
    *          or <tt>null</tt> if an end of stream has been reached.
    */
    public char[] readPassword() {
        return readPassword("");
    }

Attention cependant, cette ne fonctionne pas avec la console Eclipse. Vous devez exécuter le programme à partir d'un fichier vrai console/shell/terminal/prompt pour pouvoir le tester.

12voto

Vijay Shanker Points 1580

Oui, c'est possible. C'est ce qu'on appelle le masquage des entrées en ligne de commande. Vous pouvez l'implémenter facilement.

Vous pouvez utiliser un thread séparé pour effacer les caractères échos lors de leur saisie et les remplacer par des astérisques. Pour ce faire, vous utilisez la classe EraserThread présentée ci-dessous.

import java.io.*;

class EraserThread implements Runnable {
   private boolean stop;

   /**
    *@param The prompt displayed to the user
    */
   public EraserThread(String prompt) {
       System.out.print(prompt);
   }

   /**
    * Begin masking...display asterisks (*)
    */
   public void run () {
      stop = true;
      while (stop) {
         System.out.print("\010*");
     try {
        Thread.currentThread().sleep(1);
         } catch(InterruptedException ie) {
            ie.printStackTrace();
         }
      }
   }

   /**
    * Instruct the thread to stop masking
    */
   public void stopMasking() {
      this.stop = false;
   }
}

En utilisant ce fil

public class PasswordField {

   /**
    *@param prompt The prompt to display to the user
    *@return The password as entered by the user
    */
   public static String readPassword (String prompt) {
      EraserThread et = new EraserThread(prompt);
      Thread mask = new Thread(et);
      mask.start();

      BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
      String password = "";

      try {
         password = in.readLine();
      } catch (IOException ioe) {
        ioe.printStackTrace();
      }
      // stop masking
      et.stopMasking();
      // return the password entered by the user
      return password;
   }
}

Ce lien discuter en détail.

8voto

Brian Agnew Points 143181

JLine 2 peut être intéressant. Outre le masquage des caractères, il permet de compléter la ligne de commande, de l'éditer et de créer un historique. Il est donc très utile pour un outil Java basé sur la CLI.

Pour masquer votre contribution :

String password = new jline.ConsoleReader().readLine(new Character('*'));

3voto

Dhruv Gairola Points 4448

Il y a :

Console cons;
char[] passwd;
if ((cons = System.console()) != null &&
    (passwd = cons.readPassword("[%s]", "Password:")) != null) {
    ...
    java.util.Arrays.fill(passwd, ' ');
}

source

mais je ne pense pas que cela fonctionne avec un IDE comme Eclipse car le programme est exécuté en tant que processus d'arrière-plan plutôt qu'un processus de niveau supérieur avec une fenêtre de console.

Une autre approche consiste à utiliser le JPasswordField avec l'accompagnement actionPerformed méthode :

public void actionPerformed(ActionEvent e) {
    ...
    char [] p = pwdField.getPassword();
}

source

0voto

rlinden Points 1278

La classe Console a une méthode readPassword() qui pourrait résoudre votre problème.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X