Visualizzazione dei risultati da 1 a 10 su 16

Hybrid View

  1. #1
    Quote Originariamente inviata da andbin Visualizza il messaggio
    Perfetto proprio no! Ci sono svariate cose che non sono particolarmente buone (es. il catch che ritorna null).
    Ma poi scusa ... che te ne fai di una classe che ha tutto private e nessun metodo "pubblico" ??
    Se il codice dovesse intopparsi o qualcuno dovesse farlo intoppare apposta con null non sarebbe possibile risalire alla causa dell'intoppo. Quando si tenta di acherare la prima cosa che si fa è mandare in eccezione il programma. Studiando le eccezioni si possono sapere informazioni relative alla classe. Se getInstance() non richiedesse try/catch non userei la gestione delle eccezioni.
    Hai ragione sul discorso dei metodi, devo mettere public per poterli usare.
    Voglio che nel file in cui vado a salvare le password degli utenti queste ultime non siano visibili in chiaro.
    Più pratica in futuro...

  2. #2
    Quote Originariamente inviata da andbin Visualizza il messaggio
    Il "minimo" per fare la cosa corretta e un pochino pulita (ma si potrebbe fare ancora meglio!) può essere questo, scritto e provato al volo:

    codice:
    public class DigestUtils {
        private DigestUtils() {}
    
        public static String md5Hex(String str) throws NoSuchAlgorithmException {
            MessageDigest md = MessageDigest.getInstance("MD5");
            byte[] digest = md.digest(utf8Bytes(str));
            BigInteger number = new BigInteger(1, digest);
            return String.format("%032x", number);
        }
    
        private static byte[] utf8Bytes(String str) {
            try {
                return str.getBytes("UTF-8");
            } catch (UnsupportedEncodingException e) {
                throw new Error("Grave error, UTF-8 not supported!");
            }
        }
    }
    Cosa significa “%032x”?
    Cosa significa “1”?
    Perché semplicemente non “BigInteger(digest)”?
    Si converte tutto in Byte perché digest() vuole così, giusto?
    Farei questa modifica:
    codice:
    package web1;
    
    import java.io.UnsupportedEncodingException;
    import java.math.BigInteger;
    import java.security.MessageDigest;
    import java.security.NoSuchAlgorithmException;
    
    public class FromStringToHash {
    
        private String Code;
        private String PreCode;
        private String HashText;
    
        public void FromStringToHash(String Code, String PreCode){
            this.Code = Code;
            this.PreCode = PreCode;
        }
    
        public void FromStringToHash(String Code){
            this.Code = Code;
            this.PreCode = "";
        }
    
        public static String hashConvert(String Password, String HashFunction) throws NoSuchAlgorithmException {
            MessageDigest md = MessageDigest.getInstance(HashFunction);
            byte[] digest = md.digest(utf8Bytes(Password));
            BigInteger number = new BigInteger(1, digest);
            return String.format("%032x", number);
        }
    
        private static byte[] utf8Bytes(String str) {
            try {
                return str.getBytes("UTF-8");
            } catch (UnsupportedEncodingException e) {
                throw new Error("Errore grave, UTF-8 non supportato!");
            }
        }
    
        public String combineString(String a, String b) {
            try {
                StringBuilder sb = new StringBuilder("");
                sb.append(a);
                sb.append(b);
                return sb.toString();
            }catch(Exception e){
                throw new RuntimeException(e);
            }
        }
    
        public String getHashText() {
            try {
                if(this.PreCode.equals("")){
                    // Vecchie versioni di Tomcat
    String HF = "MD5";
                    HashText = hashConvert(this.Code, HF);
                    return HashText;
                }else{
                    // Nuove versioni di Tomcat
    String HF = "SHA3-512";
                    HashText = hashConvert(combineString(hashConvert(this.Code,HF), hashConvert(this.PreCode,HF)),HF);
                    return HashText;
                }
            } catch (Exception e){
                throw new RuntimeException(e);
            }
        }
    
    }
    Per fare una cosa bella bisognerebbe che lo script calcolasse in automatico il sistema di conversione più evoluto del container ed usasse quello ma non saprei come fare (su IntelliJ ho java 1.10, sul server non posso saperlo). Tu sei in grado?
    Ultima modifica di giannino1995; 08-08-2018 a 19:07
    Più pratica in futuro...

  3. #3
    Utente di HTML.it L'avatar di andbin
    Registrato dal
    Jan 2006
    residenza
    Italy
    Messaggi
    18,284
    Allora, un po' di questioni, vediamo di andare con ordine:

    Quote Originariamente inviata da giannino1995 Visualizza il messaggio
    Se getInstance() non richiedesse try/catch non userei la gestione delle eccezioni.
    Il getInstance() riceve una stringa con il nome dell'algoritmo. Il nome potrebbe essere "sballato" (es. "MDD5", se fosse un input preso da qualche parte) oppure potrebbe essere sensato ma non supportato su una certa versione della piattaforma Java. Il getInstance segnala la cosa con un NoSuchAlgorithmException, che purtroppo è una eccezione "checked", quindi il programmatore non la può ignorare.

    Nel mio esempio "basilare" ho fatto semplicemente uscire NoSuchAlgorithmException dal md5Hex. Ma ci sono diverse varianti che possono aver senso:

    1) Nel md5Hex() far uscire NoSuchAlgorithmException (come ho fatto)
    2) Nel md5Hex() catturare NoSuchAlgorithmException per fare del "logging" e poi rilanciare fuori dal md5Hex il NoSuchAlgorithmException così come è.
    3) Nel md5Hex() catturare NoSuchAlgorithmException (con/senza logging) e lanciare fuori un'altra eccezione differente magari "unchecked" in modo che il programmatore possa non doversene preoccupare subito.

    Ma catturare NoSuchAlgorithmException e fare un return null, no, ha davvero poco senso.

    Quote Originariamente inviata da giannino1995 Visualizza il messaggio
    Cosa significa “%032x”?
    E' una stringa di "formato" utilizzata dalla funzionalità di "formattazione delle stringhe" che è stata introdotta in Java 5. Documentati perché è una cosa molto utile in generale.

    Quote Originariamente inviata da giannino1995 Visualizza il messaggio
    Cosa significa “1”? Perché semplicemente non “BigInteger(digest)”?
    La documentazione di BigInteger è chiara:

    BigInteger(int signum, byte[] magnitude)

    signum - signum of the number (-1 for negative, 0 for zero, 1 for positive).
    magnitude - big-endian binary representation of the magnitude of the number.
    Il digest lo passiamo al BigInteger che lo tratterà come un numero di tot byte (bit x 8) ma con il solo scopo poi di formattarlo in hex (non ci interessa farci calcoli!). Ma il digest NON è un numero (in senso stretto, specifico), è solo un tot di byte "crudi". Quindi con 1 indichiamo al BigInteger di trattarlo come numero positivo, perché non ci interessa altro modo.

    Quote Originariamente inviata da giannino1995 Visualizza il messaggio
    Si converte tutto in Byte perché digest() vuole così, giusto?
    Il risultato di un algoritmo di hash è un tot di bit "crudi", che non hanno alcun significato particolare, a parte appunto rappresentare una sorta di "firma" di un messaggio di tot byte.
    Quindi il MessageDigest dà il risultato come array di byte. Non offre alcun supporto alla "formattazione". Come formattarlo in stringa (tipicamente in hex ma in rari casi in Base64 o altro) è compito nostro.

    Quote Originariamente inviata da giannino1995 Visualizza il messaggio
    Per fare una cosa bella bisognerebbe che lo script calcolasse in automatico il sistema di conversione più evoluto del container ed usasse quello
    Prima hai detto, quoto:

    Quote Originariamente inviata da giannino1995 Visualizza il messaggio
    Voglio che nel file in cui vado a salvare le password degli utenti queste ultime non siano visibili in chiaro.
    Se vuoi fare un file (o DB) con delle password NON in chiaro, allora un hash è ok. Ma l'algoritmo di hashing lo devi stabilire TU a priori. Non è una cosa che puoi far scegliere ad una macchina, non ha senso!

    La API della security (package java.security) permette di scoprire dinamicamente tutti i servizi (compresi quelli di message digest) di un certo provider. Quindi puoi prendere l'elenco dei Provider, per ciascuno l'elenco dei service e filtrarli per trovare tutti gli algoritmi di digest disponibili. Se vuoi del codice, non c'è problema. Per ciascun MessageDigest puoi anche sapere la lunghezza del digest (metodo getDigestLength() ).

    Ma il punto è che per fare quello che hai detto, l'algoritmo lo devi scegliere e imporre TU, non lo può fare una macchina. Non puoi determinare programmaticamente quale algoritmo è il "migliore". La conoscenza anche basilare sulle caratteristiche degli algoritmi la devi avere tu ... non la macchina!
    Andrea, Senior Java developerSCJP 5 (91%) • SCWCD 5 (94%)
    Java Versions Cheat Sheet

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2026 vBulletin Solutions, Inc. All rights reserved.