Cátedra: Osvaldo Clua
Fecha: Primera Oportunidad - Primer Cuatrimestre 2004
Día: 01/06/2004
Un organismo previsional necesita que desarrollemos una solución rápida que responda a la siguiente pregunta:
¿Cuántas jubilaciones se deberán pagar el próximo mes?
La ley que rige para este organismo dice que se pagará una jubilación a todo aportante que este en trámite de jubilarse y que tenga por lo menos 200 aportes. Se encuentra en tramite de jubilarse todo aportante activo, con Tipo de Tramite “JUBILACION” y Fecha Fin de Tramite en NULO. La información se encuentra en un archivo llamado “TramitesAportantes“, con los siguientes campos de longitud variable y separados por el caracter ”]”:
IMPORTANTE: Utilizar solamente comandos que acepten expresiones regulares, wc y/o cat.
Se tiene una máquina servidora, en la que se requiere disponer de un ejecutor de comandos, al que llamaremos TASKS, que le permita a los operadores ejecutar determinadas tareas en base a archivos residentes en el directorio que le pasarán como parámetro. TASKS deberá procesar todos los archivos de dicho directorio y ejecutar un comando por cada uno de ellos, según indique el archivo de configuración sever.config, residente en el mismo directorio que TASKS. Cada línea de este archivo tiene alguno de los siguientes formatos: (el separador tanto para FILE como para CMD es ”:”)
Ejemplo:
CMD:8:teleproc
Este tipo de línea indica que el comando <cmd> acepta la cantidad de parámetros indicada en <cant total de parámetros>: Esta cantidad total de parámetros debe ser la suma de los 'fijos' mas los 'variables': Chequear que sea así (es decir que en el archivo venga la cantidad que corresponde).
Ejemplo:
FILE:teleproc:telefonos.txt:-f|-o \tmp|-r no-hung
Este tipo de linea indica que para procesar un archivo con nombre <nombre archivo> se deberá ejecutar el comando <cmd>, con ciertos parámetros: una cantidad de parámetro (fijos) indicada en <lista de parametros fijos separados por '|'> seguida de una cantidad de parámetros variables que constituyen la primera linea del archivo siendo procesado y cambien están separados por '|'.
Se pide escribir en PERL, el script TASKS.pl que recibiendo como parámetro el directorio donde se encuentran los archivos a procesar, primero cargue en estructuras de memoria adecuadas la información de configuración, y luego afectúe el procesamiento de los archivos. Como resultado, deberá mostrar por pantalla el porcentaje de comando para los que no coincidió la cantidad total de parámetros especificada, el porcentaje otros errores, y el porcentaje de ejecutados exitosamente.
Nota: resolver haciendo uso de hashes, arreglos y de la función split, siempre que resulte adecuado y simplifique el desarrollo
Se tiene un archivo con parámetros de usuarios, llamado PARAMETROS.DAT, con el siguiente formato:
usuario;directorio origen;grupo;cantidad max de archivos
Se pide hacer un script que procese el archivo de la siguiente manera:
(*) Para determinar el tipo de archivo analizar la primera linea del mismo.
#!/usr/bin/perl #Autor: Maria Ines Parnisari $cantArgs = @ARGV; if ($cantArgs != 1) { print "ERROR: se requiere un argumento.\n"; exit 0; } $dirArchivos = $ARGV[0]; %cantParamsComando = (); #clave->comando, valor->cantidad parametros %cantParamsFijos = (); #clave->comando, valor->cantidad parametros fijos %comandoArchivo = (); #clave->archivo, valor->comando # Proceso el archivo de configuracion open ($archivoConfig, "< server.config") or die "No se pudo abrir server.config."; while ($linea = <$archivoConfig>) { chomp($linea); @datos = split (":", $linea); $cantidadDatos = @datos; if ($cantidadDatos == 3) { #CMD:8:TELEPROC $cantParamsComando{$datos[2]} = $datos[1]; } elsif ($cantidadDatos == 4) { #FILE:teleproc:telefonos.txt:-f|-o \tmp|-r no-hung $comandoArchivo{$datos[2]} = $datos[1]; @paramsFijos = split ("|", $datos[3]); $cant = @paramsFijos; $cantParamsFijos{$datos[1]} = $cant; } } close ($archivoConfig); # Examino archivos del directorio if (opendir($dirHandle, $dirArchivos)) { @archivos = readdir($dirHandle); closedir($dirHandle); } else { die "No se pudo abrir el directorio $dirArchivos."; } $cantidadArchivos = @archivos; $cantidadok = 0; $cantidaderror = 0; foreach $archivo (@archivos) { open ($archHandle, "<$archivo") or die "No se pudo abrir $archivo."; while( $primLinea = <$archHandle>) { chomp ($primLinea); if ($. == 1) { last; } } @paramsVariables = split ("|", $primLinea); $cantParamsVar = @paramsVariables; $comando = $comandoArchivo{$archivo}; # Cantidad de parametros OK? if ($cantParamsVar + $cantParamsFijos{$comando} == $cantParamsComando{$comando}) { $paramsFijos =~ s/^FILE:$comando:$archivo:\(.*\)$/\1/g; $res = `$comando @paramsFijos @paramsVariables`; $cantidadok += 1; } else { $cantidaderror += 1; } close ($archHandle); } $porcentajeok = $cantidadok / $cantidadArchivos; $porcentajeerror = $cantidaderror / $cantidadArchivos; print "Porcentaje OK: $porcentajeok. \nPorcentaje ERROR: $porcentajeerror.\n";
#!/bin/bash ################################################################################################## # Parcial 20040601_1 : Ejercicio REGEX # Resolucion # Autor: Maximiliano Milicich (mmilicich) # # HIPOTESIS Y PRECONDICIONES: # # - El ultimo campo de un registro NO lleva separador de campo final # - <Fecha Fin de Tramite> NULO significa que NO HAY DATOS PARA ESE CAMPO # - El campo activo posee unicamente los valores [SI-NO]. SI = activo. NO = inactivo ################################################################################################## JUB_SEP=']' # separador de campos JUB_NOSEP="[^${JUB_SEP}]" # cualquier caracter que no sea un separador de campos JUB_ACTIVO='SI' # Indicador de registro ACTIVO JUB_TIPO_TRAMITE_JUBILACION='JUBILACION' # Tipo de Tramite JUBILACION JUB_DATAFILE='TramitesAportantes' # Archivo de datos a procesar JUB_TEMPFILE='/tmp/jub_count.tmp' # Archivo temporal auxiliar # Expresion para el GREP: filtra los registros que cumplen las condiciones pedidas # notar que ${JUB_CANT_APORTES} es variable, por eso la necesidad de una funcion que "reevalue" la expresion # Para hacer mas clara la construccion de la REGEX, la separamos en pasos: function set_jub_grep_expr() { # Los 3 primeros campos pueden ser cualquier cosa: JUB_GREP_EXPR="^\(${JUB_NOSEP}*${JUB_SEP}\)\{3\}" # Luego viene el filtro para el campo Cantidad de aportes: JUB_GREP_EXPR=${JUB_GREP_EXPR}"${JUB_CANT_APORTES}${JUB_SEP}" # Luego, 2 campos mas que pueden ser cualquier cosa: JUB_GREP_EXPR=${JUB_GREP_EXPR}"\(${JUB_NOSEP}*${JUB_SEP}\)\{2\}" # Luego viene el filtro por ACTIVOS: JUB_GREP_EXPR=${JUB_GREP_EXPR}"${JUB_ACTIVO}${JUB_SEP}" # Luego, 3 campos mas que pueden ser cualquier cosa: JUB_GREP_EXPR=${JUB_GREP_EXPR}"\(${JUB_NOSEP}*${JUB_SEP}\)\{3\}" # Luego el filtro por Tipo de tramite (JUBILACION): JUB_GREP_EXPR=${JUB_GREP_EXPR}"${JUB_TIPO_TRAMITE_JUBILACION}${JUB_SEP}" # Por ultimo, el campo de Fecha_Inicio (puede ser cualquier cosa) # Y luego de este, viene un separador y el final de linea (caracter de anclaje $): # Esto es senial de que el campo fecha_fin_tramite es NULO JUB_GREP_EXPR=${JUB_GREP_EXPR}"${JUB_NOSEP}*${JUB_SEP}$" } # end function set_jub_grep_expr() # filtramos primero los que tienen cantidad de 200 a 999 (pueden haber ceros a izquierda) JUB_CANT_APORTES='0*[2-9][0-9]\{2\}' set_jub_grep_expr grep "$JUB_GREP_EXPR" "$JUB_DATAFILE" > "$JUB_TEMPFILE" # luego filtramos los que tienen cantidad de 1000 en adelante (pueden haber ceros a izquierda) JUB_CANT_APORTES='0*[1-9][0-9]\{3,\}' set_jub_grep_expr grep "$JUB_GREP_EXPR" "$JUB_DATAFILE" >> "$JUB_TEMPFILE" # Por ultimo, contamos los registros filtrados (SOLUCION) y nos vamos: cat "$JUB_TEMPFILE" | wc -l rm "$JUB_TEMPFILE" exit
#!/bin/bash ################################################################################################### # FI.UBA.AR 75.08 # Parcial 20040601_1 - Ejercicio BASH # Resolucion # Autor: Maximiliano Milicich (mmilicich) # # HIPOTESIS Y PRECONDICIONES: # # - FALTA HACER EL PUNTO 2.3 (el de programas PERL) !!!!!!! ################################################################################################### USU_PARMFILE='PARAMETROS.DAT' USU_LOGFILE='LOG.TXT' USU_THISUSER=`whoami` # el usuario que ejecuta el script # Validamos si el usuario existe: USU_VALIDUSER=$(grep "^$USU_THISUSER;.*$" "$USU_PARMFILE") if [ -z "$USU_VALIDUSER" ] then echo "$USU_THISUSER - usuario inexistente" exit 1 fi # Recorremos el archivo de usuarios realizando las validaciones pedidas: while read USU_LINEA do if [ -z "$USU_LINEA" ] ; then continue fi USU_USER=$(echo "$USU_LINEA" | cut -f1 -d';') USU_SDIR=$(echo "$USU_LINEA" | cut -f2 -d';') USU_GRUP=$(echo "$USU_LINEA" | cut -f3 -d';') USU_MAXF=$(echo "$USU_LINEA" | cut -f4 -d';') if [ ! -d "$USU_SDIR" ] then echo "$USU_USER sin directorio origen" >> "$USU_LOGFILE" continue fi if [ $(find "$USU_SDIR" -type f 2> /dev/null | wc -l) -gt $USU_MAXF ] then echo "$USU_USER supera el limite de archivos" >> "$USU_LOGFILE" continue fi done < "$USU_PARMFILE" exit