i should break these commits up

This commit is contained in:
Ross
2024-04-08 14:16:13 +01:00
parent f13d1ba7e2
commit 98756baa37
25 changed files with 839 additions and 366 deletions
+67 -33
View File
@@ -311,20 +311,32 @@ class Case(models.Model, AuthorMixin, QuestionMixin):
# findings = models.TextField(null=True, blank=True)
# subspecialty = models.CharField(max_length=2, choices=SubspecialtyChoices.choices)
subspecialty = models.ManyToManyField(Subspecialty, blank=True)
subspecialty = models.ManyToManyField(
Subspecialty,
blank=True,
help_text="The subspecialties the case is associated with. Multiple subspecialties can be selected.",
)
condition = models.ManyToManyField(Condition, blank=True)
condition = models.ManyToManyField(
Condition, blank=True, help_text="The condition(s) the case demonstrates."
)
presentation = models.ManyToManyField(Presentation, blank=True)
presentation = models.ManyToManyField(
Presentation,
blank=True,
help_text="The presentation(s) the case is associated with.",
)
pathological_process = models.ManyToManyField(PathologicalProcess, blank=True)
differential = models.ManyToManyField(
Condition, through=Differential, related_name="casedifferential"
Condition, through=Differential, related_name="casedifferential",
help_text="The differential diagnosis for the case.",
)
diagnostic_certainty = models.IntegerField(
choices=CertaintyChoices.choices, default=CertaintyChoices.NONE
choices=CertaintyChoices.choices, default=CertaintyChoices.NONE,
help_text="The diagnostic certainty of the case.",
)
verified = models.BooleanField(default=False)
@@ -352,7 +364,9 @@ class Case(models.Model, AuthorMixin, QuestionMixin):
help_text="If a case should be freely available to browse", default=True
)
series = models.ManyToManyField("Series", through="SeriesDetail", related_name="case")
series = models.ManyToManyField(
"Series", through="SeriesDetail", related_name="case"
)
notes = GenericRelation(QuestionNote)
@@ -362,6 +376,7 @@ class Case(models.Model, AuthorMixin, QuestionMixin):
null=True,
related_name="next_case",
blank=True,
help_text="If this case is related to another case on the system (e.g. follow up), link them here.",
)
resource = models.ManyToManyField("Resource", through="CaseResource")
@@ -378,12 +393,15 @@ class Case(models.Model, AuthorMixin, QuestionMixin):
# return f"{self.pk}: {self.title}"
return format_html("<a href='{}'>{}</a>", self.get_absolute_url(), str(self))
#def get_base_template(self):
# def get_base_template(self):
#def get_edit_template_links(self):
# def get_edit_template_links(self):
def __str__(self):
return f"{self.pk}: {self.title}"
if self.open_access:
return f"{self.pk}: {self.title} [OA]"
else:
return f"{self.pk}: {self.title}"
def get_series_blocks(self):
html = ""
@@ -396,7 +414,7 @@ class Case(models.Model, AuthorMixin, QuestionMixin):
examinations = [series.get_examination() for series in self.series.all()]
return f"{self.pk}:{self.title} {'/'.join([str(c) for c in self.condition.all()])} [{', '.join(examinations)}]"
def get_case_dicom_json(self, case_title_as_patient_name = True):
def get_case_dicom_json(self, case_title_as_patient_name=True):
series_json = []
for series in self.series.all():
series_json.append(series.get_series_dicom_json())
@@ -435,7 +453,6 @@ class Case(models.Model, AuthorMixin, QuestionMixin):
return json.dumps(self.get_viva_details())
def extract_image_dicom_json_from_ds(ds, url, image_index):
to_keep = [
"Columns",
@@ -597,7 +614,7 @@ class Series(SeriesBase):
"<a href='{}'>{}</a>", self.get_absolute_url(), self.get_full_str()
)
#@lru_cache(maxsize=128)
# @lru_cache(maxsize=128)
def get_series_dicom_json(self):
instances = []
@@ -662,12 +679,13 @@ class Series(SeriesBase):
image = self.images.first()
with pydicom.dcmread(image.image) as ds:
date = ds.get("StudyDate", "No date")
date = ds.get("StudyDate", "No date")
self.description = f"{date[:4]}-{date[4:6]}-{date[6:]}"
self.save()
class CaseCollection(ExamOrCollectionGenericBase):
app_name = "atlas"
@@ -806,9 +824,13 @@ class CaseCollection(ExamOrCollectionGenericBase):
self.VIEWER_MODE_CHOICES.BUILT_IN_WITH_OHIF,
)
def show_ohif_viewer_link(self) -> bool:
def show_ohif_viewer(self) -> bool:
return self.viewer_mode in (
self.VIEWER_MODE_CHOICES.OHIF,
)
def show_ohif_viewer_link(self) -> bool:
return self.viewer_mode in (
self.VIEWER_MODE_CHOICES.BUILT_IN_WITH_OHIF,
)
@@ -843,9 +865,7 @@ class CaseCollection(ExamOrCollectionGenericBase):
) -> Case | Tuple[Case, int]:
# Seems to be a bug when case_number is 0 or 1 the same (first) object gets returned
# forces a list fixes (but is likely inefficient)
cases = list(
self.get_cases().prefetch_related()
)
cases = list(self.get_cases().prefetch_related())
try:
case = cases[case_index]
@@ -859,16 +879,14 @@ class CaseCollection(ExamOrCollectionGenericBase):
return case
def get_case_take_url(self, case):
cases = list(
self.get_cases().prefetch_related()
)
cases = list(self.get_cases().prefetch_related())
return reverse(
"atlas:collection_case_view_take_user",
kwargs={"pk": self.pk, "case_number": cases.index(case)},
)
def get_ohif_dicom_json(self, case_title_as_patient_name = True):
def get_ohif_dicom_json(self, case_title_as_patient_name=True):
studies = []
for n, case in enumerate(self.cases.all()):
series_json = []
@@ -880,7 +898,6 @@ class CaseCollection(ExamOrCollectionGenericBase):
patient_name = case.title
studies.append(
{
"StudyInstanceUID": f"1.3.6.1.4.1.14519.5.2.1.6279.6001.{n}",
"StudyDate": "20000101",
@@ -894,21 +911,16 @@ class CaseCollection(ExamOrCollectionGenericBase):
}
)
return {
"studies": studies
}
return {"studies": studies}
def add_case(self, case):
"""Adds a case to the collection and makes sure order is maintained"""
# We might be better off adding via the case detail model direct
#CaseDetail.objects.create(case=case, collection=self)
# CaseDetail.objects.create(case=case, collection=self)
self.cases.add(case)
self.order_cases()
def order_cases(self):
def order_cases(self):
"""Modifies the casedetail sort_order to sequentially order the cases"""
for n, c in enumerate(self.casedetail_set.all().order_by("sort_order")):
c.sort_order = n
@@ -921,11 +933,15 @@ class SeriesDetail(models.Model):
sort_order = models.IntegerField(default=1000)
feedback = models.BooleanField(default=False, help_text="Set to true if the series should only be shown for feedback purposes.")
feedback = models.BooleanField(
default=False,
help_text="Set to true if the series should only be shown for feedback purposes.",
)
class Meta:
ordering = ("sort_order",)
class CaseDetail(models.Model):
case = models.ForeignKey(Case, on_delete=models.CASCADE)
collection = models.ForeignKey(CaseCollection, on_delete=models.CASCADE)
@@ -950,6 +966,8 @@ class BaseReportAnswer(models.Model):
blank=True, null=True, validators=[MaxValueValidator(10), MinValueValidator(0)]
)
completed = models.BooleanField(default=False)
def save(self, *args, **kwargs):
self.clean()
return super(BaseReportAnswer, self).save(*args, **kwargs)
@@ -1145,6 +1163,7 @@ class UncategorisedDicom(models.Model):
class DuplicateDicom(Exception):
pass
class Resource(models.Model, AuthorMixin):
name = models.CharField(max_length=255)
description = models.TextField(blank=True, null=True)
@@ -1166,11 +1185,26 @@ class Resource(models.Model, AuthorMixin):
def get_link(self):
return format_html("<a href='{}'>{}</a>", self.get_absolute_url(), self.name)
def get_display(self) -> str:
if self.url:
html = f"<a target='_blank' href='{self.url}'>{self.name}</a>"
elif self.file:
html = f"<a target='_blank' href='{self.file.url}'>{self.name}</a>"
else:
html = self.name
return format_html(html)
class CaseResource(models.Model):
resource = models.ForeignKey(Resource, on_delete=models.CASCADE)
case = models.ForeignKey(Case, on_delete=models.CASCADE)
pre_review = models.BooleanField(default=False)
pre_review = models.BooleanField(
default=False,
help_text="Defines if the resource should be shown pre review (i.e. for pre reading before the case is taken)",
)
def __str__(self) -> str:
return f"{self.resource} - {self.case}"
return f"{self.resource} - {self.case} (Pre: {self.pre_review})"