From 737ac54c1b2ef80b431db86fa35f6d587d3bc8ce Mon Sep 17 00:00:00 2001 From: salahangal Date: Mon, 17 Nov 2025 13:49:40 +0100 Subject: [PATCH] fix ingestion tests errors --- hadith-ingestion/.env | 3 +- ...est_hadithapi.cpython-311-pytest-7.4.0.pyc | Bin 0 -> 5518 bytes ...mainhadithapi.cpython-311-pytest-7.4.0.pyc | Bin 0 -> 6150 bytes .../__pycache__/settings.cpython-312.pyc | Bin 3556 -> 3491 bytes .../__pycache__/settings.cpython-38.pyc | Bin 2757 -> 2710 bytes hadith-ingestion/config/settings.py | 8 +- .../src/__pycache__/__init__.cpython-311.pyc | Bin 0 -> 206 bytes .../main_hadithapi.cpython-311.pyc | Bin 0 -> 19329 bytes .../main_hadithapi.cpython-312.pyc | Bin 0 -> 17198 bytes .../__pycache__/main_hadithapi.cpython-38.pyc | Bin 0 -> 9965 bytes .../__pycache__/__init__.cpython-311.pyc | Bin 0 -> 218 bytes .../hadithapi_client.cpython-311.pyc | Bin 0 -> 11155 bytes .../hadithapi_client.cpython-312.pyc | Bin 9795 -> 9799 bytes .../__pycache__/__init__.cpython-312.pyc | Bin 0 -> 203 bytes .../__pycache__/__init__.cpython-38.pyc | Bin 0 -> 197 bytes .../__pycache__/repository.cpython-312.pyc | Bin 0 -> 16578 bytes hadith-ingestion/src/database/repository.py | 86 ++++++++------ hadith-ingestion/src/main_hadithapi.py | 50 ++++---- .../__pycache__/__init__.cpython-312.pyc | Bin 0 -> 205 bytes .../__pycache__/text_cleaner.cpython-312.pyc | Bin 0 -> 6611 bytes hadith-ingestion/test_mainhadithapi.py | 109 ++++++++++++++++++ .../__pycache__/__init__.cpython-311.pyc | Bin 0 -> 208 bytes .../test_clients.cpython-311-pytest-7.4.0.pyc | Bin 0 -> 212 bytes 23 files changed, 194 insertions(+), 62 deletions(-) create mode 100644 hadith-ingestion/__pycache__/test_hadithapi.cpython-311-pytest-7.4.0.pyc create mode 100644 hadith-ingestion/__pycache__/test_mainhadithapi.cpython-311-pytest-7.4.0.pyc create mode 100644 hadith-ingestion/src/__pycache__/__init__.cpython-311.pyc create mode 100644 hadith-ingestion/src/__pycache__/main_hadithapi.cpython-311.pyc create mode 100644 hadith-ingestion/src/__pycache__/main_hadithapi.cpython-312.pyc create mode 100644 hadith-ingestion/src/__pycache__/main_hadithapi.cpython-38.pyc create mode 100644 hadith-ingestion/src/api_clients/__pycache__/__init__.cpython-311.pyc create mode 100644 hadith-ingestion/src/api_clients/__pycache__/hadithapi_client.cpython-311.pyc create mode 100644 hadith-ingestion/src/database/__pycache__/__init__.cpython-312.pyc create mode 100644 hadith-ingestion/src/database/__pycache__/__init__.cpython-38.pyc create mode 100644 hadith-ingestion/src/database/__pycache__/repository.cpython-312.pyc create mode 100644 hadith-ingestion/src/processors/__pycache__/__init__.cpython-312.pyc create mode 100644 hadith-ingestion/src/processors/__pycache__/text_cleaner.cpython-312.pyc create mode 100644 hadith-ingestion/test_mainhadithapi.py create mode 100644 hadith-ingestion/tests/__pycache__/__init__.cpython-311.pyc create mode 100644 hadith-ingestion/tests/__pycache__/test_clients.cpython-311-pytest-7.4.0.pyc diff --git a/hadith-ingestion/.env b/hadith-ingestion/.env index db27494..ce151b8 100644 --- a/hadith-ingestion/.env +++ b/hadith-ingestion/.env @@ -1,5 +1,6 @@ # Database -DATABASE_HOST=postgres.db.svc.cluster.local +# DATABASE_HOST=postgres.db.svc.cluster.local +DATABASE_HOST = pg.betelgeusebytes.io DATABASE_PORT=5432 DATABASE_NAME=hadith_db DATABASE_USER=hadith_ingest diff --git a/hadith-ingestion/__pycache__/test_hadithapi.cpython-311-pytest-7.4.0.pyc b/hadith-ingestion/__pycache__/test_hadithapi.cpython-311-pytest-7.4.0.pyc new file mode 100644 index 0000000000000000000000000000000000000000..030be74f4e0282e5fae8cddb4b25307aeb8a891c GIT binary patch literal 5518 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 VQq30CY?OPEMpP3_QwG4c{{Sw1W>NqE literal 0 HcmV?d00001 diff --git a/hadith-ingestion/__pycache__/test_mainhadithapi.cpython-311-pytest-7.4.0.pyc b/hadith-ingestion/__pycache__/test_mainhadithapi.cpython-311-pytest-7.4.0.pyc new file mode 100644 index 0000000000000000000000000000000000000000..37d4806682f95d6ba7a11d054ac3dc2411efe860 GIT binary patch literal 6150 zcmbVQTWk~A8J@An@v%Lz;}8geg`8Y~m^eZ&`Mo(`%=wBBVmn%gj($bZ>hE`t>{btbH;ZJ zw4FIQKIi z>jpE|Dz-rFmja^u3guJYcQ8_$i0*?;58brqWaIpw)Uw=Sz~c^Ky;U6{b)Lc3D69ZJ2|tv)-k-tGp`>YxyN3w%mK!ic0D+ z%nDm@RpqO#`Z?<@72P8Gp`)w9e2n>EFXSDw>R5Hw+2&bsfCb(ar|7G4!w3%}t#u>* zd+z!8e*FmeAHh5S*>!l^N5=ob=6TjRyc8Ut>yP# z&W_p`Zvp`LEAUkTlnQD48a@Iw@x6zYg-vy?R(b}r={fsic>Z+6KUvV|_ zm$*xG%bwMim6qn4f1@Rr7}34z`kqVN4I3qGU1P5?*PWM`YiwvwE=2cCZAqe=C9Z6V zI8ojcv1)IMx$xA~6ejFIs$r~bp18DoV&L=U!qEtxP9?O2ASZHl5*2|Ge>r&T$wI;hbXN}rE|n8B$Y64=%S)nuR-TlYs?p%NB15yxJi?n)VawGF6`R;1!~p(hYd7kqA49sJ#8N}+K0^c zp}hMkp-dQPzlrwiX#ZC&jK{D0M-4P)qA?wf6+3r6=^S0}95p)knVtLcJQX-}Z|v@h zu{~^V59|Izb}`Ul6CKvk;iuhwh0{;^C)WEXjQ#^={{f@>pxJ%!aqr{k<6g6SYJ*`t zAFy_Pb0$B1TYJg}_4e=F?ScwQL40t?+`ZrKJl^-mfO%-v?m%tu@0VuE}B$vA`Fe~~Kh`U=ry?laK1iN)lbKd(7+}+hAOt4qDZ?Ww7AU+XtZ- zeAwi}Iv=Lq8o7J1Flg?G=;cL_CA03B;T4-g-9=?*`;R+s|5m+XAg<@=<^y$cL^xJ%-{U3>RxQPcr=3Q749^tVc?$HW;9%@maW3bL1q-^#S-ROAQT?qj!iN%9RNS zvbDsqAP;vK-N-!N&xdsE{Cv0w4*n_r>fEDtG5) zvu%JjiBE(A3fVa<1gS)lNV3{hB_62{wbD;moa(Y_alm)g;^OJdvgI#(W0nXi7B7fm z4Cpi^Ehj)Q%S&~VLDlkB{X@~0LOx}M-0ngx$`EPOXeMbakxFkhjR~ z(d!GG?=G+I9X7ZTlN-^wk*6J&tpAYp@NI(o>O^YDKCm51R0EI0^aC|A^)=mSCbN1+&K)I_5?8m(Z0XPa+!JcI z+_9LLj>lpan$IR=m_oJqZ)TQbm0njYL#_l`gvf&paM4wyYYNF-Nwp-vVGFtmM;pfet6r zVpf*Ep`3y)S*5xO>J2B$vKyR(oI(Nrmqj~6t0dUYRf~~-45RL-SXvqgri&c?KFJY^x~TNU>VY1mprilt!hgruF3KOwMAW1?hT8sU@j7>8Yi~sY#V3 zsl|Gk`I|kMpEELwY&KvmU}TiuypT}Vf(RoJVFDt|K!gQ| zumlm-AOd7pkqd~B01;v!f(=G+0vW~Cj0_B|3^!SL9X@a{NEtTxPB6aAVlepx_kzh4 wJl7fBCI|4^FuF|c<&|Izn7oWvS=y12QLdxr3j>J$=*7gqBhqcv$N@GV04O12ga7~l delta 534 zcmZ21{Y0AgG%qg~0}!Ns5X-EX$a{84B9#@$lL7N& zqa;%iD&(MIQeYMGV4gyhbSmp)Rwh?j4xlb=u$WGiB3Okkn5Pt_l*%zVoypu8WUd)l zOfpIx$y{@=m_?KZSeGS;$Hd^ykYd%skYc@>3CIP4D9uVqO`FM=nVjWh3-XIg(u-1y z^-_}bip!Gql5qI!%-}l$V!_0SJD7k;=@Q$a{rx&csLiOj%ReQemVQzcSaB^iKxIWS)` z6(lDQWGh5Tf!T^cwo;UID#zrTjMkDMSzWM*Vk!ratp{Z5M=7PUPS$18*M^y80Ti{2 zQU~j|vSDy%NU=__X<;tCDYYauCq1>aI5nxVB(+#C zGk^0JrfNn;k;w%thZ&_Oo3Os#Y`}Jfk;m^AhnK%oyq}}5>#fQB9Jj^Xf&MCH0}>pJ zEI?Rf4rFR-PU7tHkpZ%bm_dXrh>!yj3LruWM5urWH4vczA~ZpS7KqRW5jr434@4M% d2*b&@Ikh=lfJ`n%7M96;T(XmOxu!F^0su>ePC@_x delta 400 zcmbOxdQ_A*l$V!_0SHn*h-Fqxd$p%3BAO>t?98_O^k#k*_kKJM5-x9<)>@=$&x|QZTgx@;L}$oC!kgukElrRJCd> W9{oHvjz7^lqDwgE9h=~jnEe1US~u$e literal 0 HcmV?d00001 diff --git a/hadith-ingestion/src/__pycache__/main_hadithapi.cpython-311.pyc b/hadith-ingestion/src/__pycache__/main_hadithapi.cpython-311.pyc new file mode 100644 index 0000000000000000000000000000000000000000..2a9148cd42b964fb33e2a173bef8bb27b7db1471 GIT binary patch literal 19329 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⋘ed}5Nuq^^V@8WoeQM*%tC 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 CR%br| literal 0 HcmV?d00001 diff --git a/hadith-ingestion/src/__pycache__/main_hadithapi.cpython-312.pyc b/hadith-ingestion/src/__pycache__/main_hadithapi.cpython-312.pyc new file mode 100644 index 0000000000000000000000000000000000000000..68d7bf574ad979348d9cc7a16885f8a4aaffdcff GIT binary patch literal 17198 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 literal 0 HcmV?d00001 diff --git a/hadith-ingestion/src/api_clients/__pycache__/__init__.cpython-311.pyc b/hadith-ingestion/src/api_clients/__pycache__/__init__.cpython-311.pyc new file mode 100644 index 0000000000000000000000000000000000000000..e6ce56257d3f51818f9fb5f0ab692404e7e21a6b GIT binary patch literal 218 zcmXwzF$%&!5Jh(liU`5ZJ6PykKsn^l*yxf{#c5F)?V!*Z`C>;lNA^@%V3&ffNu`F+dIqJ)l2>Y9 dx5M&KR#{{4=;on){EycGT_mOK!~_?G><48!Jh1=( literal 0 HcmV?d00001 diff --git a/hadith-ingestion/src/api_clients/__pycache__/hadithapi_client.cpython-311.pyc b/hadith-ingestion/src/api_clients/__pycache__/hadithapi_client.cpython-311.pyc new file mode 100644 index 0000000000000000000000000000000000000000..f178923f02625d65b0705b70a4ea61a75c1ee31d GIT binary patch literal 11155 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 literal 0 HcmV?d00001 diff --git a/hadith-ingestion/src/api_clients/__pycache__/hadithapi_client.cpython-312.pyc b/hadith-ingestion/src/api_clients/__pycache__/hadithapi_client.cpython-312.pyc index 8c6dce5fb4f5f4007f0bbedc6bf6f626b20cd420..a0ad7e75daaea587a9f1e620ba260096f26a98c9 100644 GIT binary patch delta 1224 zcmZ8fOKcle6rHg>%Lz8j(JQ15f zSRuoz@D_Bz!ewPqgi={m%>oIj3l?l@S!$e7i$Frkl8I8pmUqW-EAbZho_FTmJLjJF z9xng7?D~!8?G#xbJdDVV@p~@LN}F)lnm%n;dEjB~nD5d9^n>HBX@F?L7Aet*WosW7 zxNqrS@L$|F{MBZ;=MfvsGnTTs+n?JGO>`D3&Y4AxtE@{~Y8BNr&k&VXt7>Jvx+0oT zmUKla2x$^T2893{Y!uMT5MCt#A3AgFIRfgB@k{*oyuG#1^G`Rp!4IGEI_+j2C;G&qm*-boKsqa1`25_zZ3idK{)lxE(P6_f$QtW?X}YiJ4%PD40L0y$SW0RGW;-S%b^_1vjPTndN%ZxdfX@*m7`j#BvsPvThf}WNUB^@G`?J`-6&ORn_C-IwJMqi z_T=zEXo{H3h0iP*eqDxYhgwsmjS{J@)~|>bR3PMF6qpU2AwlF%MghX8G(1^^Z65E2 zN9i~4cj0aJYeLlLa6%ZRNALw<V;+-g??mmKa%Q3QmuT)*NfyEOGh3m5W}Ae zQvURQG~JD+TZO%1FFL2&C~y23#dv+Xhl-2)u}n9XX?@svrx#mjEcb$_A6-crw2Gyui3*(T?W80J!VHGq8RvAw^c!G;>`==o;|GlK>0R32i%^=Q@Pp(I{d+rmYQ!9$1qzxItuNmH2(TCM&CyHr zBz`bj^vuHv(-mZ78qMSA*t;I17Nl!tSy52|e>S$e8)t&IvrS90*cxkIyW{G{rjIGY z>G?56XjXKJq}Iw_wqx!TJKVk3x>F0s!0B(%)P&d%1p7hZ$T7pD|L_KMhGdRtlnmBSS(M-tb1%NaQgmtR{ uxnW7%Q6yEWA*SmJS{IB?)XWKb<55C~8?ZWRzmm^W@x)IEIj%{TA8 z{ob4TX6EY|3>GV`v)dG`Ho>E*op594^k^ z$d$6oxkcTA&(H(h4{(x#F5n<=riOu?rqGfO6UlEKqvBaA6~8A5=VuPFYH9fT%M$$V zN2iHgN}fCPNjVp`e5VE#@5BkM8nnlozzRb zzN-k4obM4Y-{i>>~qZiQlKihL4U7vG~oafoPY z3>_nBwL2p3o@xYB)wWzE?@rD7bY93kxJ|&x0BV-ZoCmrnKI|; z`im1hUenEW_3Vsok5!ZPM5FV3d8Vnxc9d|eG%L(#+q>r}#d1UnDQ3EaI$@7>mtgkNQFm3*68oTRDqiOf zHg!85fyUud+xKmI%fN+vVX4IzOBi1Voy`wMhfe{3J>Bu_5Sg>H*l+LL4h*V)zhcl4eAB59-Bg)B^4KwngdnR0gckFMOdF%pVO^PR?OZ@L9h2m%L{wzL%jA#5KWKpbbo>?1 QoE7;uSO4Z<#TxDSKa4gaYXATM diff --git a/hadith-ingestion/src/database/__pycache__/__init__.cpython-312.pyc b/hadith-ingestion/src/database/__pycache__/__init__.cpython-312.pyc new file mode 100644 index 0000000000000000000000000000000000000000..789481c63f574f0d3fe426077b6fe46740b1098a GIT binary patch literal 203 zcmZ9Fu?@m75Jh7G5<*JL4is<;AV#30wl480HgRm^b3hq^37COd7=w}urAvj=@}>L# z-RY$NDvDK>bpNc)l<&#@HO$lHk@eX|9G_X3rEQpg#xtCl0t2H(jjl!uHy;`qL+2VO zDUz+JV=DVd42rH`*kWrc$(8mN187tx>aB4#aWvimhYA!%ERhMMG|ogRcb9%#?pv=q TONX#X)glc~@Xdt~Ay4!JAjvsQ literal 0 HcmV?d00001 diff --git a/hadith-ingestion/src/database/__pycache__/__init__.cpython-38.pyc b/hadith-ingestion/src/database/__pycache__/__init__.cpython-38.pyc new file mode 100644 index 0000000000000000000000000000000000000000..679f0e9c3c135d97af9461e08516b1a423cb69a1 GIT binary patch literal 197 zcmYk0F%H5o5Ck2G0wJa44-{}8K!_L6pw!kSJ|#yS8~Geip1@Q15-lYq9Tj#3EA6ay ztF6j%p^|Q|CFgu*{HsW1pDeQkqmF7-9PTRQ`G?O5Dxn}CXt6`rqJ^suy^djYJ=7G* zwloUWQzQXH7hthCaHFN^yu|<=8jjtXT}u+#JCM+T!H6{qf!6FeYP~s6kNI}+X0)`+ IAKuC83rB4>r~m)} literal 0 HcmV?d00001 diff --git a/hadith-ingestion/src/database/__pycache__/repository.cpython-312.pyc b/hadith-ingestion/src/database/__pycache__/repository.cpython-312.pyc new file mode 100644 index 0000000000000000000000000000000000000000..9927d164af75690d51641948e946daebca89e8d2 GIT binary patch literal 16578 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 JZj6xh^FNC@r$_(* literal 0 HcmV?d00001 diff --git a/hadith-ingestion/src/database/repository.py b/hadith-ingestion/src/database/repository.py index 85e8b0b..87011a8 100644 --- a/hadith-ingestion/src/database/repository.py +++ b/hadith-ingestion/src/database/repository.py @@ -2,6 +2,7 @@ Database repository for hadith data operations """ from typing import List, Dict, Any, Optional +import json from uuid import UUID import structlog from sqlalchemy import create_engine, text, select, insert, update @@ -14,31 +15,37 @@ logger = structlog.get_logger() class HadithRepository: """Repository for hadith database operations""" - + def __init__(self, database_url: Optional[str] = None): self.database_url = database_url or settings.DATABASE_URL self.engine = create_engine(self.database_url, pool_pre_ping=True) self.SessionLocal = sessionmaker(bind=self.engine) - + + @staticmethod + def _coerce_uuid(value: Any) -> UUID: + if isinstance(value, UUID): + return value + return UUID(str(value)) + def get_session(self) -> Session: """Get database session""" return self.SessionLocal() - + # ===== Collections ===== - + def get_collection_by_abbreviation(self, abbr: str) -> Optional[Dict[str, Any]]: """Get collection by abbreviation""" with self.get_session() as session: query = text(""" - SELECT * FROM collections + SELECT * FROM collections WHERE abbreviation = :abbr """) result = session.execute(query, {"abbr": abbr}).fetchone() - + if result: return dict(result._mapping) return None - + def get_all_collections(self) -> List[Dict[str, Any]]: """Get all collections""" with self.get_session() as session: @@ -68,34 +75,35 @@ class HadithRepository: metadata: Optional[Dict] = None ) -> UUID: """Insert or update a book""" + metadata_json = json.dumps(metadata or {}) with self.get_session() as session: query = text(""" INSERT INTO books (collection_id, book_number, name_english, name_arabic, metadata) VALUES (:collection_id, :book_number, :name_english, :name_arabic, :metadata) - ON CONFLICT (collection_id, book_number) - DO UPDATE SET + ON CONFLICT (collection_id, book_number) + DO UPDATE SET name_english = EXCLUDED.name_english, name_arabic = EXCLUDED.name_arabic, metadata = EXCLUDED.metadata RETURNING id """) - + result = session.execute(query, { "collection_id": str(collection_id), "book_number": book_number, "name_english": name_english, "name_arabic": name_arabic, - "metadata": metadata or {} + "metadata": metadata_json }) session.commit() - - return UUID(result.fetchone()[0]) - + + return self._coerce_uuid(result.fetchone()[0]) + def get_book(self, collection_id: UUID, book_number: int) -> Optional[Dict[str, Any]]: """Get book by collection and book number""" with self.get_session() as session: query = text(""" - SELECT * FROM books + SELECT * FROM books WHERE collection_id = :collection_id AND book_number = :book_number """) result = session.execute(query, { @@ -125,6 +133,7 @@ class HadithRepository: source_metadata: Optional[Dict] = None ) -> UUID: """Insert or update a hadith""" + with self.get_session() as session: query = text(""" INSERT INTO hadiths ( @@ -152,7 +161,8 @@ class HadithRepository: updated_at = NOW() RETURNING id """) - + metadata_json = json.dumps(source_metadata or {}) + result = session.execute(query, { "collection_id": str(collection_id), "book_id": str(book_id) if book_id else None, @@ -165,12 +175,12 @@ class HadithRepository: "chapter_name": chapter_name, "source_id": source_id, "source_url": source_url, - "source_metadata": source_metadata or {} + "source_metadata": metadata_json }) session.commit() - - return UUID(result.fetchone()[0]) - + + return self._coerce_uuid(result.fetchone()[0]) + def get_hadiths_without_embeddings( self, limit: int = 100, @@ -180,8 +190,8 @@ class HadithRepository: with self.get_session() as session: if collection_id: query = text(""" - SELECT * FROM hadiths - WHERE embedding_generated = FALSE + SELECT * FROM hadiths + WHERE embedding_generated = FALSE AND collection_id = :collection_id ORDER BY created_at ASC LIMIT :limit @@ -200,22 +210,26 @@ class HadithRepository: result = session.execute(query, {"limit": limit}).fetchall() return [dict(row._mapping) for row in result] - + def mark_embedding_generated(self, hadith_id: UUID, version: str = "v1"): """Mark hadith as having embedding generated""" with self.get_session() as session: + # Prepare the update query query = text(""" - UPDATE hadiths - SET embedding_generated = TRUE, + UPDATE hadiths + SET embedding_generated = TRUE, embedding_version = :version, updated_at = NOW() WHERE id = :id """) + # Pre-serialize parameters (keeping consistent with other methods that + # serialize payloads/configs before execution) + params = {"id": str(hadith_id), "version": version} session.execute(query, {"id": str(hadith_id), "version": version}) session.commit() - + # ===== Ingestion Jobs ===== - + def create_ingestion_job( self, job_name: str, @@ -230,15 +244,16 @@ class HadithRepository: VALUES (:job_name, :job_type, :source_name, :config, 'running', NOW()) RETURNING id """) + # serialize config as JSON for storage result = session.execute(query, { "job_name": job_name, "job_type": job_type, "source_name": source_name, - "config": config or {} + "config": json.dumps(config or {}) }) session.commit() - - return UUID(result.fetchone()[0]) + job_id = result.fetchone()[0] + return job_id if isinstance(job_id, UUID) else UUID(str(job_id)) def update_job_progress( self, @@ -297,7 +312,7 @@ class HadithRepository: "error_message": error_message }) session.commit() - + def add_processing_log( self, job_id: UUID, @@ -311,16 +326,17 @@ class HadithRepository: INSERT INTO processing_logs (job_id, log_level, message, details) VALUES (:job_id, :level, :message, :details) """) + details_json = json.dumps(details or {}) session.execute(query, { "job_id": str(job_id), "level": level, "message": message, - "details": details or {} + "details": details_json }) session.commit() - + # ===== Statistics ===== - + def get_collection_stats(self, collection_id: UUID) -> Dict[str, Any]: """Get statistics for a collection""" with self.get_session() as session: @@ -328,7 +344,7 @@ class HadithRepository: SELECT * FROM get_collection_statistics(:collection_id) """) result = session.execute(query, {"collection_id": str(collection_id)}).fetchone() - + if result: return dict(result._mapping) return {} \ No newline at end of file diff --git a/hadith-ingestion/src/main_hadithapi.py b/hadith-ingestion/src/main_hadithapi.py index 19dc566..73ce32e 100644 --- a/hadith-ingestion/src/main_hadithapi.py +++ b/hadith-ingestion/src/main_hadithapi.py @@ -7,9 +7,9 @@ from typing import Optional, Dict, Any from uuid import UUID import structlog from config.settings import settings -from api_clients.hadithapi_client import HadithAPIClient -from database.repository import HadithRepository -from processors.text_cleaner import ArabicTextProcessor, TextCleaner +from src.api_clients.hadithapi_client import HadithAPIClient +from src.database.repository import HadithRepository +from src.processors.text_cleaner import ArabicTextProcessor, TextCleaner # Configure structured logging structlog.configure( @@ -35,14 +35,15 @@ logger = structlog.get_logger() BOOK_SLUG_MAPPING = { 'sahih-bukhari': 'bukhari', 'sahih-muslim': 'muslim', - 'sunan-abu-dawood': 'abudawud', - 'jami-at-tirmidhi': 'tirmidhi', - 'sunan-an-nasai': 'nasai', - 'sunan-ibn-e-majah': 'ibnmajah', + 'abu-dawood': 'abudawud', + 'al-tirmidhi': 'tirmidhi', + 'sunan-nasai': 'nasai', + 'ibn-e-majah': 'ibnmajah', 'muwatta-imam-malik': 'malik', 'musnad-ahmad': 'ahmad', 'sunan-ad-darimi': 'darimi', - 'mishkat-al-masabih': 'mishkat' + 'mishkat': 'mishkat', + 'al-silsila-sahiha': 'al-silsila-sahiha' } @@ -66,12 +67,12 @@ class HadithAPIIngestionService: # Get books from API api_books = self.api_client.get_books() - + book_mapping = {} - + # print(BOOK_SLUG_MAPPING) for api_book in api_books: book_slug = api_book.get('bookSlug') - + # print(book_slug) # Map to our collection abbreviation collection_abbr = BOOK_SLUG_MAPPING.get(book_slug) @@ -82,7 +83,6 @@ class HadithAPIIngestionService: book_name=api_book.get('bookName') ) continue - # Get or verify collection exists in database collection = self.repo.get_collection_by_abbreviation(collection_abbr) @@ -93,8 +93,10 @@ class HadithAPIIngestionService: book_slug=book_slug ) continue - - collection_id = UUID(collection['id']) + + collection_id = collection['id'] + if not isinstance(collection_id, UUID): + collection_id = UUID(str(collection_id)) book_mapping[book_slug] = { 'collection_id': collection_id, 'book_id': api_book.get('id'), @@ -305,7 +307,7 @@ class HadithAPIIngestionService: if not arabic_text: raise ValueError("Missing Arabic text") - + # passed logger.warning("Arabic text extracted and validated", hadith_number=hadith_number) # Clean texts arabic_text = self.text_cleaner.clean_text(arabic_text) if english_text: @@ -319,14 +321,15 @@ class HadithAPIIngestionService: # Get or create chapter (book in our schema) book_id = None chapter_name = None - + # logger.warning("Processing chapter data####", chapter_data.get('positional_args', {}).get('id')) + # logger.info("Processing chapter data####2####", chapter_data.get('id')) if chapter_data: chapter_id = chapter_data.get('id') chapter_number = chapter_data.get('chapterNumber') chapter_name_en = chapter_data.get('chapterEnglish') chapter_name_ar = chapter_data.get('chapterArabic') chapter_name = chapter_name_en - + # print(chapter_number, chapter_name) if chapter_number: try: chapter_number = int(chapter_number) @@ -335,7 +338,8 @@ class HadithAPIIngestionService: # Get or create book (chapter in HadithAPI = book in our schema) existing_book = self.repo.get_book(collection_id, chapter_number) - + # logger.warning("EXISTING BOOK : ", existing_book) + # logger.warning("Fetched or created book", collection_id=collection_id, chapter_number=chapter_number, chapter_name=chapter_name) if not existing_book: book_id = self.repo.upsert_book( collection_id=collection_id, @@ -345,8 +349,12 @@ class HadithAPIIngestionService: metadata=chapter_data ) else: - book_id = UUID(existing_book['id']) - + # print(existing_book['id']) + existing_id = existing_book['id'] + if isinstance(existing_id, str): + existing_id = UUID(existing_id) + book_id = existing_id + # Build source metadata source_metadata = { 'api_id': hadith_data.get('id'), @@ -356,7 +364,7 @@ class HadithAPIIngestionService: 'chapterId': hadith_data.get('chapterId'), 'chapter': chapter_data } - + # logger.warning("Hadith metadata built", source_metadata) # Store hadith hadith_id = self.repo.upsert_hadith( collection_id=collection_id, diff --git a/hadith-ingestion/src/processors/__pycache__/__init__.cpython-312.pyc b/hadith-ingestion/src/processors/__pycache__/__init__.cpython-312.pyc new file mode 100644 index 0000000000000000000000000000000000000000..f24452cc0ccd189951e0bf1750fadc5289494708 GIT binary patch literal 205 zcmZ8au?@m75VQ$M2q`T)P{1#M7=e!3a*|hU#j&G*2b2+*fEk#DF(|1}x>PtVC;i{u z>vi|a^NmQjf3|k!_q_fwF4N^92CN&x3*MVn&32n(Upy6Z+(p%ZScTULPw!Q=8%$=vff6e4&5-Vk8P-W ThbLO4a+!u_@y(=^lqK~8wG%pQ literal 0 HcmV?d00001 diff --git a/hadith-ingestion/src/processors/__pycache__/text_cleaner.cpython-312.pyc b/hadith-ingestion/src/processors/__pycache__/text_cleaner.cpython-312.pyc new file mode 100644 index 0000000000000000000000000000000000000000..d576a61fd320644924147e8a79f04bc2cea10663 GIT binary patch literal 6611 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 X7LR@&Z;oHlI-*NB=N+5ilQ{bUzK%H9 literal 0 HcmV?d00001 diff --git a/hadith-ingestion/tests/__pycache__/test_clients.cpython-311-pytest-7.4.0.pyc b/hadith-ingestion/tests/__pycache__/test_clients.cpython-311-pytest-7.4.0.pyc new file mode 100644 index 0000000000000000000000000000000000000000..97ad15a40ceb91ebdc604353b2fd819745dc909d GIT binary patch literal 212 zcmXwzK?=e!5JeMoB=W^+$&|Oz1V*ldJ zpP3Ic&pcm{sQYK7Q++3lqJPuRqInQOj$};_FXAV$@6&RS?1bQvAvaucE4g7e=g&p( zjXkpx0vHJmLfHmDCg9368eZ$Fz)Cs8JyTrhpf=h{z@VLFF&Oa2qB0t6!0n|S=DXU7 X#=zcB