Blog
Cifrado es un procedimiento que implementa un algoritmo de cifrado junto con una clave de cifrado para transformar un mensaje, sin cambiar su significado, de forma que sea incomprensible para quien no posea la clave de cifrado.
En la computación, es muy común implementar el cifrado como medida de seguridad en protocolos de autenticación y de mensajería. Un ejemplo de esto se tiene en el inicio de sesión de redes sociales y sistemas operativos.
Entre los algoritmos de cifrado mas utilizados se encuentra MD5 (Message-Digest Algorithm 5, implementado como medida de seguridad en descargas de internet) y SHA (Secure Hash Algorithm, implementado en la autenticación de los sistemas Unix).
hashlib
hashlib es un módulo de Python perteneciente a la librería estándar de Python implementado para cifrar datos con los algoritmos SHA (SHA1, SHA224, SHA256, SHA384, SHA512 y SHAKE), MD5, BLAKE, entre otros. Su utilización no es tan complicada como se cree comúnmente. Inicialmente, se debe importar el módulo:
import hashlib
Al utilizar las funciones de el módulo, se crean objetos de tipo hash.
new(nombre, dato)
La función new() del módulo hashlib es un constructor genérico del módulo utilizado para generar objetos hash. Toma como primer parámetro un string con el nombre del algoritmo de cifrado que será utilizado, y como segundo parámetro, un byte string con los datos que serán cifrados.
>>> h = hashlib.new("sha512",b"Unipython")
Si se intenta imprimir el objeto hash, se obtendrá una salida similar a la siguiente:
>>> print(h) <sha512 HASH object @ 0x00C0AE18>
Para poder ver el resultado del cifrado sobre el objeto, es necesario procesar los datos del objeto hash.
Una alternativa mas eficiente al uso de new() son los métodos constructores de cada algoritmo de cifrado:
- sha1(dato) que es equivalente a new(“sha1”,dato).
- sha224(dato) que es equivalente a new(“sha224”,dato).
- sha256(dato) que es equivalente a new(“sha256”,dato).
- sha384(dato) que es equivalente a new(“sha384”,dato).
- sha512(dato) que es equivalente a new(“sha512”,dato).
- blake2b(dato) que es equivalente a new(“blake2b”,dato). # Disponible a partir de Python 3.6
- blake2s(dato) que es equivalente a new(“blake2s”,dato). # Disponible a partir de Python 3.6
digest() y hexdigest()
Como lo sugiere su nombre, digest(), digiere (procesa) los datos de un objeto hash y los convierte en un objeto cifrado en bytes, conformado por bytes en el rango que va de 0 a 255.
hexdigest() tiene la misma función que digest(), pero la salida de esta es un string de longitud doble, conformado por caracteres hexadecimales.
Al utilizarlas con el objeto ‘h’ definido anteriormente se obtiene lo siguiente:
>>> print(h.digest()) b"#-'{+\x9b\x1c\x02\x94\xe8&\x13\xffd\x04\xcf\x8f\x9c\xa2\\\x9aKU\xb4\xd8\xfe\x109\x91\xb4\xf7\xfa\xa9^\x8d\x97k\xb4\x90\xb2\xb1\xbaE\xd3\xf1p\xad\xf8\xfd\xce\t\x96\xa2>\r\x11\xa6'g\x1d&\xdc\xa2\xfc" >>> print(h.hexdigest()) 232d277b2b9b1c0294e82613ff6404cf8f9ca25c9a4b55b4d8fe103991b4f7faa95e8d976bb490b2b1ba45d3f170adf8fdce0996a23e0d11a627671d26dca2fc
update(dato)
Es utilizada para actualizar el objeto hash, agregándole mas información al final. La información que es agregada, es especificada en el primer parámetro de la función. Llamadas repetidas con distintos argumentos a la función, son equivalentes a una sola llamada con la concatenación de todos los argumentos distintos (update(a) & update(b) == update(a+b)).
Anteriormente definimos un objeto ‘h’ de la siguiente manera:
>>> h = hashlib.new("sha512",b"Unipython")
Si se le aplica la función update() de la siguiente forma:
>>> h.update(b".com")
Se obtiene el equivalente a:
>>> h = hashlib.new("sha512",b"Unipython.com")
El uso de update() es muy común cuando se quieren cifrar datos de tamaño muy grande, ya que se puede ir aplicando el cifrado por partes.
hash()
hash es una clase de objeto en Python. La función new() y los métodos constructores de los algoritmos de cifrado retornan objetos de este tipo. Al igual que int, list, string, la clase hash tiene una función con su mismo nombre. hash(objeto) funciona de forma similar que int(objeto), al aplicarla en un objeto, esta nos devuelve el valor hash del mismo, en el caso de que esté disponible.
Las funciones digest(), hexdigest() y new() son métodos de la clase hash().
Atributos de la clase hash
- digest_size: Es el tamaño del hash resultante en bytes.
- block_size: Es el tamaño del bloque interno del algoritmo de hash en bytes.
Ejemplo 1:
El siguiente ejemplo muestra una manera de cifrar todas las lineas de un archivo de texto llamado “archivo.txt”, con el algoritmo de cifrado md5.
import hashlib # Se importa hashlib f = open('archivo.txt') # Se abre el archivo con la información lineas = f.readlines() # Se leen las lineas del archivo h = hashlib.new('md5') # Se crea el objeto de clase hash for linea in lineas: linea = str.encode(linea) # Se convierte el string en un byte string h.update(linea) # Se agregan las lineas del archivo al objeto hash print("El resultado en bytes del hash es: " + str(h.digest())) # Se imprime el hash en bytes print("El resultado en hexadecimales del hash es: " + str(h.hexdigest())) # Se imprime el hash en caracteres hexadecimales
El programa abre un archivo de texto con la información que se quiere cifrar, luego lee cada linea del archivo de texto. Se crea el objeto HASH con el algoritmo MD5 para luego aplicar el cifrado en cada linea del archivo.
Ejemplo 2:
En los sistemas Unix, se tiene la posibilidad de crear una cuenta de usuario de forma manual editando los archivos /etc/passwd y /etc/shadow. En el primero se encuentra toda la información del usuario como el username, el directorio home, la shell de inicio, etc. En el segundo archivo se encuentra la contraseña del usuario junto con toda la información referente a la contraseña. En el siguiente ejemplo, se mostrará como crear un archivo que genere una contraseña cifrada con el algoritmo SHA-512 que podría ser utilizada para una cuenta de usuario en un sistema operativo:
import hashlib # Se importa hashlib contraseña = input("Contraseña\n") # El usuario ingresa la contraseña que va a utilizar contraseña_cifrada = hashlib.sha512(contraseña.encode()) # Se codifica la contraseña y luego se # aplica el algoritmo de cifrado print("Su contraseña cifrada es:") print(contraseña_cifrada.hexdigest()) # Se imprime la contraseña cifrada en caracteres hexadecimales
El programa pide al usuario que ingrese la contraseña que será cifrada, luego la codifica en “UTF-8” (la convierte en byte string), se le aplica el cifrado y al final se imprime la contraseña.
➡ Te invitamos a realizar nuestro Curso de Python Gratis para Principiantes:
Excelente Ejercicio, muy claro y bien explicado.
Me sirvió mucho para entender como puedo cifrar con Python.
muchas gracias …