Table of Contents
Procedimiento operativo de preprocesamiento para MRIFACE
La gestión de imágenes MRI de este proyecto se ha ido complicando paulatinamente. En este punto, necesitamos un procedimiento operativo que permita manejar los DCM que llegan de Corachan e incorporarlos adecuadamente a XNAT.
TL;DR
Sacamos el NHC con,
[osotolongo@brick03 mri_face]$ ./preanon.sh /path/al/archivo/zip.zip
y lo subimos a XNAT con,
[osotolongo@brick03 mri_face]$ ./preanon.sh /path/al/archivo/zip.zip 12345678
Identificación del sujeto
Los DCM vienen dentro de un archivo zip con el nombre del sujeto. Ejemplo,
-rw-r--r-- 1 mtejero mtejero 262780990 Mar 1 10:30 'VALLE LOPEZ, EMILIO.zip'
La primera tarea es identificar este sujeto en nuestra DB y localizar su codigo de NHC. Idealmente podriamos capturar nombre y apellidos del sujeto con una regex sencilla. Pero la realidad es otra, asi que debemos tener en cuenta que pueda existir sujetos con un solo apellido o un nombre compuesto. Por supuesto que pueden exisitir irregularidades mas alla de esto pero vamos a suponer que entonces podemos renombrar el zip para que encaje dentro de una regex todavia sencilla como,
/(\S+)\s*(\S*),\s*(\S+\s*\S*)\.zip/
Idealmente, con esto podría hacer una query como,
SELECT dmg.xapellido1, dmg.xapellido2, dmg.xnombre, dmg.his_interno, cts.xdtprogramado, cts.xdtvisitado, cts.xestado_id FROM [UNIT4_DATA].[imp].[vh_pac_gral] AS dmg JOIN [UNIT4_DATA].[imp].[his_cites_programa] AS cts ON (dmg.his_interno = cts.his_interno) WHERE dmg.xapellido1 = 'VALLE' AND xapellido2 = 'LOPEZ' AND cts.xprestacion_id LIKE 'MRI';
y tendria un resultado como,
xapellido1,xapellido2,xnombre,his_interno,xdtprogramado,xdtvisitado,xestado_id ----------,----------,-------,-----------,-------------,-----------,---------- VALLE,LOPEZ,EMILIO,20221917,2023-02-24 13:00:00.000,2023-02-27 11:06:37.000,6 (1 rows affected)
de donde obtendria directamente el NHC. Pero como puede existir mas de un resultado, lo unico que voy a hacer es imprimir la info en la pantalla para permitir comprobar la fecha de peticion de MRI con la fecha de realizacion, en caso necesario.
Hacemos un wrapper sencillo que recoja el nombre de archivo y ejecute la consulta,
y entonces buscamos los datos haciendo,
[osotolongo@brick03 mri_face]$ ./get_nhc.pl "/ruby/neuroimagen/corachan/NO_NHC_MAT_MRIFACE/VALLE LOPEZ, EMILIO.zip" VALLE,LOPEZ,EMILIO -->> 2023-02-24 13:00:00.000,2023-02-27 11:06:37.000,6 -->> 20221917
donde podemos comprobar,
- El nombre del sujeto se corresponde con el archivo zip.
- Existe una MRI con una fecha que debe coincidir con la escrita en el DICOM. La segunda fecha es la de “devolucion” de la MRI, es decir, una visita clinica asociada a la peticion de MRI. El ultimo numero es el estado de la peticion (debe ser = 6)
- El NHC que buscamos
Claramente, puede existir mas de un registro en cuyo caso debe comprobarse en el DICOM la fecha correcta de la peticion y el nombre del sujeto.
Ejemplo, en la consulta,
[osotolongo@brick03 mri_face]$ ./get_nhc.pl "/ruby/neuroimagen/corachan/NO_NHC_MAT_MRIFACE/MARTINEZ PEREZ, ANA.zip" MARTINEZ,PEREZ,ANA -->> 2023-01-14 16:45:00.000,2023-01-16 17:09:50.000,6 -->> 20221990 MARTINEZ,PEREZ,ENRIQUE -->> 2022-10-04 14:30:00.000,2022-10-27 17:38:39.000,6 -->> 20220874
el registro correcto es el primero pero no podemos saberlo automagicamente (si, por diseño pero el diseño se ha hecho asi porque la DB es un cacao).
Anonimización, y subida a XNAT
Si ya hemos identificado el sujeto, procedemos a anonimizar el DICOM y además de borrar todos los datos identificativos, cambiar el PatientID por el código de NHC.
Descomprimimos el zip a un directorio temporal, y sacamos del DICOM la fecha y el ID del experimento (StudyID, StudyDate)
tdir=$(mktemp -t -d dcm.XXXXXXXX) unzip "${src}" -d ${tdir} hfile=$(find ${tdir} -type f | head -n 1) patid=$(dckey -k "StudyID" "${hfile}" 2>&1 | sed 's/[[:space:]]//g') sdate=$(dckey -k "StudyDate" "${hfile}" 2>&1 | sed 's/[[:space:]]//g') echo "${outdir}/${nhc}/${sdate}"
y ahora lo anonimizamos, y subimos a XNAT. Para la aninmizacion utilizamos el NHC y StudyID como los argumentos newpatientname y newpatientid respectivamente. Al final utilizamos xnatapic (es lo mas sencillo) para subir todo.
outdir=$(mktemp -t -d anon.XXXXXX) dcanon ${tdir} "${outdir}/${nhc}/${sdate}" nomove ${nhc} ${patid} xnatapic upload_dicom --project_id unidad --subject_id ${nhc} --pipelines ${outdir}/${nhc}/${sdate}
Datos añadidos
Ahora quiero añadir sexo y edad de nacimiento a los datos ya almacenados en XNAT. Esto es sencillo ya que al tener el NHC los sacamos directamente de la DB. Basta hacer el query,
SELECT his_interno, xfecha_nac, xsexo_id FROM [UNIT4_DATA].[imp].[vh_pac_gral] WHERE his_interno = '$nhc';
y tenemos estos datos.
Para subirlos a XNAT usamos la funcion xput_sbj_data() de la libreria XNATACE.
Comprobación ultima
Antes de terminar voy a comprobar si el NHC que tengo corresponde al sujeto. Parece muy redundante pero en la practica no lo es en absoluto. Desde que comienza el procedimiento pasan entre 10 y 20 minutos durante los cuales se puede perder el hilo de las operaciones.
Ahora por supuesto es mucho mas sencillo. Se ejecuta solo la query,
SELECT xapellido1, xapellido2, xnombre, his_interno FROM [UNIT4_DATA].[imp].[vh_pac_gral] WHERE his_interno = '$nhc';
Por comodidad esto se resume en otro perl wrapper
No parece demasiado complicado |
- preanon.sh
#!/bin/bash src=$1 shift nhc=$1 shift if [ -z ${nhc} ]; then ./get_nhc.pl "${src}" else tdir=$(mktemp -t -d dcm.XXXXXXXX) outdir=$(mktemp -t -d anon.XXXXXX) unzip "${src}" -d ${tdir} hfile=$(find ${tdir} -type f | head -n 1) patid=$(dckey -k "StudyID" "${hfile}" 2>&1 | sed 's/[[:space:]]//g') sdate=$(dckey -k "StudyDate" "${hfile}" 2>&1 | sed 's/[[:space:]]//g') echo "${outdir}/${nhc}/${sdate}" dcanon ${tdir} "${outdir}/${nhc}/${sdate}" nomove ${nhc} ${patid} xnatapic upload_dicom --project_id unidad --subject_id ${nhc} --pipelines ${outdir}/${nhc}/${sdate} # Este añade dob y gender ./update_sbj.pl -x unidad -i ${nhc} rm -rf ${tdir} rm -rf ${outdir} ./nhc2data.pl ${nhc} fi
y entonces ejecuto,
[osotolongo@brick03 mri_face]$ ./preanon.sh /ruby/neuroimagen/corachan/NO_NHC_MAT_MRIFACE/VALLE\ LOPEZ\,\ EMILIO.zip VALLE,LOPEZ,EMILIO -->> 2023-02-24 13:00:00.000,2023-02-27 11:06:37.000,6 -->> 20221917
y luego
[osotolongo@brick03 mri_face]$ ./preanon.sh /ruby/neuroimagen/corachan/NO_NHC_MAT_MRIFACE/VALLE\ LOPEZ\,\ EMILIO.zip 20221917
para subirlo a XNAT.
Nota: Es fundamental hacer la ultima comparacion contra el nombre de archivo zip El nombre de archivo puede ser algo como MARTINEZ GARCIA, MARIA DEL CARMEN.zip y la entrada en la DB como MARTNEZ GARCIA, M CARMEN o MARTNEZ GARCIA, CARMEN III. Un minuto de pararse a comprobar aqui ahorra mucho dolor de cabeza posterior.