martedì 18 agosto 2015

MASCHERARE INPUT DA TASTIERA IN CONSOLE (DOTNET)

I vari ambienti di sviluppo ci hanno ormai assuefatto alla costruzione di interfacce grafiche per realizzare le più comuni finestre di dialogo di login ai nostri programmi. Quello che vogliamo fare oggi è costruire una interfaccia di login a riga di comando mascherando la digitazione della password.

Ho deciso di scrivere questo articolo in seguito all'arrivo dell'ennesimo stagista di passaggio nella nostra azienda, posto davanti al problema di scrivere un piccolo toolkit a riga di comando ha pensato bene di partire dal login utente. Quando è arrivato il momento di vedere i progressi della giornata è stata una sorpresa vedere come l'inserimento di utente e password fosse del tutto lasciato visibile.

Il bello di costruire una interfaccia grafica con un ambiente di sviluppo grafico consiste nell'impostare una textbox per mascherare l'input della tastiera mostrando gli adorati caratteri asterisco al posto di quelli della nostra password super segreta. 

Quando si lavora con una interfaccia a riga di comando dobbiamo utilizzare la classe Console la quale ci mette a disposizione metodi per la lettura e scrittura sul prompt dei comandi; principalmente abbiamo tre metodi principali: WriteLine, ReadLine e ReadKey.
Il metodo WriteLine permette di scrivere una porzione di testo sulla console, il metodo ReadLine permette di leggere la digitazione dell'utente fino alla pressione del tasto INVIO(ENTER), il metodo ReadKey permette di leggere la pressione di un singolo tasto. Quest'ultimo metodo è proprio quello di cui abbiamo bisogno per mascherare il nostro input da tastiera, andando ad utilizzarlo nella forma ReadKey(true).

Vediamo un esempio molto semplice di come è possibile mascherare l'input sostituendo il carattere asterisco (*):
static void Main(string[] args)
{
    ConsoleKeyInfo key;
    StringBuilder password;
    password = new StringBuilder();
    key = Console.ReadKey(true);
    while (key.Key != ConsoleKey.Enter)
    {
        password.Append(key.KeyChar);
        Console.Write("*");
        key = Console.ReadKey(true);
    }
    Console.WriteLine("\n"+password.ToString());
    Console.ReadKey();
}

L'esempio sopra riportato chiaramente è una porzione di codice grezza e lasciata libera per il programma ma ci permette di testare immediatamente la funzionalità del metodo ReadKey(true), se volessimo incapsulare il codice in una funzione maggiormente riutilizzabile potremmo optare per questa versione:
public static String ConsoleReadPassword(String mask = "*", ConsoleKey endKey = ConsoleKey.Enter )
{
    ConsoleKeyInfo key;
    StringBuilder password;
    password = new StringBuilder();
    key = Console.ReadKey(true);
    while (key.Key != endKey)
    {
        password.Append(key.KeyChar);
        Console.Write(mask);
        key = Console.ReadKey(true);
    }
    Console.WriteLine("");
    return password.ToString();
}

Costruita in questo modo la nostra funzione inserirà di default il carattere asterisco al posto della digitazione utente e terminerà alla pressione del tasto invio(enter), tuttavia per come è stata scritta è possibile modificarne le caratteristiche agendo sui parametri.

A questo punto per ottenere la password è sufficiente chiamare la nostra nuova funzione:
static void Main(string[] args)
{
    String username;
    String password;
    Console.Write("username: ");
    username = Console.ReadLine();
    Console.Write("password: ");
    password = ConsoleReadPassword();
    [...]
}

La prossima volta che dobbiamo scrivere un login a riga di comando adesso non sarà più un problema leggere la digitazione della password da tastiera.

Nessun commento:

Posta un commento