Conservar el estado del mostrador tras reiniciar

JavaBeginner
Practicar Ahora

Introducción

Un mostrador debe recordar quién tiene cada herramienta después de cerrar la aplicación. Este entorno independiente proporciona reglas de préstamo funcionales y un nuevo archivo del mostrador, con préstamos existentes y una herramienta en mantenimiento. Su código de almacenamiento incompleto pierde actualmente el estado guardado al cargar y no escribe los cambios.

Mapearás registros de archivos UTF-8 a objetos y guardarás solo cambios válidos. Debes conocer las reglas de objetos del laboratorio anterior; no necesitas ningún archivo de aquel entorno. Es una aplicación didáctica de un solo proceso, no una base de datos ni una garantía contra cortes de corriente. Tiempo de lectura y práctica estimado por el autor: 45 minutos.

Cargar el estado que realmente está en el disco

En este paso, leerás un registro normal de un archivo y después repararás cómo se convierten en objetos Java el estado guardado y las relaciones de prestatarios.

Abre la pestaña Terminal. cd selecciona la carpeta de este laboratorio independiente. Usa Ctrl+U para borrar una línea incorrecta del shell que aún no hayas ejecutado. Si hay un error de ruta, vuelve aquí y repite el comando correcto.

cd /home/labex/project/tool-library

La aplicación tiene reglas de objetos funcionales, pero un almacenamiento incompleto. Usa primero un pequeño archivo de práctica para ver el formato de cinco campos sin arriesgar los préstamos existentes. mkdir -p crea el directorio de práctica si hace falta. printf escribe con un formato elegido: \t crea un tabulador y \n termina el registro; > escribe su salida en el archivo indicado, reemplazando una copia de práctica anterior. Las comillas simples impiden que el shell cambie el formato. cp copia la lista de miembros junto a ese archivo porque la aplicación busca members.tsv junto a su archivo de entrada del mostrador. Ninguno de estos comandos cambia el mostrador real.

mkdir -p work
printf 'S01\tSpare drill\tAVAILABLE\t-\tPractice only\n' > work/sample.tsv
cp members.tsv work/members.tsv

Compila el código fuente actual. -encoding UTF-8 selecciona su codificación de texto, -d out selecciona la salida compilada y *.java selecciona los archivos Java de esta carpeta. Continúa solo si la compilación termina sin errores.

javac -encoding UTF-8 -d out *.java

-cp out indica a Java dónde están las clases. -Dfile.encoding=UTF-8 selecciona la codificación del texto durante la ejecución. La entrada de práctica es work/sample.tsv; --memory impide guardar esta demostración.

java -Dfile.encoding=UTF-8 -cp out Desk work/sample.tsv --memory

Dentro del programa, escribe estas líneas y pulsa Enter después de cada una:

list
borrow S01 M01
list
quit

S01 empieza AVAILABLE con prestatario -; su préstamo a M01 se acepta. Este caso normal funciona incluso con el cargador incompleto porque la fila de práctica ya tiene el estado que supone el código defectuoso. No demuestra la conservación de los préstamos existentes. El cambio de práctica desaparece cuando se cierra este proceso.

Lee el mostrador real y los miembros registrados. cat muestra un archivo sin editarlo:

cat desk.tsv
cat members.tsv

Hay cinco campos separados por tabuladores: ID, nombre, estado del enum, prestatario y nota. Este formato controlado admite espacios y texto UTF-8 en los campos, pero no tabuladores ni saltos de línea. T24 ya está prestada a M03; T25 está prestada a M02 y tiene la nota Cafe workshop. T23 está en mantenimiento. Estos hechos deben conservarse al cargar. No edites directamente desk.tsv, members.tsv ni la carpeta reference.

Lee el código de almacenamiento preparado:

cat Store.java

Store es el límite de persistencia: los registros se convierten en objetos en load; los objetos se convierten en registros en save. Files.readAllLines lee explícitamente en UTF-8. fields(line) comprueba el formato y produce los campos f[0] a f[4]. Busca la llamada new Tool(...): actualmente sustituye el estado y el prestatario de cada fila por Tool.State.AVAILABLE y "-". Predice el efecto sobre el prestatario de T24 y el estado de mantenimiento de T23. El bucle, la lista y los métodos auxiliares de análisis y validación ya están preparados; consérvalos. No necesitas reescribir su implementación con HashSet.

Crea una copia de seguridad solo del código fuente antes de editar:

cp Store.java work/Store-before-load.java.txt
nano Store.java

Como en el primer laboratorio, Ctrl+W busca, Enter confirma la búsqueda, las flechas desplazan el cursor y Backspace corrige caracteres. Busca Tool tool = new Tool para localizar esta única llamada al constructor. Edita sus argumentos de estado y prestatario para que quede así:

            Tool tool = new Tool(f[0], f[1], Tool.State.valueOf(f[2]), f[3], f[4]);

Tool.State.valueOf(f[2]) convierte el nombre del enum guardado en su valor; f[3] restaura el prestatario guardado. Conserva los argumentos de ID, nombre y nota, el bucle que rodea la llamada y todos los métodos auxiliares. Estás mapeando información existente, no inventando una herramienta nueva disponible. Guarda con Ctrl+O, Enter y sal con Ctrl+X. Para descartar un error sin guardar, usa Ctrl+X, N. Reabre y busca la llamada para corregir un error de compilación. Si necesitas empezar esta edición de nuevo deliberadamente, cp work/Store-before-load.java.txt Store.java restaura solo este archivo fuente; después rehaz el mapeo. Nunca vuelvas a ejecutar setup para deshacer modificaciones.

Aquí, throws IOException declara que el acceso al archivo puede fallar. El bucle de comandos imprime Cannot continue y se detiene si la entrada falta o está mal formada. Es un problema de archivo, no un préstamo rechazado. Corrige la ruta indicada o el mapeo del código fuente; no vacíes ni reescribas los registros originales para eliminar el error.

Compila el código fuente guardado e inicia el mostrador real. A diferencia de la demostración, omite --memory: el mostrador real guardará los cambios válidos cuando completes el guardado en el siguiente paso. Un error de sintaxis indica el archivo y la línea; corrígelo en nano y compila correctamente antes de iniciar, en vez de ejecutar clases antiguas.

javac -encoding UTF-8 -d out *.java
java -Dfile.encoding=UTF-8 -cp out Desk desk.tsv

Escribe estas líneas dentro del mostrador:

list
members
quit

La lista debe conservar T24 → M03, T25 → M02, el estado MAINTENANCE de T23 y todas las notas. members muestra los ID registrados. Abrir y listar no debe reescribir el archivo. quit vuelve al shell. El siguiente paso completa el guardado real; un mensaje de éxito por sí solo no demuestra persistencia.

Guardar cambios válidos y volver a abrir el mostrador

En este paso, harás que un nuevo préstamo y una devolución válida sobrevivan a la salida real del proceso.

Empieza en el shell de la misma pestaña Terminal. El guardado serializa cada objeto actual, incluidos los préstamos y registros de mantenimiento sin modificar. row(tool) une los cinco campos con tabuladores. El bucle añade todas las filas a una lista; Files.write las escribe como UTF-8. El bucle de comandos llama a save solo cuando un método del dominio termina normalmente. Una acción rechazada no debe escribir en el archivo de datos, ni siquiera para reescribir contenido idéntico.

Lee el marco de comandos para relacionar esa regla con el límite de almacenamiento:

cat Desk.java

Busca found.borrow(c[2]), found.giveBack(c[2]) y la llamada posterior a Store.save(path, tools). Una excepción del dominio omite la llamada de guardado y se convierte en un rechazo normal. Conserva este orden preparado; añadir una escritura al manejador de rechazos incumpliría el contrato.

Crea una copia de seguridad solo del código fuente que conserve tu cargador corregido:

cp Store.java work/Store-before-save.java.txt
nano Store.java

Pulsa Ctrl+W, busca TODO: write all rows y pulsa Enter. Lee el bucle situado justo encima: recoge una fila serializada por cada herramienta, incluidos los préstamos sin modificar. Usa las flechas para llegar al final de ese comentario y Backspace para borrar sus caracteres. Escribe la instrucción de escritura con la misma sangría. Reemplaza únicamente el comentario TODO por esta escritura real después del bucle y antes de la llave de cierre del método:

        Files.write(path, rows, StandardCharsets.UTF_8);

path es el archivo del mostrador elegido; rows es la lista serializada completa, no solo el último objeto modificado. La codificación explícita conserva la codificación del texto de cada campo. Conserva el método load corregido, el bucle de filas y todos los métodos auxiliares. Guarda con Ctrl+O, Enter, Ctrl+X. Si hay un error sin guardar, Ctrl+X, N lo descarta. Si el error del código fuente ya está guardado, reabre y corrígelo; cp work/Store-before-save.java.txt Store.java es una reversión opcional solo del código fuente que conserva el cargador. Después rehaz la escritura. No restablezcas el archivo del mostrador ni vuelvas a ejecutar setup.

Vuelve a compilar el código fuente guardado:

javac -encoding UTF-8 -d out *.java
java -Dfile.encoding=UTF-8 -cp out Desk desk.tsv

Escribe lo siguiente dentro del mostrador:

borrow T21 M01
borrow T21 M02
return T24 M01
borrow T23 M01
borrow TYPO M01
return T24 M03
list
quit

T21 queda prestada a M01. El préstamo duplicado, el prestatario incorrecto, el préstamo de la herramienta en mantenimiento y el ID mal escrito se rechazan intencionadamente. Solo la devolución de T24 por M03 tiene éxito. T22 sigue disponible, T23 sigue en mantenimiento y T25 sigue prestada a M02 con su nota original. El rechazo del ID desconocido mantiene utilizable el bucle; corrige el ID en lugar de reiniciar o restablecer el entorno.

Inicia ahora un nuevo proceso Java con el mismo archivo:

java -Dfile.encoding=UTF-8 -cp out Desk desk.tsv
list
quit

T21 debe seguir BORROWED por M01, y T24 debe seguir AVAILABLE con prestatario -. Si no ocurre, comprueba que compilaste el Store.java actual y que iniciaste sin --memory. No edites los registros finales para imitar un préstamo guardado. Si una operación aceptada ya se guardó, no la repitas solo porque ahora se rechaza; list muestra la realidad actual.

De nuevo en el shell, lee el resultado almacenado:

cat desk.tsv

Las relaciones de los registros deben coincidir con la lista del nuevo proceso. Conserva todos los ID, nombres, miembros, estado de mantenimiento, préstamos no afectados y notas. Solo cambian el estado/prestatario de T21 y el estado/prestatario de T24. Este pequeño escritor reemplaza el archivo durante un guardado correcto; no proporciona acceso concurrente, recuperación ante fallos ni una transacción atómica. Si la escritura falla, detente y examina el error antes de continuar.

Resumen

Mapeaste registros UTF-8 a objetos Java, guardaste todos los registros actuales después de una transición válida y volviste a abrir el mostrador en un proceso nuevo. Los préstamos, el mantenimiento y las notas existentes permanecieron intactos, mientras que las operaciones rechazadas no escribieron en el almacenamiento.