From 32dda973983cdda9f3e8919dfcc1e66b39bd7ac8 Mon Sep 17 00:00:00 2001 From: mohsentaba Date: Sat, 12 Sep 2026 11:40:57 +0330 Subject: [PATCH] fix(sqlite-export): include full rich reference details, book metadata and absolute image urls for corrections and interpretations --- .../commands/export_hadis_sqlite.py | 143 +++++++++++++++--- 1 file changed, 121 insertions(+), 22 deletions(-) diff --git a/apps/hadis/management/commands/export_hadis_sqlite.py b/apps/hadis/management/commands/export_hadis_sqlite.py index 91bdde5..c0037e0 100644 --- a/apps/hadis/management/commands/export_hadis_sqlite.py +++ b/apps/hadis/management/commands/export_hadis_sqlite.py @@ -14,6 +14,10 @@ from apps.hadis.models import ( HadisCorrection, HadisDatabaseVersion ) +from apps.hadis.serializers.hadis import ( + DetailedCorrectionReferenceSerializer, + DetailedInterpretationReferenceSerializer, +) class Command(BaseCommand): @@ -250,25 +254,118 @@ class Command(BaseCommand): ) return len(rows) + def _make_full_url(self, url): + if not url: + return '' + if url.startswith('http://') or url.startswith('https://'): + return url + if not url.startswith('/'): + url = '/' + url + return f'https://dovodi.newhorizonco.uk{url}' + + def _serialize_reference(self, ref): + book = getattr(ref, 'book_reference', None) + author = book.author if book and getattr(book, 'author', None) else None + ed = getattr(ref, 'edition', None) + vol_obj = getattr(ref, 'book_volume', None) + + images_list = [] + if hasattr(ref, 'images'): + for img in ref.images.all(): + if img.image: + img_url = self._make_full_url(img.image.url) + thumb_url = self._make_full_url(img.thumbnail.url if getattr(img, 'thumbnail', None) else img.image.url) + images_list.append({ + 'id': img.id, + 'image': img_url, + 'thumbnail': thumb_url, + 'priority': getattr(img, 'priority', 0), + }) + + book_dict = { + 'id': book.id, + 'slug': book.slug, + 'title': book.title, + 'publisher': getattr(book, 'publisher', '') or '', + 'year_of_publication': getattr(book, 'year_of_publication', '') or '', + 'number_of_volumes': getattr(book, 'number_of_volumes', None), + } if book else None + + author_dict = { + 'id': author.id, + 'slug': author.slug, + 'name': author.name, + } if author else None + + edition_dict = { + 'id': ed.id, + 'edition_number': ed.edition_number, + 'publisher': getattr(ed, 'publisher', '') or '', + 'year_of_publication': getattr(ed, 'year_of_publication', '') or '', + 'number_of_volumes': getattr(ed, 'number_of_volumes', None), + } if ed else None + + volume_info = { + 'id': vol_obj.id, + 'title': vol_obj.title, + } if vol_obj else None + + open_book_url = None + if getattr(ref, 'url', None): + open_book_url = ref.url + elif vol_obj and getattr(vol_obj, 'file', None): + open_book_url = self._make_full_url(vol_obj.file.url) + elif ed and getattr(ed, 'source_url', None): + open_book_url = ed.source_url + elif book and getattr(book, 'slug', None): + open_book_url = f"/arguments/sources/{book.slug}" + + parts = [] + vol_val = getattr(ref, 'volume', None) or (vol_obj.title if vol_obj else None) + if vol_val: + v_str = str(vol_val).strip() + parts.append(v_str if v_str.startswith("جلد") else f"جلد {v_str}") + pg_val = getattr(ref, 'pages', None) + if pg_val: + p_str = str(pg_val).strip() + parts.append(p_str if (p_str.startswith("ص") or p_str.startswith("صفحه")) else f"صفحه {p_str}") + num_val = getattr(ref, 'hadith_number', None) + if num_val: + n_str = str(num_val).strip() + parts.append(n_str if (n_str.startswith("ح") or n_str.startswith("حدیث") or n_str.startswith("شماره")) else f"شماره حدیث {n_str}") + citation_summary = " • ".join(parts) if parts else "" + + return { + 'id': ref.id, + 'book': book_dict, + 'author': author_dict, + 'edition': edition_dict, + 'volume_info': volume_info, + 'hadith_number': getattr(ref, 'hadith_number', None), + 'volume': vol_val, + 'pages': pg_val, + 'address': getattr(ref, 'address', None), + 'url': getattr(ref, 'url', None), + 'open_book_url': open_book_url, + 'citation_summary': citation_summary, + 'images': images_list, + 'images_count': len(images_list), + 'book_title': getattr(book, 'title', None) if book else None, + 'book_authors': [{'id': author.id, 'name': author.name, 'slug': author.slug}] if author else [], + 'edition_info': getattr(ed, 'publisher', None) if ed else None, + } + def _export_category_interpretations(self, cursor): interps = HadisInterpretation.objects.select_related('category').prefetch_related( - 'references__book_reference', 'references__images' + 'references__book_reference__author', + 'references__images', + 'references__edition', + 'references__book_volume', ).all() rows = [] for inp in interps: - refs_list = [] - for ref in inp.references.all(): - book = ref.book_reference - refs_list.append({ - 'id': ref.id, - 'book_title': getattr(book, 'title', None), - 'address': getattr(ref, 'address', None), - 'edition': getattr(ref, 'edition_id', None), - 'volume': getattr(ref, 'volume_id', None), - 'pages': getattr(ref, 'pages', None), - 'hadith_number': getattr(ref, 'hadith_number', None), - }) + refs_list = [self._serialize_reference(ref) for ref in inp.references.all()] rows.append(( inp.id, @@ -302,6 +399,9 @@ class Command(BaseCommand): 'transmitters__transmitter__reliability', 'transmitters__uncertain_transmitters__reliability', 'transmitters__narrator_layer', + 'hadiscorrection_set__references__book_reference__author', + 'hadiscorrection_set__references__edition', + 'hadiscorrection_set__references__book_volume', 'hadiscorrection_set__references__images', ) .order_by('id') @@ -335,7 +435,7 @@ class Command(BaseCommand): for img in ref.images.all(): ref_imgs_list.append({ 'id': img.id, - 'thumbnail': img.thumbnail.url if img.thumbnail else None, + 'thumbnail': self._make_full_url(img.thumbnail.url if img.thumbnail else None), 'priority': img.priority, }) @@ -403,13 +503,12 @@ class Command(BaseCommand): corr_imgs = [] corr_refs = [] for cref in corr.references.all(): - for cimg in cref.images.all(): - if cimg.image: - corr_imgs.append({'id': cimg.id, 'image': cimg.image.url}) - corr_refs.append({ - 'id': cref.id, - 'address': getattr(cref, 'address', None), - }) + ref_data = self._serialize_reference(cref) + corr_refs.append(ref_data) + if ref_data.get('images'): + corr_imgs.extend(ref_data['images']) + + corr_address = corr_refs[0].get('address') or '' if corr_refs else '' correction_rows.append(( corr.id, @@ -420,7 +519,7 @@ class Command(BaseCommand): corr.text or '', json.dumps(corr.translation, ensure_ascii=False) if isinstance(corr.translation, (dict, list)) else (corr.translation or ''), corr.share_link or '', - corr.address if hasattr(corr, 'address') else '', + corr_address, json.dumps(corr_imgs, ensure_ascii=False), json.dumps(corr_refs, ensure_ascii=False), json.dumps(corr.links or [], ensure_ascii=False),