From c728c4e1160791f7a9d69ceae754a752661d6e85 Mon Sep 17 00:00:00 2001 From: Flatlogic Bot Date: Tue, 27 Jan 2026 02:20:46 +0000 Subject: [PATCH] adding api for phone app --- config/__pycache__/settings.cpython-311.pyc | Bin 9574 -> 9584 bytes config/__pycache__/urls.cpython-311.pyc | Bin 1259 -> 2483 bytes config/settings.py | 1 + config/urls.py | 23 ++++++++++++++++++- core/__pycache__/api_views.cpython-311.pyc | Bin 5515 -> 6123 bytes core/__pycache__/serializers.cpython-311.pyc | Bin 3664 -> 4730 bytes core/__pycache__/urls.cpython-311.pyc | Bin 6199 -> 6395 bytes core/api_views.py | 12 +++++++++- core/serializers.py | 21 +++++++++++++++++ core/urls.py | 3 ++- requirements.txt | 3 ++- 11 files changed, 59 insertions(+), 4 deletions(-) diff --git a/config/__pycache__/settings.cpython-311.pyc b/config/__pycache__/settings.cpython-311.pyc index 3f9c1b0e9a8223ad83fc779e1dfe23e7d59d1c1e..9ec34c718448923cc4fd4ed27b9909da2ddf289b 100644 GIT binary patch delta 266 zcmaFn^}&mGIWI340}#Z^RAesN$UB9bk$dtY?o*r`DMe}Vm5Igao3nXpnc0+pN{Vzh zzvGu1_VNFUQQdd$YK( zATy)%W=%16M#h54hT_tUiJN`J(^)fZK+0@^#4YB`ypke25Z3`jID!Z#5aA3WT!F+b z*5ZPk%#tEckbpOc@C6b6ASwP3565svKhJo_0MGc)AfKWjkW?^;2mukHlVxSsF&^4{ ZMmC&LkXwl90|Sg`;QJu8*+kxk4FDF3Gjjj{ diff --git a/config/__pycache__/urls.cpython-311.pyc b/config/__pycache__/urls.cpython-311.pyc index 96daeade0e01ef62bea0babc677bc6f29adfe44d..3468c39d1296e210bd502ecb8b2ab7df00ebd312 100644 GIT binary patch literal 2483 zcmaJ?O>omj6kglwpZGs9jzfrx6CfnCi6(>sr6CY-S~C3Q4=84)8pT>WawW?n$#KvO zog6si&_fQ)lq09K9dhWABS(%BqZvFpG1F6Trf}lax3bmXPTKYE`rEhPzW2SSwfsvg z7Dmu2Lz}{1euVy@3%5l(;C;Y{(9eiRyhlWmr{M8W>=nI|ui%q#0Xu7-=$8V8fP=9Z zltP7&gZ*NU6fT4v91tT?v=DW0P>f0OLfpY2F(D-jNe}WO5{Hqj^tvMW9zM)R_^4y; z`^OsFi|=|6dJd!Aoc)x$;uCwx?)|;q-2m`mv>V??qLoALs^r;A?LwB%VYFKz4IX{` zA(%0r?)J6o1tyGkb9ntE{jA@$eEQ9!y-fFMegL#}#d16x1`nA}Pr8^NbbNHhyKTr1Wu*?dNz&sE&JWT;sHLJ1A6(Vx1?j6H@=)E^Nl~Z!_n>B@~YHn_E!S-%U z>E{9Dc)3`YNR@_>tGSY_`H=4^U!Uj=PeRN&ZYU%}sX*3#>WmztZ zWU?qrOidPrqCivzL`o{752*E8O;)ta5*0w&@hKD3`9Y~5>X9oe`P>bmNUADL9#=Vu zj0bGLCTJqD6Fez#bx~t!SP*DOc%l{+p+?o(Nhb^|mspi38{oqZ7G+4KsM$dfLS3#x zg#)$v8Z7O;{feV8^QMo;q~x6D&X7; z#zuNiQC5f}<{Jo`foE3|Hd(hIBIvDiWm>bC`wUq{mNh-Z(9|@Qu>);zYkb&_?m=Ze^&IZ>1wbJd4-r}EBi zx5EuVTZiYt)&)CAF$EDw%>BjKSQRv4W16e&&(B}E^Q|3TS)E&5xXRvHzF|i?c=`72 zRlDcre12ihv4`8xF^8_qt<1Ceh2`JSd(enJPBQDVM40+oy{gq2vPp_{O;#A1saoTT zgrOxA%8YZPY7ak#W+a)fi)2>$3XaqN9(5hw%PpVB<7uLt(cPQqgmF+mh7I zqr1OFqegdcb{_!`O*CY5_qXxvw%qh3w$44CX-1DW`v;qSH=3DCO|X}Ll8xiDM*NZ) zzhuQ-)3b|4e9DYZS@Ee>EQtN@5KJHF)JmdAqL~@7GM^j$6RmV4;e7`d?*}?4a}ODwJ_V}4eWgVCN=sxHTtaa zf-_R1X6mw)y8QA-1K&0AT?^lBMFNhlB=SVJA8kK!kA3;%!jnrTK4#%#ZByU&z3qED z56sxG6&p73h=oU*L&L2gPC|k(eV`K{56v=)aP;wP3;8_Do+eK0oZUJ5bj%u@c=4Te zamh$6o2g|BX1u(0{gdr4UR<+gZX2mZGqq^Jj2HK}PyK$)Iy3(&WS&_xQcGrP$$}X# SZC$6IR*(j2hf~hMjr$whk+dHG delta 377 zcmdli{F+l^IWI340}#ajD9v2R#K7JW?+D6fQdrXrw9ZyfUu_EWFuy`$p={ECkL^HGKx%I!CE/', schema_view.without_ui(cache_timeout=0), name='schema-json'), + path('swagger/', schema_view.with_ui('swagger', cache_timeout=0), name='schema-swagger-ui'), + path('redoc/', schema_view.with_ui('redoc', cache_timeout=0), name='schema-redoc'), ] urlpatterns += i18n_patterns( @@ -17,4 +38,4 @@ urlpatterns += i18n_patterns( if settings.DEBUG: urlpatterns += static(settings.STATIC_URL, document_root=settings.STATIC_ROOT) urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT) - urlpatterns += static("/assets/", document_root=settings.BASE_DIR / "assets") + urlpatterns += static("/assets/", document_root=settings.BASE_DIR / "assets") \ No newline at end of file diff --git a/core/__pycache__/api_views.cpython-311.pyc b/core/__pycache__/api_views.cpython-311.pyc index 34addef3c50973c3460920156f3d4ee4c1c1fcab..b9df1fd9c23e4b9bf3e4f4766e969de88ab89b9e 100644 GIT binary patch delta 1641 zcmZ`(&2Jk;6yLG8j_s_yv12FeBo3RpQCUKrptL|CDoRNqg4c{ z&+pUMChkurKTjm$0z3HYrqxbtClyrOKIw{U89lRoBj3t~gjWSq`cNKyqUQoXjwXinkY=a zK;w!(P;M;QR<&%9Dz>j+Vi~rzi3weZ4D9@d?jxkoyWv@sr75wb3^Tt3oRd5QE#`|Z zwwFnUHpS5hWI%E|H^pT%_%yqJDUeejngB?1ph{#a!i8z7rgA$gk=_tGL*3}vp$rhX zi>Khme?)@Y82uqyP{topyHG_{RmlWJvER`t`bX@0=I5LE$-!rtM(ZKn?&zQKLYg~y zk`dexw`b;s-fMXXsHDY7k$sX$fGL0^z$m@lTYTarxXuAQ18|tuG<=<=inI`DQG;R)ihGoBH z;bw6Kd-Sj5XRIhxUPzw@=F1E^ru1L=omP-?^6@Eyi3o53;1z&QaDLdZZ9jUofysu8 zJst$P1eC7I%!3R7YT>@kV5{@&(Mc&qf9;zIiZ;(?;rfZ!8AS_sl}1B6c^5Gybo-ao zh1Y`EW8JaKj6y~Mx?;Z!vaaaLAS=^a`g{;VnL1ML^t()YUBH5lOhFHsNDpICKZYZ< z9;V=D1?f>7tMTOr!Kb}+tS3Y7NODUuLwdptv;7kN?1M|SNQ~+#v}Us!XEUn?Iu+N= zb;qiEs^_R4P*g)*=Ub>QZK#!iOqShO0OPCb7b;(hUhW8$>dsfx(ET^s#e6?Yb z7B&NdFLQ6qt`gXlwC+CpJ(Y^-R4WzI$8tC{PQ2EJrF&T3=5 zvTR}7e4wl?zUGU-1AwBta|{l?#YE+xv(|A*MDN`5L&?yy~;8%)^O7ys|5ZFh)D0Ie~j>S()5%5 zK{QRj>p!l;0Q%X>Y)~!yK7MoEG(0?8z6jkQFay4PpgWNA3?81A|DrQ%j@hvBIf9uD r%%Xdf4rgwREVhLsU-Wk7+ZU5jG`=r93Lnq!j-37*6#qO%%k%vo0}x;K delta 937 zcmZvaO=uHA6vuZqYnr5+-EO{ilNb#)61S~s2o)4-AdMxqYHBH{1UwY7#YjY)O$j2X z2XDPJyqgDaB0?`Uco4jK6AvN?67c3p4=o-&i0@4x(zQwWW#<1r_Wft}=j_(B_A(p} zN%+}$(QUQWo@Oznmv?*5GkQ#xYEn~uDmB9nyA$v2n|eY>8cI4!CP|i%CQvd^N}@ED zYDU&1I|>cfWiotbC;Ph0WM+b)R9Fnwl)9C|C-OAmD8dd76xV5Q@F=`hj`>Z}t^PM< zgPGH~ekJi4lBNiT05tqXzYvZ7wm&DcId~H|mx@wQl-slt4^U~9g+Or9${h&1KHO%r zSw02T;14zfh0uHK^DC4$&tSwJz0e8G>i_Rnk1ut&p|?JCOyI+Hu;~?KFIdeNWPxH!!ZW+)kA{>m8?ZZRvW; z>Eg|OjGtgN*o&u6iTZ;*e+TC8-fM2Qoie|L9cW_rHe5h- diff --git a/core/__pycache__/serializers.cpython-311.pyc b/core/__pycache__/serializers.cpython-311.pyc index 74c967f3e9fc4d0eaeeb5e9ea7bbb97bb074aa28..c2e22d3b7b8b929097d6339fff714addcfac8517 100644 GIT binary patch delta 991 zcmZvYL2nX46vt!k#>QVE%DGqX&RDRZ8d0OOw?Fgf~A27ns#L;&03^nSTtZ7 zdg!6YHhYjypfUEwRTIB~L$U|b=vOe*G#)${XFv%pJCpfk=l$RN&wERh-_v97M@L0K z*UHgrebIe57UC|#!z({U4m<$b_#V)FhkwE&ec)z(;y|E9*R$!`tKtXLHO?F8SV|uV7Q- zI$NWS*yOlPpIfernn)+|90!t>=LJ2VRB;{^QV8p6L9ZcPlS+Dit5RCu+4=MYe5YabedT`S5Wi!g?=)Q0|0^f-MLr~+rJ)LL53Q2<2&@R zW1(!QMx~6G*k!1#b=KDLU_-r#O+!6lupz~$c7ymX^Y&<{oX2{}(6@_;s9>&$5pz?J z>Io{w=qXQA?Dlut7ua`pIMFY5z<=xuY-5=w;xI)b>cJE2GRYt@I2ax>BpDtvtTLn+ z*pS^y9AaP0$ow%P)R)(hRxUwUaU}DPu{Q-9(4?I_X~+#tDm^+6cX0#0E-4eP-Ib1DDOO k-YM}3jX*ZyPV<*{3C2SckQxu8k+Y_5oG{_kM(w))1q`?caR2}S delta 92 zcmeyRazTb~IWI340}w1;TAq1?bt0bx(-($`8lTuw_=6cV1va}ensP8|Zm!|9VPv$~ syp!tyBeS0-|KtFH+R2v$B)R;6IvIhuIB4@%0WZeMGD6&}MUp@P0IyaTfB*mh diff --git a/core/__pycache__/urls.cpython-311.pyc b/core/__pycache__/urls.cpython-311.pyc index 7ed389c10060a75d98c1a4e99c4f5c187adfe5a9..0394ab04b72b0b11f5bf671edc02b9b10c15697c 100644 GIT binary patch delta 534 zcmdmP@Y|4YIWI340}zz1DbLImn8+u=q{6XL;~M*91x8lZ^i;Mi!^scWbfq)aurFg~ zU|0>r5HOK3$|xl>m_ajZGaH8=yOBa-L8g95QDSnozD;pSkrkMknU@})SDKrYT4bkx zO8}@M9xNPRkXV$QIys16nbCN28UJ2JA<=-+q@2v;0FZc22*{MldV)z@fk3+$fw=g{ zP9c3DX$dAXg=B&3b|D2IxkAVnNPZKt2a;yOEfJBLWhs1+(Xa$%A0>v4|2-oJ|x&YJy20Fqto^r0mMb&-5XJ zk%5)7!KFiHLg^K8?F&Xu7g(GxvN&I1asChq)UySw`no8{rk|qnKvGf+WR?w>j2Ba4 z1DldDIZ#}hITI+cR7{>7ER@GM`L3`8b3Rb)nHb1%?BXCpG{r&MeZXYCxE_!_Ph1yB zo)OnG1?zKT0z2per}m1-E4n_{bwe)chFsJQyP_L*AvXU4OTk5!f-5WqAKaP1$~`7Y Rs0n(4*$vzvSmX~3YXGIsm+Jrk delta 400 zcmexuxZQwnIWI340}xzYTAulbepoHW4Zi+Iv9btcMpywz+6wyu$!=kLAbDEY1xN~r*a1m@5s;c(5jh~)BLY&n zRzwj4C52h8phlLv~d1B+Y)lV8M?*ul1DFixH*BE_5u zl(!NGsfrQ@xv&~c&JhQhv`-vl>O(NeBB2Ll8%yW{$wUb~Hi*k7ACXWKbY}u_8n{8Q I$QKxx02$|R3jhEB diff --git a/core/api_views.py b/core/api_views.py index fd9febd..be583de 100644 --- a/core/api_views.py +++ b/core/api_views.py @@ -5,7 +5,7 @@ from rest_framework.authtoken.models import Token from rest_framework.views import APIView from django.db.models import Q from .models import Parcel, Profile -from .serializers import ParcelSerializer, ProfileSerializer +from .serializers import ParcelSerializer, ProfileSerializer, PublicParcelSerializer class CustomAuthToken(ObtainAuthToken): def post(self, request, *args, **kwargs): @@ -78,3 +78,13 @@ class UserProfileView(generics.RetrieveUpdateAPIView): def get_object(self): return self.request.user.profile + +class PublicParcelTrackView(generics.RetrieveAPIView): + """ + Public endpoint to track a parcel by its tracking number. + No authentication required. + """ + serializer_class = PublicParcelSerializer + permission_classes = [permissions.AllowAny] + queryset = Parcel.objects.all() + lookup_field = 'tracking_number' \ No newline at end of file diff --git a/core/serializers.py b/core/serializers.py index 90c468e..415be60 100644 --- a/core/serializers.py +++ b/core/serializers.py @@ -35,3 +35,24 @@ class ParcelSerializer(serializers.ModelSerializer): model = Parcel fields = '__all__' read_only_fields = ['shipper', 'tracking_number', 'created_at', 'updated_at', 'thawani_session_id'] + +class PublicParcelSerializer(serializers.ModelSerializer): + pickup_governate_name = serializers.CharField(source='pickup_governate.name', read_only=True) + pickup_city_name = serializers.CharField(source='pickup_city.name', read_only=True) + delivery_governate_name = serializers.CharField(source='delivery_governate.name', read_only=True) + delivery_city_name = serializers.CharField(source='delivery_city.name', read_only=True) + status_display = serializers.CharField(source='get_status_display', read_only=True) + + class Meta: + model = Parcel + fields = [ + 'tracking_number', + 'status', + 'status_display', + 'pickup_governate_name', + 'pickup_city_name', + 'delivery_governate_name', + 'delivery_city_name', + 'updated_at', + 'description' + ] \ No newline at end of file diff --git a/core/urls.py b/core/urls.py index 4c421ef..d6e84f3 100644 --- a/core/urls.py +++ b/core/urls.py @@ -70,5 +70,6 @@ urlpatterns = [ path('api/auth/token/', api_views.CustomAuthToken.as_view(), name='api_token_auth'), path('api/parcels/', api_views.ParcelListCreateView.as_view(), name='api_parcel_list'), path('api/parcels//', api_views.ParcelDetailView.as_view(), name='api_parcel_detail'), + path('api/track//', api_views.PublicParcelTrackView.as_view(), name='api_track_parcel'), path('api/profile/', api_views.UserProfileView.as_view(), name='api_user_profile'), -] +] \ No newline at end of file diff --git a/requirements.txt b/requirements.txt index 7ee7378..e59ab91 100644 --- a/requirements.txt +++ b/requirements.txt @@ -5,4 +5,5 @@ Pillow weasyprint qrcode django-jazzmin==3.0.1 -djangorestframework==3.15.1 \ No newline at end of file +djangorestframework==3.15.1 +drf-yasg