Mercurial > hgweb > health
changeset 4862:bcdb9d00c7b3
task #16043: Migration to GNU Health 4.0: Migrate health_orthanc
| author | Luis Falcon <falcon@gnuhealth.org> |
|---|---|
| date | Fri, 14 Jan 2022 21:43:01 +0000 |
| parents | e1567c3d934f |
| children | 3a5171e5694f |
| files | tryton/health_orthanc/__init__.py tryton/health_orthanc/data/data.xml tryton/health_orthanc/health_orthanc.py tryton/health_orthanc/tryton.cfg tryton/health_orthanc/wizard/wizard.py |
| diffstat | 5 files changed, 96 insertions(+), 74 deletions(-) [+] |
line wrap: on
line diff
--- a/tryton/health_orthanc/__init__.py +++ b/tryton/health_orthanc/__init__.py @@ -1,4 +1,3 @@ -# -*- coding: utf-8 -*- ############################################################################## # # GNU Health: The Free Health and Hospital Information System @@ -20,20 +19,21 @@ ############################################################################## from trytond.pool import Pool -from .health_orthanc import * -from .wizard import * +from . import health_orthanc +from . import wizard def register(): Pool.register( - AddOrthancInit, - AddOrthancResult, - OrthancServerConfig, - OrthancStudy, - OrthancPatient, - TestResult, - Patient, + wizard.wizard.AddOrthancInit, + wizard.wizard.AddOrthancResult, + health_orthanc.OrthancServerConfig, + health_orthanc.OrthancStudy, + health_orthanc.OrthancPatient, + health_orthanc.TestResult, + health_orthanc.Patient, module="health_orthanc", type_="model", ) - Pool.register(FullSyncOrthanc, module="health_orthanc", type_="wizard") + Pool.register( + wizard.wizard.FullSyncOrthanc, module="health_orthanc", type_="wizard")
--- a/tryton/health_orthanc/data/data.xml +++ b/tryton/health_orthanc/data/data.xml @@ -12,20 +12,6 @@ <field name="group" ref="health.group_health_admin"/> </record> - <!-- Sync Orthanc servers --> - <record model="ir.cron" id="cron_orthanc_sync"> - <field name="name">Sync Orthanc servers</field> - <field name="request_user" ref="res.user_admin"/> - <field name="user" ref="user_orthanc"/> - <field name="active" eval="True"/> - <field name="interval_number" eval="15"/> - <field name="interval_type">minutes</field> - <field name="number_calls" eval="-1"/> - <field name="repeat_missed" eval="False"/> - <field name="model">gnuhealth.orthanc.config</field> - <field name="function">sync</field> - </record> - <!-- Access rights Default = Deny models and menu access Providers = Read studies and patients with relevant menu access
--- a/tryton/health_orthanc/health_orthanc.py +++ b/tryton/health_orthanc/health_orthanc.py @@ -1,7 +1,12 @@ -# -*- coding: utf-8 -*- ############################################################################## # # GNU Health: The Free Health and Hospital Information System +# +# *** ORTHANC INTEGRATION PACKAGE *** +# +# Copyright (C) 2019-2022 Chris Zimmerman <chris@teffalump.com> +# Copyright (C) 2021-2022 Luis Falcon <falcon@gnuhealth.org> +# Copyright (C) 2021-2022 GNU Solidario <info@gnusolidario.org> # # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by @@ -45,36 +50,44 @@ __name__ = "gnuhealth.orthanc.config" _rec_name = "label" - label = fields.Char("Label", required=True, help="Label for server (eg., remote1)") + label = fields.Char( + "Label", required=True, help="Label for server (eg., remote1)") + domain = fields.Char( - "URL", required=True, help="The full URL of the Orthanc server" - ) + "URL", required=True, help="The full URL of the Orthanc server") + user = fields.Char( - "Username", required=True, help="Username for Orthanc REST server" - ) + "Username", required=True, help="Username for Orthanc REST server") + password = fields.Char( - "Password", required=True, help="Password for Orthanc REST server" - ) - last = fields.BigInteger("Last Index", readonly=True, help="Index of last change") + "Password", required=True, help="Password for Orthanc REST server") + + last = fields.BigInteger( + "Last Index", readonly=True, help="Index of last change") + sync_time = fields.DateTime( - "Sync Time", readonly=True, help="Time of last server sync" - ) + "Sync Time", readonly=True, help="Time of last server sync") + validated = fields.Boolean( - "Validated", help="Whether the server details have been successfully checked" - ) + "Validated", help="Whether the server details have been " + "successfully checked") + since_sync = fields.Function( fields.TimeDelta("Since last sync", help="Time since last sync"), - "get_since_sync", - ) + "get_since_sync",) + since_sync_readable = fields.Function( fields.Char("Since last sync", help="Time since last sync"), "get_since_sync_readable", ) - patients = fields.One2Many("gnuhealth.orthanc.patient", "server", "Patients") + patients = fields.One2Many( + "gnuhealth.orthanc.patient", "server", "Patients") + studies = fields.One2Many("gnuhealth.orthanc.study", "server", "Studies") link = fields.Function( - fields.Char("URL", help="Link to server in Orthanc Explorer"), "get_link" - ) + fields.Char( + "URL", + help="Link to server in Orthanc Explorer"), "get_link") def get_link(self, name): pre = "".join([self.domain.rstrip("/"), "/"]) @@ -104,14 +117,16 @@ study = pool.get("gnuhealth.orthanc.study") if not servers: - servers = cls.search([("domain", "!=", None), ("validated", "=", True)]) + servers = cls.search([("domain", "!=", None), + ("validated", "=", True)]) logger.info("Starting sync") for server in servers: if not server.validated: continue logger.info("Getting new changes for <{}>".format(server.label)) - orthanc = RestClient(server.domain, auth=auth(server.user, server.password)) + orthanc = RestClient(server.domain, + auth=auth(server.user, server.password)) curr = server.last new_patients = set() update_patients = set() @@ -123,7 +138,8 @@ changes = orthanc.get_changes(since=curr) except: server.validated = False - logger.exception("Invalid details for <{}>".format(server.label)) + logger.exception( + "Invalid details for <{}>".format(server.label)) break for change in changes["Changes"]: type_ = change["ChangeType"] @@ -138,7 +154,8 @@ else: pass curr = changes["Last"] - if changes["Done"] == True: + + if changes["Done"] is True: logger.info("<{}> at newest change".format(server.label)) break @@ -163,7 +180,8 @@ server.last = curr server.sync_time = datetime.now() logger.info( - "<{}> sync complete: {} new patients, {} update patients, {} new studies, {} updated studies".format( + "<{}> sync complete: {} new patients, {} \ + update patients, {} new studies, {} updated studies".format( server.label, len(new_patients), len(update_patients), @@ -215,10 +233,12 @@ studies = fields.One2Many( "gnuhealth.orthanc.study", "patient", "Studies", readonly=True ) - server = fields.Many2One("gnuhealth.orthanc.config", "Server", readonly=True) + server = fields.Many2One( + "gnuhealth.orthanc.config", "Server", readonly=True) link = fields.Function( - fields.Char("URL", help="Link to patient in Orthanc Explorer"), "get_link" - ) + fields.Char( + "URL", help="Link to patient in Orthanc Explorer"), "get_link" + ) def get_link(self, name): pre = "".join([self.server.domain.rstrip("/"), "/"]) @@ -263,26 +283,27 @@ def update_patients(cls, patients, server): """Update patients""" - Patient = pool.get("gnuhealth.patient") - entries = cls.get_info_from_dicom(patients) updates = [] for entry in entries: try: patient = cls.search( - [("uuid", "=", entry["uuid"]), ("server", "=", server)], limit=1 + [("uuid", "=", entry["uuid"]), + ("server", "=", server)], limit=1 )[0] patient.name = entry["name"] patient.bd = entry["bd"] patient.ident = entry["ident"] - if not patient.patient: # don't update unless no patient attached + # don't update unless no patient attached + if not patient.patient: try: g_patient = Patient.search( [("puid", "=", entry["ident"])], limit=1 )[0] patient.patient = g_patient logger.info( - "New Matching PUID found for {}".format(entry["ident"]) + "New Matching PUID found for {}". + format(entry["ident"]) ) except: pass @@ -290,7 +311,8 @@ logger.info("Updating patient {}".format(entry["uuid"])) except: continue - logger.warning("Unable to update patient {}".format(entry["uuid"])) + logger.warning("Unable to update patient {}". + format(entry["uuid"])) cls.save(updates) @classmethod @@ -303,7 +325,8 @@ entries = cls.get_info_from_dicom(patients) for entry in entries: try: - g_patient = Patient.search([("puid", "=", entry["ident"])], limit=1)[0] + g_patient = Patient.search( + [("puid", "=", entry["ident"])], limit=1)[0] logger.info("Matching PUID found for {}".format(entry["uuid"])) except: g_patient = None @@ -317,20 +340,26 @@ __name__ = "gnuhealth.orthanc.study" - patient = fields.Many2One("gnuhealth.orthanc.patient", "Patient", readonly=True) + patient = fields.Many2One( + "gnuhealth.orthanc.patient", "Patient", readonly=True) + uuid = fields.Char("UUID", readonly=True, required=True) description = fields.Char("Description", readonly=True) date = fields.Date("Date", readonly=True) ident = fields.Char("ID", readonly=True) institution = fields.Char( - "Institution", readonly=True, help="Imaging center where study was undertaken" + "Institution", readonly=True, + help="Imaging center where study was undertaken" ) ref_phys = fields.Char("Referring Physician", readonly=True) req_phys = fields.Char("Requesting Physician", readonly=True) - server = fields.Many2One("gnuhealth.orthanc.config", "Server", readonly=True) + server = fields.Many2One( + "gnuhealth.orthanc.config", "Server", readonly=True) + link = fields.Function( - fields.Char("URL", help="Link to study in Orthanc Explorer"), "get_link" - ) + fields.Char( + "URL", help="Link to study in Orthanc Explorer"), "get_link") + imaging_test = fields.Many2One("gnuhealth.imaging.test.result", "Test") def get_link(self, name): @@ -367,7 +396,8 @@ except: date = None try: - description = study["MainDicomTags"]["RequestedProcedureDescription"] + description = \ + study["MainDicomTags"]["RequestedProcedureDescription"] except: description = None data.append( @@ -377,11 +407,13 @@ "description": description, "date": date, "ident": study.get("MainDicomTags").get("StudyID"), - "institution": study.get("MainDicomTags").get("InstitutionName"), + "institution": study.get( + "MainDicomTags").get("InstitutionName"), "ref_phys": study.get("MainDicomTags").get( "ReferringPhysicianName" ), - "req_phys": study.get("MainDicomTags").get("RequestingPhysician"), + "req_phys": study.get( + "MainDicomTags").get("RequestingPhysician"), } ) return data @@ -395,7 +427,8 @@ for entry in entries: try: study = cls.search( - [("uuid", "=", entry["uuid"]), ("server", "=", server)], limit=1 + [("uuid", "=", entry["uuid"]), + ("server", "=", server)], limit=1 )[0] study.description = entry["description"] study.date = entry["date"] @@ -407,7 +440,8 @@ logger.info("Updating study {}".format(entry["uuid"])) except: continue - logger.warning("Unable to update study {}".format(entry["uuid"])) + logger.warning( + "Unable to update study {}".format(entry["uuid"])) cls.save(updates) @classmethod @@ -421,7 +455,8 @@ for entry in entries: try: patient = Patient.search( - [("uuid", "=", entry["parent_patient"]), ("server", "=", server)], + [("uuid", "=", + entry["parent_patient"]), ("server", "=", server)], limit=1, )[0] except:
--- a/tryton/health_orthanc/tryton.cfg +++ b/tryton/health_orthanc/tryton.cfg @@ -1,5 +1,5 @@ [tryton] -version=3.8.0 +version=3.9.0 depends: health_imaging
--- a/tryton/health_orthanc/wizard/wizard.py +++ b/tryton/health_orthanc/wizard/wizard.py @@ -1,8 +1,8 @@ -# -*- coding: utf-8 -*- ############################################################################## # # GNU Health: The Free Health and Hospital Information System # +# *** ORTHANC INTEGRATION PACKAGE *** # # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by @@ -21,7 +21,6 @@ from datetime import datetime from trytond.model import ModelView, fields from trytond.wizard import Wizard, StateTransition, StateView, Button -from trytond.transaction import Transaction from trytond.pool import Pool from requests.auth import HTTPBasicAuth as auth from requests.exceptions import HTTPError @@ -39,7 +38,8 @@ __name__ = "gnuhealth.orthanc.add.init" label = fields.Char( - "Label", required=True, help="The label of the Orthanc server. Must be unique" + "Label", required=True, + help="The label of the Orthanc server. Must be unique" ) domain = fields.Char( "URL", required=True, help="The full URL of the Orthanc server" @@ -81,7 +81,8 @@ ) def transition_first_sync(self): - """Import and create all current patients and studies on remote DICOM server + """ Import and create all current patients + and studies on remote DICOM server """ pool = Pool()
