From 834d56b911d253bf7d4a62b07060ca6693124112 Mon Sep 17 00:00:00 2001 From: Laetitia Fesselier Date: Wed, 19 Oct 2022 13:27:43 -0400 Subject: [PATCH 1/4] ProjectID fix --- dicom-archive/profileTemplate.pl | 15 ++++++++++----- uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm | 14 +++++++------- 2 files changed, 17 insertions(+), 12 deletions(-) diff --git a/dicom-archive/profileTemplate.pl b/dicom-archive/profileTemplate.pl index a805f33c6..3925040f9 100755 --- a/dicom-archive/profileTemplate.pl +++ b/dicom-archive/profileTemplate.pl @@ -51,13 +51,15 @@ sub getSubjectIDs { $subjectID{'createVisitLabel'} = 1; - # When createVisitLabel is set to 1, CohortID must also + # $subjectID{'CohortID'} = undef; + # When createVisitLabel is set to 1, CohortID must also # be set to the ID of the cohort that the newly created # visit should have. Assuming for example that all patient # names end with "_", then we could write: # ($subjectID{'CohortID'}) = $patientName =~ /_(\d+)$/; # When createVisitLabel is set to 0, $subjectID{'CohortID'} is ignored. + # $subjectID{'ProjectID'} = 1; # If config setting 'createVisitLabel' is true # then $subjectID{'ProjectID'} must be set to the project ID of the # newly created visit. Assuming for example that all patients @@ -79,6 +81,7 @@ sub getSubjectIDs { $subjectID{'createVisitLabel'} = 0; + # $subjectID{'CohortID'} = 1; # When createVisitLabel is set to 1, CohortID must also # be set to the ID of the cohort that the newly created # visit should have. Assuming for example that visits V01 and V02 @@ -88,6 +91,7 @@ sub getSubjectIDs { # ? 1 : 2; # When createVisitLabel is set to 0, $subjectID{'CohortID'} is ignored. + $subjectID{'ProjectID'} = 1; # If config setting 'createVisitLabel' is true # then $subjectID{'ProjectID'} must be set to the project ID of the # newly created visit. Assuming for example that candidates with a @@ -96,11 +100,12 @@ sub getSubjectIDs { # could write: # $subjectID{'ProjectID'} = $subjectID{'CandID'} > 400000 ? 1 : 2; # ? 1 : 2; - # When createVisitLabel is set to 0, $subjectID{'ProjectID'} is ignored. + # When createVisitLabel and createCandidates are set to 0, $subjectID{'ProjectID'} is ignored. - print "PSCID is: " . $subjectID{'PSCID'} . - "\n CandID id: " . $subjectID{'CandID'} . - "\n visit_label is: " . $subjectID{'visitLabel'} . "\n"; + print "PSCID is: " . $subjectID{'PSCID'} . + "\n CandID id: " . $subjectID{'CandID'} . + "\n visit_label is: " . $subjectID{'visitLabel'} . "\n" . + "\n ProjectID is: " . $subjectID{'ProjectID'} . "\n"; } # Return subjectIDs diff --git a/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm b/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm index dd8ed7ec3..cf32789a0 100755 --- a/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm +++ b/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm @@ -1783,13 +1783,13 @@ sub CreateMRICandidates { chomp($User); $candID = NeuroDB::MRI::createNewCandID($dbhr) unless $candID; my %record = ( - CandID => $subjectIDsref->{'CandID'}, - PSCID => $subjectIDsref->{'PSCID'}, - DoB => $subjectIDsref->{'PatientDoB'}, - ProjectID => $subjectIDsref->{'ProjectID'}, - Sex => $sex, - RegistrationCenterID => $centerID, - UserID => $User, + CandID => $subjectIDsref->{'CandID'}, + PSCID => $subjectIDsref->{'PSCID'}, + DoB => $subjectIDsref->{'PatientDoB'}, + Sex => $sex, + RegistrationCenterID => $centerID, + RegistrationProjectID => $subjectIDsref->{'ProjectID'}, + UserID => $User, ); $query = sprintf( From 516b093008a9427d1f239e162bbf013adcced1b1 Mon Sep 17 00:00:00 2001 From: Laetitia Fesselier Date: Sun, 19 Feb 2023 03:47:47 -0500 Subject: [PATCH 2/4] New Config CreateVisit, default_project and default_cohort --- dicom-archive/profileTemplate.pl | 6 +- docs/scripts_md/ConfigOB.md | 6 + docs/scripts_md/MRI.md | 12 ++ uploadNeuroDB/NeuroDB/ExitCodes.pm | 2 +- uploadNeuroDB/NeuroDB/MRI.pm | 137 +++++++++++++++++- uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm | 20 ++- .../NeuroDB/objectBroker/ConfigOB.pm | 18 +++ uploadNeuroDB/imaging_non_minc_insertion.pl | 2 +- uploadNeuroDB/minc_insertion.pl | 2 +- uploadNeuroDB/tarchiveLoader.pl | 2 +- 10 files changed, 191 insertions(+), 16 deletions(-) diff --git a/dicom-archive/profileTemplate.pl b/dicom-archive/profileTemplate.pl index 3925040f9..691534e79 100755 --- a/dicom-archive/profileTemplate.pl +++ b/dicom-archive/profileTemplate.pl @@ -59,7 +59,7 @@ sub getSubjectIDs { # ($subjectID{'CohortID'}) = $patientName =~ /_(\d+)$/; # When createVisitLabel is set to 0, $subjectID{'CohortID'} is ignored. - # $subjectID{'ProjectID'} = 1; + # $subjectID{'ProjectID'} = undef; # If config setting 'createVisitLabel' is true # then $subjectID{'ProjectID'} must be set to the project ID of the # newly created visit. Assuming for example that all patients @@ -81,7 +81,7 @@ sub getSubjectIDs { $subjectID{'createVisitLabel'} = 0; - # $subjectID{'CohortID'} = 1; + # $subjectID{'CohortID'} = undef; # When createVisitLabel is set to 1, CohortID must also # be set to the ID of the cohort that the newly created # visit should have. Assuming for example that visits V01 and V02 @@ -91,7 +91,7 @@ sub getSubjectIDs { # ? 1 : 2; # When createVisitLabel is set to 0, $subjectID{'CohortID'} is ignored. - $subjectID{'ProjectID'} = 1; + # $subjectID{'ProjectID'} = undef; # If config setting 'createVisitLabel' is true # then $subjectID{'ProjectID'} must be set to the project ID of the # newly created visit. Assuming for example that candidates with a diff --git a/docs/scripts_md/ConfigOB.md b/docs/scripts_md/ConfigOB.md index c241b855d..851ce2956 100644 --- a/docs/scripts_md/ConfigOB.md +++ b/docs/scripts_md/ConfigOB.md @@ -195,6 +195,12 @@ Get the createCandidates Config setting. RETURN: (boolean) 1 if createCandidates is set to Yes in the Config module, 0 otherwise +### getCreateVisit() + +Get the createVisit Config setting. + +RETURN: (boolean) 1 if createVisit is set to Yes in the Config module, 0 otherwise + ### getPythonConfigFile() Get the MriPythonConfigFile Config setting. diff --git a/docs/scripts_md/MRI.md b/docs/scripts_md/MRI.md index 7ef965d7e..84f1af0a8 100644 --- a/docs/scripts_md/MRI.md +++ b/docs/scripts_md/MRI.md @@ -243,6 +243,18 @@ RETURNS: a two element array: - first is the MRI alias of the PSC or "UNKN" - second is the `CenterID` or 0 +### getProject($patientName, $dbhr, $db) + +Looks for the project id using the C table C as +a first resource, then using the C table C, +otherwise, look for the default_project config value, and return C. + +INPUTS: + - $subjectIDsref: subject's information hash ref + - $dbhr : database handle reference + +RETURNS: the C or an error if not found + ### compute\_hash($file\_ref) Semi-intelligently generates a hash (MD5 digest) for the `NeuroDB::File` object diff --git a/uploadNeuroDB/NeuroDB/ExitCodes.pm b/uploadNeuroDB/NeuroDB/ExitCodes.pm index 98975e021..d61a0ef35 100755 --- a/uploadNeuroDB/NeuroDB/ExitCodes.pm +++ b/uploadNeuroDB/NeuroDB/ExitCodes.pm @@ -125,7 +125,7 @@ our $INVALID_ENVIRONMENT_VAR = 40; # used when an environment variable is # value our $PROJECT_CUSTOMIZATION_FAILURE = 41; # used when either missing a function # or a customization variable - +our $PROJECT_INIT_FAILURE = 42; # used when project can't be initialized ## -- Common file manipulation failures (exit codes from 60 to 79) our $EXTRACTION_FAILURE = 60; # if archive extraction failed diff --git a/uploadNeuroDB/NeuroDB/MRI.pm b/uploadNeuroDB/NeuroDB/MRI.pm index 7ea00fd5d..5746799ea 100755 --- a/uploadNeuroDB/NeuroDB/MRI.pm +++ b/uploadNeuroDB/NeuroDB/MRI.pm @@ -140,6 +140,7 @@ RETURNS: an array of 2 elements: sub getSessionInformation { my ($subjectIDref, $studyDate, $dbh, $db) = @_; + my $configOB = NeuroDB::objectBroker::ConfigOB->new(db => $db); my ($sessionID, $studyDateJD); my ($query, $sth); @@ -167,7 +168,7 @@ sub getSessionInformation { return (\%session, ''); } - if (!$subjectIDref->{'createVisitLabel'}) { + if (!$configOB->getCreateVisit()) { my $msg = sprintf( "Visit %s for candidate %d does not exist.", $subjectIDref->{'visitLabel'}, @@ -278,6 +279,7 @@ sub getSessionInformation { Visit_label => $subjectIDref->{'visitLabel'}, CandID => $subjectIDref->{'CandID'} ); + return (\%session, ''); } @@ -1104,7 +1106,7 @@ sub getPSC { my $sth = $${dbhr}->prepare($query); $sth->execute($PSCID, $visitLabel); - if ( $sth->rows > 0) { + if ($sth->rows > 0) { my $row = $sth->fetchrow_hashref(); return ($row->{'MRI_alias'},$row->{'CenterID'}); } @@ -1125,6 +1127,137 @@ sub getPSC { =pod +=head3 getProject($patientName, $dbhr, $db) + +Looks for the project id using the C table C as +a first resource, then using the C table C, +otherwise, look for the default_project config value, and return C. + +INPUTS: + - $subjectIDsref: subject's information hash ref + - $dbhr : database handle reference + +RETURNS: the C or an error if not found + +=cut + +sub getProject { + my ($subjectIDsref, $dbhr) = @_; + my $PSCID = $subjectIDsref->{'PSCID'}; + my $visitLabel = $subjectIDsref->{'visitLabel'}; + + ## Get the ProjectID from the session table, if the PSCID and visit labels exist + ## and could be extracted + if ($PSCID && $visitLabel) { + my $query = "SELECT s.ProjectID FROM session s + JOIN candidate c on c.CandID=s.CandID + WHERE c.PSCID = ? AND s.Visit_label = ?"; + + my $sth = $${dbhr}->prepare($query); + $sth->execute($PSCID, $visitLabel); + if ($sth->rows > 0) { + my $row = $sth->fetchrow_hashref(); + return $row->{'ProjectID'}; + } + } + + ## Otherwise get the ProjectID from the candidate table, if the PSCID exists + if ($PSCID) { + my $query = "SELECT RegistrationProjectID + FROM candidate + WHERE PSCID = ?"; + + my $sth = $${dbhr}->prepare($query); + $sth->execute($PSCID); + if ($sth->rows > 0) { + my $row = $sth->fetchrow_hashref(); + return $row->{'RegistrationProjectID'}; + } + } + + ## Otherwise, use the default_project config value + my $query = "SELECT p.ProjectID + FROM Config c + JOIN ConfigSettings cs ON c.ConfigID = cs.ID + JOIN Project p ON p.Name = c.Value + WHERE cs.Name = 'default_project'"; + + my $sth = $${dbhr}->prepare($query); + $sth->execute(); + if ( $sth->rows > 0) { + my $row = $sth->fetchrow_hashref(); + if ($row->{'ProjectID'}) { + return $row->{'ProjectID'}; + } + } + + print STDERR "\nERROR: ProjectID cannot be initialized. ". + "Please set the default_project config.\n\n"; + exit $NeuroDB::ExitCodes::PROJECT_CUSTOMIZATION_FAILURE; +} + +=pod + +=head3 getCohort($subjectIDsref, $projectID, $dbhr) + +Looks for the cohort id using the C table C as +a first resource, for the cases where it is created using the front-end, +otherwise, look for the default_cohort config value, and return C. + +INPUTS: + - $subjectIDsref: subject's information hash ref + - $projectID : the project ID + - $dbhr : database handle reference + +RETURNS: the C or 0 + +=cut + +sub getCohort { + my ($subjectIDsref, $projectID, $dbhr) = @_; + my $PSCID = $subjectIDsref->{'PSCID'}; + my $visitLabel = $subjectIDsref->{'visitLabel'}; + + ## Get the CohortID from the session table, if the PSCID and visit labels exist + ## and could be extracted + if ($PSCID && $visitLabel) { + my $query = "SELECT s.CohortID FROM session s + JOIN candidate c on c.CandID=s.CandID + WHERE c.PSCID = ? AND s.Visit_label = ?"; + + my $sth = $${dbhr}->prepare($query); + $sth->execute($PSCID, $visitLabel); + if ( $sth->rows > 0) { + my $row = $sth->fetchrow_hashref(); + return $row->{'CohortID'}; + } + } + + ## Otherwise, use the default_cohort config value + my $query = "SELECT c.Value + FROM Config c + JOIN ConfigSettings cs ON c.ConfigID = cs.ID + WHERE cs.Name = 'default_cohort' + AND Value IN ( + SELECT title + FROM cohort + JOIN `project_cohort_rel` USING (CohortID) + WHERE ProjectID = ?)"; + + my $sth = $${dbhr}->prepare($query); + $sth->execute($projectID); + if ( $sth->rows > 0) { + my $row = $sth->fetchrow_hashref(); + if ($row->{'Value'}) { + return $row->{'Value'}; + } + } + + return ("UNKN", 0); +} + +=pod + =head3 compute_hash($file_ref) Semi-intelligently generates a hash (MD5 digest) for the C object diff --git a/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm b/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm index cf32789a0..ec930ea42 100755 --- a/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm +++ b/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm @@ -394,6 +394,8 @@ sub determineSubjectID { my $this = shift; my ($scannerID, $tarchiveInfo, $to_log, $upload_id, $User, $centerID) = @_; + my $dbhr = $this->{dbhr}; + $to_log = 1 unless defined $to_log; if (!defined(&Settings::getSubjectIDs)) { if ($to_log) { @@ -414,6 +416,15 @@ sub determineSubjectID { $patientName, $patientID, $scannerID, $this->{dbhr}, $this->{'db'} ); + if (!$subjectIDsref->{'ProjectID'}) { + my $projectID = NeuroDB::MRI::getProject($subjectIDsref, $dbhr); + $subjectIDsref->{'ProjectID'} = $projectID; + } + + if (!$subjectIDsref->{'SubprojectID'}) { + $subjectIDsref->{'SubprojectID'} = NeuroDB::MRI::getCohort($subjectIDsref, $subjectIDsref->{'ProjectID'}, $dbhr); + } + # create the candidate if it does not exist $this->CreateMRICandidates( $subjectIDsref, $tarchiveInfo, $User, $centerID, $upload_id @@ -1735,7 +1746,6 @@ sub CreateMRICandidates { my $pscID = $subjectIDsref->{'PSCID'}; my $candID = $subjectIDsref->{'CandID'}; - # If there already is a candidate with that PSCID, skip the creation. # Note that validateCandidate (which is called later on) will validate # that pscid and candid match so we don't do it here. @@ -1805,7 +1815,6 @@ sub CreateMRICandidates { $message = "\n==> CREATED NEW CANDIDATE: $candID"; $this->{LOG}->print($message); $this->spool($message, 'N', $upload_id, $notify_detailed); - } @@ -1933,6 +1942,7 @@ or a phantom sub validateCandidate { my $this = shift; + my $configOB = $this->{'configOB'}; my ($subjectIDsref, $upload_id) = @_; my ($CandMismatchError, $message); @@ -1996,17 +2006,13 @@ sub validateCandidate { # if we end up here, it means that the visit label was not found in Visit_Windows # therefore need to check if 'createVisitLabel' was set - if ($subjectIDsref->{'createVisitLabel'}) { + if ($configOB->getCreateVisit()) { $message = "\n=> Will create visit label $visit_label in Visit_Windows\n"; - } else { - $message = "\n=> No Visit label\n"; $this->writeErrorLog($message, $NeuroDB::ExitCodes::INSERT_FAILURE); - return "Visit label $visit_label does not exist in Visit_Windows"; - } # write the message about the visit label in the notification spool table diff --git a/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm b/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm index 00ddfffa5..ba9b6e622 100644 --- a/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm +++ b/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm @@ -65,6 +65,7 @@ use NeuroDB::objectBroker::ObjectBrokerException; use TryCatch; +<<<<<<< HEAD use constant TARCHIVE_LIBRARY_DIR => 'tarchiveLibraryDir'; use constant DATA_DIR_BASE_PATH => 'dataDirBasepath'; use constant MAIL_USER => 'mail_user'; @@ -93,6 +94,8 @@ use constant BIDS_DATASET_AUTHORS => 'bids_dataset_authors'; use constant BIDS_ACKNOWLEDGMENTS_TEXT => 'bids_acknowledgments_text'; use constant BIDS_README_TEXT => 'bids_readme_text'; use constant BIDS_VALIDATOR_OPTIONS_TO_IGNORE => 'bids_validator_options_to_ignore'; +use constant CREATE_CANDIDATES => 'createCandidates'; +use constant CREATE_VISIT => 'createVisit'; =pod @@ -446,6 +449,21 @@ sub getCreateCandidates { return $getBooleanRef->($value); } +=head3 getCreateVisit() + +Get the createVisit Config setting. + +RETURN: (boolean) 1 if createVisit is set to Yes in the Config module, 0 otherwise + +=cut +sub getCreateVisit { + my $self = shift; + + my $value = &$getConfigSettingRef($self, CREATE_VISIT); + + return $getBooleanRef->($value); +} + =head3 getPythonConfigFile() Get the MriPythonConfigFile Config setting. diff --git a/uploadNeuroDB/imaging_non_minc_insertion.pl b/uploadNeuroDB/imaging_non_minc_insertion.pl index 02f1a4ef1..0f656a201 100755 --- a/uploadNeuroDB/imaging_non_minc_insertion.pl +++ b/uploadNeuroDB/imaging_non_minc_insertion.pl @@ -475,7 +475,7 @@ =head2 Methods 'imaging_non_minc_insertion.pl' , $upload_id, 'Y', 'N' ); - exit ($subjectIDsref->{'createVisitLabel'} == 1 + exit ($configOB->getCreateVisit() == 1 ? $NeuroDB::ExitCodes::CREATE_SESSION_FAILURE : $NeuroDB::ExitCodes::GET_SESSION_ID_FAILURE); } diff --git a/uploadNeuroDB/minc_insertion.pl b/uploadNeuroDB/minc_insertion.pl index 0eb4aaeba..ef7283543 100755 --- a/uploadNeuroDB/minc_insertion.pl +++ b/uploadNeuroDB/minc_insertion.pl @@ -558,7 +558,7 @@ =head2 Methods 'minc_insertion.pl', $upload_id, 'Y', $notify_notsummary ); - exit ($subjectIDsref->{'createVisitLabel'} == 1 + exit ($configOB->getCreateVisit() == 1 ? $NeuroDB::ExitCodes::CREATE_SESSION_FAILURE : $NeuroDB::ExitCodes::GET_SESSION_ID_FAILURE); } diff --git a/uploadNeuroDB/tarchiveLoader.pl b/uploadNeuroDB/tarchiveLoader.pl index 4d6dc072b..8d84a0e47 100755 --- a/uploadNeuroDB/tarchiveLoader.pl +++ b/uploadNeuroDB/tarchiveLoader.pl @@ -570,7 +570,7 @@ =head2 Methods 'tarchiveLoader.pl', $upload_id, 'Y', $notify_notsummary ); - exit ($subjectIDsref->{'createVisitLabel'} == 1 + exit ($configOB->getCreateVisit() == 1 ? $NeuroDB::ExitCodes::CREATE_SESSION_FAILURE : $NeuroDB::ExitCodes::GET_SESSION_ID_FAILURE); } From c465f7d4cb3bdb74ec8bcecd8761d62615906629 Mon Sep 17 00:00:00 2001 From: Laetitia Fesselier Date: Sun, 19 Feb 2023 21:44:47 -0500 Subject: [PATCH 3/4] Create getDefaultCohort and getDefaultProject in ConfigOB --- dicom-archive/profileTemplate.pl | 4 +-- docs/scripts_md/ConfigOB.md | 12 +++++++ uploadNeuroDB/NeuroDB/MRI.pm | 33 +++++++++---------- uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm | 6 ++-- .../NeuroDB/objectBroker/ConfigOB.pm | 29 +++++++++++++++- 5 files changed, 61 insertions(+), 23 deletions(-) diff --git a/dicom-archive/profileTemplate.pl b/dicom-archive/profileTemplate.pl index 691534e79..e3527affc 100755 --- a/dicom-archive/profileTemplate.pl +++ b/dicom-archive/profileTemplate.pl @@ -51,8 +51,8 @@ sub getSubjectIDs { $subjectID{'createVisitLabel'} = 1; - # $subjectID{'CohortID'} = undef; - # When createVisitLabel is set to 1, CohortID must also + # $subjectID{'CohortID'} = undef; + # When createVisitLabel is set to 1, CohortID must also # be set to the ID of the cohort that the newly created # visit should have. Assuming for example that all patient # names end with "_", then we could write: diff --git a/docs/scripts_md/ConfigOB.md b/docs/scripts_md/ConfigOB.md index 851ce2956..3d767b986 100644 --- a/docs/scripts_md/ConfigOB.md +++ b/docs/scripts_md/ConfigOB.md @@ -201,6 +201,18 @@ Get the createVisit Config setting. RETURN: (boolean) 1 if createVisit is set to Yes in the Config module, 0 otherwise +### getDefaultProject() + +Get the default_project Config setting. + +RETURN: value (string) of the default_project config in the Config table. + +### getDefaultCohort() + +Get the default_cohort Config setting. + +RETURN: value (string) of the default_cohort config in the Config table. + ### getPythonConfigFile() Get the MriPythonConfigFile Config setting. diff --git a/uploadNeuroDB/NeuroDB/MRI.pm b/uploadNeuroDB/NeuroDB/MRI.pm index 5746799ea..3ab1ffb7a 100755 --- a/uploadNeuroDB/NeuroDB/MRI.pm +++ b/uploadNeuroDB/NeuroDB/MRI.pm @@ -1145,6 +1145,7 @@ sub getProject { my ($subjectIDsref, $dbhr) = @_; my $PSCID = $subjectIDsref->{'PSCID'}; my $visitLabel = $subjectIDsref->{'visitLabel'}; + my $configOB = NeuroDB::objectBroker::ConfigOB->new(db => $db); ## Get the ProjectID from the session table, if the PSCID and visit labels exist ## and could be extracted @@ -1176,14 +1177,13 @@ sub getProject { } ## Otherwise, use the default_project config value - my $query = "SELECT p.ProjectID - FROM Config c - JOIN ConfigSettings cs ON c.ConfigID = cs.ID - JOIN Project p ON p.Name = c.Value - WHERE cs.Name = 'default_project'"; + my $query = "SELECT ProjectID + FROM Project + WHERE Name = ?"; + my $default_project = $configOB->getDefaultProject(); my $sth = $${dbhr}->prepare($query); - $sth->execute(); + $sth->execute($default_project); if ( $sth->rows > 0) { my $row = $sth->fetchrow_hashref(); if ($row->{'ProjectID'}) { @@ -1217,6 +1217,7 @@ sub getCohort { my ($subjectIDsref, $projectID, $dbhr) = @_; my $PSCID = $subjectIDsref->{'PSCID'}; my $visitLabel = $subjectIDsref->{'visitLabel'}; + my $configOB = NeuroDB::objectBroker::ConfigOB->new(db => $db); ## Get the CohortID from the session table, if the PSCID and visit labels exist ## and could be extracted @@ -1234,18 +1235,16 @@ sub getCohort { } ## Otherwise, use the default_cohort config value - my $query = "SELECT c.Value - FROM Config c - JOIN ConfigSettings cs ON c.ConfigID = cs.ID - WHERE cs.Name = 'default_cohort' - AND Value IN ( - SELECT title - FROM cohort - JOIN `project_cohort_rel` USING (CohortID) - WHERE ProjectID = ?)"; - + my $query = "SELECT CohortID + FROM cohort + JOIN project_cohort_rel USING (CohortID) + JOIN Project USING(ProjectID) + WHERE title = ? AND Name = ?"; + + my $default_cohort = $configOB->getDefaultCohort(); + my $default_project = $configOB->getDefaultProject(); my $sth = $${dbhr}->prepare($query); - $sth->execute($projectID); + $sth->execute($default_cohort, $default_project); if ( $sth->rows > 0) { my $row = $sth->fetchrow_hashref(); if ($row->{'Value'}) { diff --git a/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm b/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm index ec930ea42..d19aa00dd 100755 --- a/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm +++ b/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm @@ -394,7 +394,7 @@ sub determineSubjectID { my $this = shift; my ($scannerID, $tarchiveInfo, $to_log, $upload_id, $User, $centerID) = @_; - my $dbhr = $this->{dbhr}; + my $dbhr = $this->{dbhr}; $to_log = 1 unless defined $to_log; if (!defined(&Settings::getSubjectIDs)) { @@ -421,8 +421,8 @@ sub determineSubjectID { $subjectIDsref->{'ProjectID'} = $projectID; } - if (!$subjectIDsref->{'SubprojectID'}) { - $subjectIDsref->{'SubprojectID'} = NeuroDB::MRI::getCohort($subjectIDsref, $subjectIDsref->{'ProjectID'}, $dbhr); + if (!$subjectIDsref->{'CohortID'}) { + $subjectIDsref->{'CohortID'} = NeuroDB::MRI::getCohort($subjectIDsref, $subjectIDsref->{'ProjectID'}, $dbhr); } # create the candidate if it does not exist diff --git a/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm b/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm index ba9b6e622..0ae1b4f5b 100644 --- a/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm +++ b/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm @@ -65,7 +65,6 @@ use NeuroDB::objectBroker::ObjectBrokerException; use TryCatch; -<<<<<<< HEAD use constant TARCHIVE_LIBRARY_DIR => 'tarchiveLibraryDir'; use constant DATA_DIR_BASE_PATH => 'dataDirBasepath'; use constant MAIL_USER => 'mail_user'; @@ -96,6 +95,8 @@ use constant BIDS_README_TEXT => 'bids_readme_text'; use constant BIDS_VALIDATOR_OPTIONS_TO_IGNORE => 'bids_validator_options_to_ignore'; use constant CREATE_CANDIDATES => 'createCandidates'; use constant CREATE_VISIT => 'createVisit'; +use constant DEFAULT_PROJECT => 'default_project'; +use constant DEFAULT_COHORT => 'default_cohort'; =pod @@ -464,6 +465,32 @@ sub getCreateVisit { return $getBooleanRef->($value); } +=head3 getDefaultProject() + +Get the default_project Config setting. + +RETURN: value (string) of the default_project config in the Config table. + +=cut +sub getDefaultProject { + my $self = shift; + + return &$getConfigSettingRef($self, DEFAULT_PROJECT); +} + +=head3 getDefaultCohort() + +Get the default_cohort Config setting. + +RETURN: value (string) of the default_cohort config in the Config table. + +=cut +sub getDefaultCohort { + my $self = shift; + + return &$getConfigSettingRef($self, DEFAULT_COHORT); +} + =head3 getPythonConfigFile() Get the MriPythonConfigFile Config setting. From a71b8af6146bd808f177502b0fc9a8bc524db68a Mon Sep 17 00:00:00 2001 From: Laetitia Fesselier Date: Sat, 4 Mar 2023 17:55:42 -0500 Subject: [PATCH 4/4] Documentation and updates --- dicom-archive/profileTemplate.pl | 95 +++++++++++-------- docs/02-Install.md | 22 ++++- uploadNeuroDB/NeuroDB/MRI.pm | 18 ++-- uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm | 18 +++- .../NeuroDB/objectBroker/ConfigOB.pm | 8 +- uploadNeuroDB/imaging_non_minc_insertion.pl | 2 +- uploadNeuroDB/minc_insertion.pl | 2 +- uploadNeuroDB/tarchiveLoader.pl | 2 +- 8 files changed, 106 insertions(+), 61 deletions(-) diff --git a/dicom-archive/profileTemplate.pl b/dicom-archive/profileTemplate.pl index e3527affc..00c29873c 100755 --- a/dicom-archive/profileTemplate.pl +++ b/dicom-archive/profileTemplate.pl @@ -40,36 +40,45 @@ sub getSubjectIDs { # If patientName is phantom scan or test scan # CandID is scanner DCCID (based on site alias) # visitLabel is scan patient name - # Set createVisitLable to - # a. 1 if imaging pipeline should create the visit label (when visit label has not been created yet in the database. - # b. 0 if imaging pipeline should not create the visit label (when visit label has not been created yet in the database. if ($patientName =~ /PHA/i or $patientName =~ /TEST/i) { $subjectID{'CandID'} = NeuroDB::MRI::my_trim(NeuroDB::MRI::getScannerCandID($scannerID, $db)); $subjectID{'visitLabel'} = NeuroDB::MRI::my_trim($patientName); $subjectID{'isPhantom'} = 1; - $subjectID{'createVisitLabel'} = 1; - - # $subjectID{'CohortID'} = undef; - # When createVisitLabel is set to 1, CohortID must also - # be set to the ID of the cohort that the newly created - # visit should have. Assuming for example that all patient - # names end with "_", then we could write: - # ($subjectID{'CohortID'}) = $patientName =~ /_(\d+)$/; - # When createVisitLabel is set to 0, $subjectID{'CohortID'} is ignored. + # Override createVisitLabel here if its value needs to be different than the createVisit DB config + # $subjectID{'createVisitLabel'} = undef; + # Set createVisitLabel to + # a. 1 if imaging pipeline should create the visit label (when visit label has not been created yet in the database. + # b. 0 if imaging pipeline should not create the visit label (when visit label has not been created yet in the database. + # + # When $subjectID{'createVisitLabel'} is set to 1: + # - $subjectID{'ProjectID'} must be set to the project ID of the newly created visit + # - $subjectID{'CohortID'} must be set to the cohort ID of the newly created visit + # + # If $subjectID{'ProjectID'} is undef, the following rules will be tried in order to assign a default value: + # - the ProjectID from the session table, if the PSCID and visit labels exist + # - the ProjectID from the candidate table, if the PSCID exists + # - the default_project DB config value + # + # If $subjectID{'CohortID'} is undef, the following rules will be tried in order to assign a default value: + # - the CohortID from the session table, if the PSCID and visit labels exist + # - the default_cohort DB config value + # + # When createVisitLabel is set to 0, $subjectID{'ProjectID'} and $subjectID{'CohortID'} are ignored. # $subjectID{'ProjectID'} = undef; - # If config setting 'createVisitLabel' is true - # then $subjectID{'ProjectID'} must be set to the project ID of the - # newly created visit. Assuming for example that all patients - # names that contain the string 'HOSPITAL' are associated to visit + # Assuming that all patient names that contain the string 'HOSPITAL' are associated to visit # done for project with ID 1 and all others to projects with ID 2, we # could write: - # $subjectID{'ProjectID'} = $patientName =~ /HOSPITAL/ - # ? 1 : 2; + # $subjectID{'ProjectID'} = $patientName =~ /HOSPITAL/ ? 1 : 2; # When createVisitLabel is set to 0, $subjectID{'ProjectID'} is ignored. + # $subjectID{'CohortID'} = undef; + # Assuming that all patient names end with "_", then we could write: + # $subjectID{'CohortID'} = $patientName =~ /_(\d+)$/; + # When createVisitLabel is set to 0, $subjectID{'CohortID'} is ignored. + # If patient match PSCID_DCCID_VisitLabel # Determine PSCID, DCCID and visitLabel based on patient name } elsif ($patientName =~ /([^_]+)_(\d+)_([^_]+)/) { @@ -79,28 +88,38 @@ sub getSubjectIDs { $subjectID{'visitLabel'} = NeuroDB::MRI::my_trim($3); $subjectID{'isPhantom'} = 0; - $subjectID{'createVisitLabel'} = 0; - - # $subjectID{'CohortID'} = undef; - # When createVisitLabel is set to 1, CohortID must also - # be set to the ID of the cohort that the newly created - # visit should have. Assuming for example that visits V01 and V02 - # are associated with cohort with ID 1 and all others to cohort - # with ID 2, then we could write: - # ($subjectID{'CohortID'}) = $subjectID{'visitLabel'} =~ /^V0[12]$/ - # ? 1 : 2; - # When createVisitLabel is set to 0, $subjectID{'CohortID'} is ignored. - + # Override createVisitLabel here if its value needs to be different than the createVisit DB config + # $subjectID{'createVisitLabel'} = undef; + # Set createVisitLabel to + # a. 1 if imaging pipeline should create the visit label (when visit label has not been created yet in the database. + # b. 0 if imaging pipeline should not create the visit label (when visit label has not been created yet in the database. + # + # When $subjectID{'createVisitLabel'} is set to 1: + # - $subjectID{'ProjectID'} must be set to the project ID of the newly created visit + # - $subjectID{'CohortID'} must be set to the cohort ID of the newly created visit + # + # If $subjectID{'ProjectID'} is undef, the following rules will be tried in order to assign a default value: + # - the ProjectID from the session table, if the PSCID and visit labels exist + # - the ProjectID from the candidate table, if the PSCID exists + # - the default_project DB config value + # + # If $subjectID{'CohortID'} is undef, the following rules will be tried in order to assign a default value: + # - the CohortID from the session table, if the PSCID and visit labels exist + # - the default_cohort DB config value + # + # When createVisitLabel is set to 0, $subjectID{'ProjectID'} and $subjectID{'CohortID'} are ignored. + # $subjectID{'ProjectID'} = undef; - # If config setting 'createVisitLabel' is true - # then $subjectID{'ProjectID'} must be set to the project ID of the - # newly created visit. Assuming for example that candidates with a - # candidate ID greater than 400000 are seen in project 1 and others are - # seen in project 2, we could write - # could write: + # Assuming for example that candidates with a candidate ID greater than 400000 are seen in project 1 + # and others are seen in project 2, we could write: # $subjectID{'ProjectID'} = $subjectID{'CandID'} > 400000 ? 1 : 2; - # ? 1 : 2; - # When createVisitLabel and createCandidates are set to 0, $subjectID{'ProjectID'} is ignored. + # When createVisitLabel is set to 0, $subjectID{'ProjectID'} is ignored. + + # $subjectID{'CohortID'} = undef; + # Assuming for example that visits V01 and V02 are associated with cohort with ID 1 and all others + # to cohort with ID 2, then we could write: + # $subjectID{'CohortID'} = $subjectID{'visitLabel'} =~ /^V0[12]$/ ? 1 : 2; + # When createVisitLabel is set to 0, $subjectID{'CohortID'} is ignored. print "PSCID is: " . $subjectID{'PSCID'} . "\n CandID id: " . $subjectID{'CandID'} . diff --git a/docs/02-Install.md b/docs/02-Install.md index e728bb4e5..f390025d4 100644 --- a/docs/02-Install.md +++ b/docs/02-Install.md @@ -152,8 +152,24 @@ Under the `Imaging Pipeline` section: typically `/data/$PROJECT/data/tarchive/` * `Patient identifiers and center name lookup variable`: DICOM header that contains the LORIS candidate identifiers; typically `PatientName` - * `Upload creation of candidates`: enable or disable candidate creation into LORIS + * `Enable candidate creation`: enable or disable candidate creation into LORIS when running the insertion pipeline + * `Enable visit creation`: enable or disable visit creation into LORIS + when running the insertion pipeline + * `Default project`: Default cohort used when Enable visit creation is set to true. This value is used when + the following rules fails: + - the $subjectID{'ProjectID'} is undef in the profileTemplate (prod) file; + - the ProjectID from the session table, if the PSCID and visit labels exist; + - the ProjectID from the candidate table, if the PSCID exists. + * `Default cohort`: Default cohort used when Enable visit creation is set to true. This value is used when + the following rules fails: + - the $subjectID{'CohortID'} is undef in the profileTemplate (prod) file; + - the CohortID from the session table, if the PSCID and visit labels exist; + - the default_cohort DB config value. + * `Default visit label for BIDS dataset`: the visit directory in BIDS + structure is optional in the case of only one visit for the whole dataset. In + this case, we need to specify to LORIS what would be the default visit label + the project wants to use to store the electrophysiology datasets (*e.g.* V01). * `Project batch management used`: enable or disable batch management * `Number of volumes in native DTI acquisitions`: used by the DTIPrep pipeline * `Scan type of native T1 acquisition`: name as specified in the `mri_scan_type` @@ -170,10 +186,6 @@ Under the `Imaging Pipeline` section: control. Feature to be integrated in the code base in a **future** release. * `Name of the Perl MRI config file`: name of the perl-based MRI config file to use when running the Perl insertion scripts; typically `prod`; used when Auto launch is turned on. - * `Default visit label for BIDS dataset`: the visit directory in BIDS - structure is optional in the case of only one visit for the whole dataset. In - this case, we need to specify to LORIS what would be the default visit label - the project wants to use to store the electrophysiology datasets (*e.g.* V01). * `Name of the environment file`: name of the MRI environment file to source before running the insertion scripts; typically `environment`; used when Auto-launch is turned on for the pipeline. diff --git a/uploadNeuroDB/NeuroDB/MRI.pm b/uploadNeuroDB/NeuroDB/MRI.pm index 3ab1ffb7a..f2deb47ae 100755 --- a/uploadNeuroDB/NeuroDB/MRI.pm +++ b/uploadNeuroDB/NeuroDB/MRI.pm @@ -140,7 +140,6 @@ RETURNS: an array of 2 elements: sub getSessionInformation { my ($subjectIDref, $studyDate, $dbh, $db) = @_; - my $configOB = NeuroDB::objectBroker::ConfigOB->new(db => $db); my ($sessionID, $studyDateJD); my ($query, $sth); @@ -168,7 +167,7 @@ sub getSessionInformation { return (\%session, ''); } - if (!$configOB->getCreateVisit()) { + if (!$subjectIDref->{'createVisitLabel'}) { my $msg = sprintf( "Visit %s for candidate %d does not exist.", $subjectIDref->{'visitLabel'}, @@ -279,7 +278,6 @@ sub getSessionInformation { Visit_label => $subjectIDref->{'visitLabel'}, CandID => $subjectIDref->{'CandID'} ); - return (\%session, ''); } @@ -1127,7 +1125,7 @@ sub getPSC { =pod -=head3 getProject($patientName, $dbhr, $db) +=head3 getProject($subjectIDsref, $dbhr, $db) Looks for the project id using the C table C as a first resource, then using the C table C, @@ -1136,13 +1134,14 @@ otherwise, look for the default_project config value, and return C. INPUTS: - $subjectIDsref: subject's information hash ref - $dbhr : database handle reference + - $db : database object RETURNS: the C or an error if not found =cut sub getProject { - my ($subjectIDsref, $dbhr) = @_; + my ($subjectIDsref, $dbhr, $db) = @_; my $PSCID = $subjectIDsref->{'PSCID'}; my $visitLabel = $subjectIDsref->{'visitLabel'}; my $configOB = NeuroDB::objectBroker::ConfigOB->new(db => $db); @@ -1198,7 +1197,7 @@ sub getProject { =pod -=head3 getCohort($subjectIDsref, $projectID, $dbhr) +=head3 getCohort($subjectIDsref, $projectID, $dbhr, $db) Looks for the cohort id using the C table C as a first resource, for the cases where it is created using the front-end, @@ -1208,13 +1207,14 @@ INPUTS: - $subjectIDsref: subject's information hash ref - $projectID : the project ID - $dbhr : database handle reference + - $db : database object RETURNS: the C or 0 =cut sub getCohort { - my ($subjectIDsref, $projectID, $dbhr) = @_; + my ($subjectIDsref, $projectID, $dbhr, $db) = @_; my $PSCID = $subjectIDsref->{'PSCID'}; my $visitLabel = $subjectIDsref->{'visitLabel'}; my $configOB = NeuroDB::objectBroker::ConfigOB->new(db => $db); @@ -1247,9 +1247,7 @@ sub getCohort { $sth->execute($default_cohort, $default_project); if ( $sth->rows > 0) { my $row = $sth->fetchrow_hashref(); - if ($row->{'Value'}) { - return $row->{'Value'}; - } + return $row->{'CohortID'}; } return ("UNKN", 0); diff --git a/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm b/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm index d19aa00dd..68d98546e 100755 --- a/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm +++ b/uploadNeuroDB/NeuroDB/MRIProcessingUtility.pm @@ -416,13 +416,20 @@ sub determineSubjectID { $patientName, $patientID, $scannerID, $this->{dbhr}, $this->{'db'} ); + if (!$subjectIDsref->{'createVisitLabel'}) { + my $configOB = $this->{'configOB'}; + $subjectIDsref->{'createVisitLabel'} = $configOB->getCreateVisit(); + } + if (!$subjectIDsref->{'ProjectID'}) { - my $projectID = NeuroDB::MRI::getProject($subjectIDsref, $dbhr); + my $projectID = NeuroDB::MRI::getProject($subjectIDsref, $dbhr, $this->{'db'}); $subjectIDsref->{'ProjectID'} = $projectID; } if (!$subjectIDsref->{'CohortID'}) { - $subjectIDsref->{'CohortID'} = NeuroDB::MRI::getCohort($subjectIDsref, $subjectIDsref->{'ProjectID'}, $dbhr); + $subjectIDsref->{'CohortID'} = NeuroDB::MRI::getCohort( + $subjectIDsref, $subjectIDsref->{'ProjectID'}, $dbhr, $this->{'db'} + ); } # create the candidate if it does not exist @@ -1942,7 +1949,6 @@ or a phantom sub validateCandidate { my $this = shift; - my $configOB = $this->{'configOB'}; my ($subjectIDsref, $upload_id) = @_; my ($CandMismatchError, $message); @@ -2006,13 +2012,17 @@ sub validateCandidate { # if we end up here, it means that the visit label was not found in Visit_Windows # therefore need to check if 'createVisitLabel' was set + if ($subjectIDsref->{'createVisitLabel'}) { - if ($configOB->getCreateVisit()) { $message = "\n=> Will create visit label $visit_label in Visit_Windows\n"; + } else { + $message = "\n=> No Visit label\n"; $this->writeErrorLog($message, $NeuroDB::ExitCodes::INSERT_FAILURE); + return "Visit label $visit_label does not exist in Visit_Windows"; + } # write the message about the visit label in the notification spool table diff --git a/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm b/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm index 0ae1b4f5b..e86428f1f 100644 --- a/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm +++ b/uploadNeuroDB/NeuroDB/objectBroker/ConfigOB.pm @@ -178,7 +178,13 @@ RETURN: 1 if the value provided is 'true' or '1'; 0 otherwise my $getBooleanRef = sub { my ($value) = @_; - return ($value eq "true" || $value == 1) ? 1 : 0; + if ($value eq "true") { + $value = 1; + } elsif ($value eq "false") { + $value = 0; + } + + return ($value == 1) ? 1 : 0; }; =head3 getTarchiveLibraryDir() diff --git a/uploadNeuroDB/imaging_non_minc_insertion.pl b/uploadNeuroDB/imaging_non_minc_insertion.pl index 0f656a201..02f1a4ef1 100755 --- a/uploadNeuroDB/imaging_non_minc_insertion.pl +++ b/uploadNeuroDB/imaging_non_minc_insertion.pl @@ -475,7 +475,7 @@ =head2 Methods 'imaging_non_minc_insertion.pl' , $upload_id, 'Y', 'N' ); - exit ($configOB->getCreateVisit() == 1 + exit ($subjectIDsref->{'createVisitLabel'} == 1 ? $NeuroDB::ExitCodes::CREATE_SESSION_FAILURE : $NeuroDB::ExitCodes::GET_SESSION_ID_FAILURE); } diff --git a/uploadNeuroDB/minc_insertion.pl b/uploadNeuroDB/minc_insertion.pl index ef7283543..0eb4aaeba 100755 --- a/uploadNeuroDB/minc_insertion.pl +++ b/uploadNeuroDB/minc_insertion.pl @@ -558,7 +558,7 @@ =head2 Methods 'minc_insertion.pl', $upload_id, 'Y', $notify_notsummary ); - exit ($configOB->getCreateVisit() == 1 + exit ($subjectIDsref->{'createVisitLabel'} == 1 ? $NeuroDB::ExitCodes::CREATE_SESSION_FAILURE : $NeuroDB::ExitCodes::GET_SESSION_ID_FAILURE); } diff --git a/uploadNeuroDB/tarchiveLoader.pl b/uploadNeuroDB/tarchiveLoader.pl index 8d84a0e47..4d6dc072b 100755 --- a/uploadNeuroDB/tarchiveLoader.pl +++ b/uploadNeuroDB/tarchiveLoader.pl @@ -570,7 +570,7 @@ =head2 Methods 'tarchiveLoader.pl', $upload_id, 'Y', $notify_notsummary ); - exit ($configOB->getCreateVisit() == 1 + exit ($subjectIDsref->{'createVisitLabel'} == 1 ? $NeuroDB::ExitCodes::CREATE_SESSION_FAILURE : $NeuroDB::ExitCodes::GET_SESSION_ID_FAILURE); }