Curso de programación en Python usando Linux. Decimoctava parte
Las entregas de este mes del curso de programación en Python usando Linux están dedicadas al ingreso, almacenamiento y modificaicón de datos. Vimos dos métodos que son ideales para aplicaciones que trabajan con pocos volúmenes de datos: el almacenamiento en texto plano y las bases de datos SQLite.
En el artÃculo anterior habÃamos comenzado a describir en detalle un ejemplo que nos permite ingresar, editar y eliminar datos de distribuciones Linux. Vamos a continaur donde lo dejamos.
Curso de programación en Python usando Linux
El programa que estamos analizando es este:
Nos toca ahora analizar a la función encargada de actualizar los registros
def actualizar(id_distro, nombre, derivada, escritorio):
Este lÃnea define la función y le asigna los cuatro parámetros con los que va a trabajar: el ID de la distribución que se modificará además de los tres nuevos valores de los parámetros que se van a cambiar.
with conectar() as con:
Abre la conexión con la base de datos. Si detecta algún error la cierra sin hacer modificaciónes.
cur = con.execute(
Esta instrucción inicia una consulta SQL y asigna el resultado en la variable cur (De cursor. En SQLite cursor es un objeto que se utiliza para interactuar con la base de datos. Adeemás,contiene información sobre las filas afectadas.
""UPDATE distros
SET nombre = ?, derivada = ?, escritorio = ?
WHERE id_distro = ?""",
Aunque por una cuestÃn de orden en el código se escriba en 3 lÃneas separadas, esto debe considerarse una sola lÃnea.
- UPDATE distros: Indica que se debe modificar la base de datos.
- SET nombre = ?, derivada = ?, escritorio = ?: Indica que se deben modificar los campos con los valores que se van a indicar. Los signos de pregunta son marcadores de posición.
- WHERE id_distro = ?: Indica que la modificación solo debe hacerse en la fila cuya clave primaria coincida con la indicada.
(nombre, derivada, escritorio, id_distro)
Esta es la tupla que incluye los valores que se van a actualizr.
Un dato importante es que en las dos últimas lÃneas la clave primaria aparece en último lugar. Esto es porque SQL reemplaza los marcadores de posición en orden y si no lo hiciéramos terminarÃa asignando la clave primaria a nombre.
Función eliminar
def eliminar(id_distro):
Define la función que eliminará registros de la base de datos. Cómo los registros se eliminan de a uno, indicando la clave primaria, solo se le asigna este parámetro.
with conectar() as con:
Como en la función anterior, inicia la conexión y la cierra en caso de que haya errores.
cur = con.execute(
Después de ejecutar la consulta SQL guarda el cursor en la variable cur. Esto permite recuperar la información sobre cuántas filas fueron afectadas.
"DELETE FROM distros WHERE id_distro = ?", (id_distro,)
Consulta SQL que cabe en una lÃnea donde:
- DELETE FROM distros: Indica que se van a borrar registros de la tabla distro
- WHERE id_distro = ?: Pero solo en caso de que la clave primaria coincida con la indicada por el usuairo. También en este caso el signo de pregunta es un marcador de posición.
Presten atención a la redacción del comando SQL, particularmente a este fragmento.
id_distro = ?", (id_distro,)
Esto es porque SQL solo trabaja con tuplas, no podemos pasarle la clave primaria directamente. En python las tuplas de un solo elemento necesitan la coma final.
if cur.rowcount:
Rowcount cuenta las columnas que fueron afectadas por el cambio. Cualquier valor mayor que cero se considera verdadero, entonces:
print(" Registro eliminado.")
Imprime el mensaje de que el registro se eliminó de manera exitosa.
else:
print(f" No existe una distro con ID {id_distro}.")
En caso de que el valor sea 0, es decir ninguna fila eliminada, imprime el mensaje correspondiente indicando la clave primaria que el usuairo habÃa dado.
Menú e ingreso de datos
MENU = """
╔══════════════════════════════╗
║ Gestor de Distros Linux ║
╠══════════════════════════════╣
║ 1. Listar todas ║
║ 2. Agregar nueva distro ║
║ 3. Buscar por ID ║
║ 4. Actualizar distro ║
║ 5. Eliminar distro ║
║ 0. Salir ║
╚══════════════════════════════╝
Opción: """
Nuestro programa tiene una interfaz de usuario muy limitada. No es por limitaciones de Python sino porque el objetivo del post no es hablar de interfases de usuario. Tanto para la creación de aplicaciones para usar en la terminal o con interfaz gráfica, Python dispone de múltiples opciones.
Habiendo dejado esto en claro, nuestro menú es solo una cadena de teto multilÃnea. Más abajo veremos como se le muestra al usuario.
def pedir_id():
return int(input(" ID Distro : "))
Define la función (Item 3 del menú) que pide al usurio que ingrese la clave primaria de la distribuición que busca. Luego comprueba que sea un número y lo convierte en entero para poder hacer la búsqueda.
def pedir_campos():
Esta es la definición de la función para ingreso de datos. No recibe parámetros porque es el usuario quien lo debe ingresar.
nombre = input("Nombre: ").strip()
Le pide al usuario que ingrese el nombre de la distribución y lo asigna a la variable nombre. strip se ocupa de eliminar los espacios vacÃos al principio y al final.
derivada = input("Derivada de: ").strip() or None
escritorio = input("Escritorio : ").strip() or None
Estas dos lÃneas ingresan los datos de derivada y escritorio pero varÃan al final con la anterior en que si el usuario no escribe nada, en la base de datos al campo se le asigna el valor «none». Esto es para indicar que el campo no tiene valor.
return nombre, derivada, escritorio
Devuelve los tres valores a la vez evitando que el sistema los confunda con una tupla.
La función principal
def main():
Esta es la función que gestiona el programa y controla a todas las demás.
crear_tabla()
Llama a la función que comprueba si la tabla existe y si no la crea.
while True:
Inicia el bucle infinito que mantendrá el programa en ejecución a menos que el usuairo o un error lo interrumpan.
try:
opcion = input(MENU).strip()
Muestra al usuario el menú y elimina los espacios en blanco al principio y al final. Try es el comienzo de un mecanismo de protección de errores que veremos en la lÃnea siguiente.
except (EOFError, KeyboardInterrupt):
print("\n Hasta luego.")
break
Se despide y finaliza el programa si el usuario pulsa una tecla incorrecta.
print()
Por motivos estéticos imprime una linea en blanco entre el menú y la respuesta del usuairo.
if opcion == "1":
listar()
Si el usuario escribió 1 llama a la función correspondiente a mostrar todos los registros.
elif opcion == "2":
nombre, derivada, escritorio = pedir_campos()
if nombre:
insertar(nombre, derivada, escritorio)
else:
print(" El nombre no puede estar vacÃo.")
Si el usuario eligió en el menú por la opción de agregar distribuciones, le pide los datos y verifica que el usuario efectivamente ingresa un nombre de la distribución ya que este campo es obligatorio.
elif opcion == "3":
try:
buscar(pedir_id())
except ValueError:
print(" ID inválido.")
En caso de que el usuario elija la opción 3 del menú llama a la función de búsqueda verificando antes que el usuario introduzca un número y no texto.
elif opcion == "4":
try:
id_d = pedir_id()
nombre, derivada, escritorio = pedir_campos()
if nombre:
actualizar(id_d, nombre, derivada, escritorio)
else:
print(" El nombre no puede estar vacÃo.")
except ValueError:
print(" ID inválido.")
Llegamos ahora a la función de actualizar datos. Primero verifica si la clave primaria establecida por el usuario es válida. EN caso de que no lo sea no pide los datos. Luego valida que el campo nombre no esté vacÃo.
elif opcion == "5":
try:
id_d = pedir_id()
confirm = input(f" ¿Eliminar distro {id_d}? (s/N): ").strip().lower()
Para eliminar distro se le pide al usaurio que ingrese una clave primaria y que luego confirme la decisión o la descarte. Strip se ocupa de que la S mayúscula se considere como minúscula.
if confirm == "s":
eliminar(id_d)
else:
print(" Cancelado.")
Solo se comprueba la tecla s, cualquier otra tecla se considera que el usuario canceló la operación
elif opcion == "0":
print(" Hasta luego.")
break
Simplemente se despide y cierra el programa.
else:
print(» Opción no válida.»)
Avisa al usuario que pulsó una tecla no incluÃda en las opciones.
print()
Imprime una lÃnea al final de cada operación para separarla de la nueva aparición del menú.
if __name__ == "__main__":
main()
Estas dos lÃneas tienen que ver con el funcionamiento interno de Python y permiten que el programa se ejecute de manera independiente o sea llamado por otros programas.
El curso va a continuar en julio del 2026
.png)




















