Ë
    ]¾øié5  ã                   óŠ  — d dl mZ d dlmZ d dlmZmZmZmZ d dlmZ d dl	m
Z
mZ d dlmZ d dlmZmZmZ d dlmZ d d	lmZ d d
lmZ d dlmZmZmZ d dlmZ d dlmZm Z  d dl!m"Z" d dl#m$Z$m%Z%m&Z&m'Z'm(Z( d dl)m*Z*m+Z+m,Z,m-Z-m.Z.  G d„ de
j^                  «      Z0 G d„ de0«      Z1 G d„ de0«      Z2 G d„ de0«      Z3 G d„ de«      Z4y)é    )Útransaction)ÚQ)ÚCountr   ÚFÚSum)Útimezone)ÚviewsetsÚstatus)Úaction)ÚMultiPartParserÚ
FormParserÚ
JSONParser)ÚIsAuthenticated)ÚResponse)ÚAPIView)ÚPermissionDeniedÚValidationErrorÚNotFound)ÚAuditLog)Úget_active_tenantÚis_tenant_admin)Úget_active_membership)Ú	PortfolioÚDebtorÚCaseÚCaseNoteÚCaseDocument)ÚPortfolioSerializerÚDebtorSerializerÚCaseSerializerÚCaseNoteSerializerÚCaseDocumentSerializerc                   ó4   ‡ — e Zd ZdZegZd„ Zd„ Zˆ fd„Zˆ xZ	S )ÚTenantScopedViewSetzO
    Base ViewSet: applique le tenant scoping via get_active_tenant(user).
    c                 ó@   — t        | j                  j                  «      S ©N)r   ÚrequestÚuser)Úselfs    ú /var/www/html/acx/cases/views.pyÚ
get_tenantzTenantScopedViewSet.get_tenant#   s   € Ü  §¡×!2Ñ!2Ó3Ð3ó    c                 ój   — | j                  «       }|r|j                  |¬«      S |j                  «       S )N©Útenant)r+   ÚfilterÚnone)r)   Úqsr/   s      r*   Útenant_filterz!TenantScopedViewSet.tenant_filter&   s,   € Ø—‘Ó"ˆÙ+1ˆr�y‰y ˆyÓ'Ð@°r·w±w³yÐ@r,   c                 óJ   •— t         ‰| �  «       }| j                  «       |d<   |S )Nr/   )ÚsuperÚget_serializer_contextr+   )r)   ÚctxÚ	__class__s     €r*   r6   z*TenantScopedViewSet.get_serializer_context*   s%   ø€ Ü‰gÑ,Ó.ˆàŸ™Ó)ˆˆH‰Øˆ
r,   )
Ú__name__Ú
__module__Ú__qualname__Ú__doc__r   Úpermission_classesr+   r3   r6   Ú__classcell__)r8   s   @r*   r$   r$      s(   ø„ ñð *Ð*Ðò4òA÷ð r,   r$   c                   ó(   — e Zd ZeZd„ Zd„ Zd„ Zd„ Zy)ÚPortfolioViewSetc                 ód  — t        j                  «       j                  «       }| j                  t        j
                  j                  d«      j                  t        d«      t        dd¬«      t        dt        g d¢¬«      d¬«      t        dt        |¬	«      t        d
¬«       z  d¬«      t        dt        d
¬«       ¬«      ¬«      «      }| j                  j                  j                  d«      }|dv r|j                  |dk(  ¬«      }| j                  j                  j                  d«      xs dj!                  «       }|dv r|j                  |¬«      }| j                  j                  j                  d«      xs dj!                  «       }|r|j                  |¬«      }|j#                  d«      S )NÚownerÚowner__usernameÚcasesT)Údistinct)ÚopenÚin_progressÚon_hold)Úcases__status__in)r0   rE   )Úcases__due_date__ltÚclosed)Úcases__statusÚcases__balance_amount)r0   )Úowner_usernameÚcases_countÚopen_cases_countÚoverdue_cases_countÚbalance_totalÚ	is_active)ÚtrueÚfalserT   )rS   ÚpriorityÚ )ÚlowÚmediumÚhigh)rV   Úq)Úname__icontainsÚname)r   ÚnowÚdater3   r   ÚobjectsÚselect_relatedÚannotater   r   r   r   r'   Úquery_paramsÚgetr0   ÚstripÚorder_by)r)   Útodayr2   rS   rV   r[   s         r*   Úget_querysetzPortfolioViewSet.get_queryset4   su  € Ü—‘“×#Ñ#Ó%ˆà×ÑÜ×Ñ×,Ñ,¨WÓ5ß‰XÜ Ð!2Ó3Ü! '°DÔ9Ü!&ØÜÒ/QÔRØ!ô"ô
 %*ØÜ°Ô7¼1È8Ô;TÐ:TÑTØ!ô%ô
 "Ø+Ü¨HÔ5Ð5ôð ó ó
ˆð. —L‘L×-Ñ-×1Ñ1°+Ó>ˆ	ØÐ)Ñ)Ø—‘ i°6Ñ&9�Ó;ˆBà—L‘L×-Ñ-×1Ñ1°*Ó=ÒCÀ×JÑJÓLˆØÐ0Ñ0Ø—‘ H�Ó-ˆBà�\‰\×&Ñ&×*Ñ*¨3Ó/Ò5°2×<Ñ<Ó>ˆÙØ—‘¨1�Ó-ˆBà�{‰{˜6Ó"Ð"r,   c                 ó¾  — | j                  «       }|j                  || j                  j                  j                  r| j                  j                  nd | j                  j                  j                  r| j                  j                  nd ¬«      }t
        j                  j                  d| j                  j                  |d|j                  |j                  ¬«       y )N)r/   Ú
created_byÚ
updated_byÚPORTFOLIO_CREATEr   ©r   Úactorr/   Úentity_typeÚ	entity_idÚentity_label©
r+   Úsaver'   r(   Úis_authenticatedr   r`   ÚcreateÚidr]   ©r)   Ú
serializerr/   Úobjs       r*   Úperform_createzPortfolioViewSet.perform_create\   s§   € Ø—‘Ó"ˆØ�o‰oØØ,0¯L©L×,=Ñ,=×,NÒ,N�t—|‘|×(Ò(ÐTXØ,0¯L©L×,=Ñ,=×,NÒ,N�t—|‘|×(Ò(ÐTXð ó 
ˆô 	×Ñ×ÑØ%Ø—,‘,×#Ñ#ØØ#Ø—f‘fØŸ™ð 	 õ 	
r,   c                 óN  — | j                  «       }|j                  | j                  j                  j                  r| j                  j                  nd ¬«      }t
        j                  j                  d| j                  j                  |d|j                  |j                  ¬«       y )N)rk   ÚPORTFOLIO_UPDATEr   rm   rr   rw   s       r*   Úperform_updatezPortfolioViewSet.perform_updatem   s‚   € Ø—‘Ó"ˆØ�o‰oØ,0¯L©L×,=Ñ,=×,NÒ,N�t—|‘|×(Ò(ÐTXð ó 
ˆô 	×Ñ×ÑØ%Ø—,‘,×#Ñ#ØØ#Ø—f‘fØŸ™ð 	 õ 	
r,   c                 ó€  — t        | j                  j                  «      }t        |«      st	        d«      ‚|j
                  }|j                  }|j                  }|j                  j                  d ¬«       |j                  «        t        j                  j                  d| j                  j                  |d||¬«       y )NúNot allowed.)Ú	portfolioÚPORTFOLIO_DELETEr   rm   )r   r'   r(   r   r   r/   r]   rv   rD   ÚupdateÚdeleter   r`   ru   ©r)   ÚinstanceÚmr/   Úlabelrp   s         r*   Úperform_destroyz PortfolioViewSet.perform_destroy|   sš   € ä! $§,¡,×"3Ñ"3Ó4ˆÜ˜qÔ!Ü" >Ó2Ð2à—‘ˆØ—‘ˆØ—K‘Kˆ	ð 	�‰×Ñ¨ÐÔ-à�‰Ôä×Ñ×ÑØ%Ø—,‘,×#Ñ#ØØ#ØØð 	 õ 	
r,   N)	r9   r:   r;   r   Úserializer_classrh   rz   r}   rˆ   © r,   r*   r@   r@   1   s   „ Ø*Ðò&#òP
ò"
ó
r,   r@   c                   ó(   — e Zd ZeZd„ Zd„ Zd„ Zd„ Zy)ÚDebtorViewSetc                 ó¢  — | j                  t        j                  j                  «       «      }| j                  j
                  j                  d«      xs dj                  «       }|r|j                  |¬«      }| j                  j
                  j                  d«      }|r |j                  |j                  «       ¬«      }|j                  d«      S )Nr[   rW   )Úfull_name__icontainsÚcountry)Úcountry__iexactÚ	full_name)
r3   r   r`   Úallr'   rc   rd   re   r0   rf   )r)   r2   r[   Úcountry_codes       r*   rh   zDebtorViewSet.get_queryset›   sŸ   € Ø×Ñ¤§¡× 2Ñ 2Ó 4Ó5ˆà�\‰\×&Ñ&×*Ñ*¨3Ó/Ò5°2×<Ñ<Ó>ˆÙØ—‘°�Ó2ˆBà—|‘|×0Ñ0×4Ñ4°YÓ?ˆÙØ—‘¨<×+=Ñ+=Ó+?�Ó@ˆBà�{‰{˜;Ó'Ð'r,   c                 óâ   — | j                  «       }|j                  |¬«      }t        j                  j	                  d| j
                  j                  |d|j                  |j                  ¬«       y )Nr.   ÚDEBTOR_CREATEr   rm   ©	r+   rs   r   r`   ru   r'   r(   rv   r‘   rw   s       r*   rz   zDebtorViewSet.perform_create¨   s[   € Ø—‘Ó"ˆØ�o‰o VˆoÓ,ˆä×Ñ×ÑØ"Ø—,‘,×#Ñ#ØØ Ø—f‘fØŸ™ð 	 õ 	
r,   c                 óÞ   — | j                  «       }|j                  «       }t        j                  j	                  d| j
                  j                  |d|j                  |j                  ¬«       y )NÚDEBTOR_UPDATEr   rm   r–   rw   s       r*   r}   zDebtorViewSet.perform_updateµ   sW   € Ø—‘Ó"ˆØ�o‰oÓˆä×Ñ×ÑØ"Ø—,‘,×#Ñ#ØØ Ø—f‘fØŸ™ð 	 õ 	
r,   c                 óH  — t        | j                  j                  «      }t        |«      st	        d«      ‚|j
                  }|j                  }|j                  }|j                  «        t        j                  j                  d| j                  j                  |d||¬«       y )Nr   ÚDEBTOR_DELETEr   rm   )r   r'   r(   r   r   r/   r‘   rv   rƒ   r   r`   ru   r„   s         r*   rˆ   zDebtorViewSet.perform_destroyÂ   s…   € ä! $§,¡,×"3Ñ"3Ó4ˆÜ˜qÔ!Ü" >Ó2Ð2à—‘ˆØ×"Ñ"ˆØ—K‘Kˆ	Ø�‰Ôä×Ñ×ÑØ"Ø—,‘,×#Ñ#ØØ ØØð 	 õ 	
r,   N)	r9   r:   r;   r   r‰   rh   rz   r}   rˆ   rŠ   r,   r*   rŒ   rŒ   ˜   s   „ Ø'Ðò(ò
ò
ó
r,   rŒ   c                   ó¾   — e Zd ZeZej                  j                  ddddd«      Zd„ Z	d„ Z
d„ Zd	„ Z ed
ddgd¬«      dd„«       Z ed
ddgdeeeg¬«      dd„«       Zy)ÚCaseViewSetr/   Údebtorr€   Úassigned_toÚcustomerc                 ó  — | j                  | j                  «      }| j                  j                  j	                  d«      }|r|j                  |¬«      }| j                  j                  j	                  d«      }|r|j                  |¬«      }| j                  j                  j	                  d«      }|r|j                  |¬«      }| j                  j                  j	                  d«      }|r |j                  |j                  «       ¬«      }| j                  j                  j	                  d	«      xs d
j                  «       }|r5|j                  t        |¬«      t        |¬«      z  t        |¬«      z  «      }|j                  d«      S )Nr
   ©r
   rž   )Úassigned_to_idr€   )Úportfolio_idr�   )Údebtor__country__iexactr[   rW   )Útitle__icontains)Úreference__icontains)Údebtor__full_name__icontainsú-id)	r3   Úquerysetr'   rc   rd   r0   re   r   rf   )r)   r2   Ústatus_qrž   r£   r“   r[   s          r*   rh   zCaseViewSet.get_querysetÛ   sG  € Ø×Ñ §¡Ó.ˆð —<‘<×,Ñ,×0Ñ0°Ó:ˆÙØ—‘ (�Ó+ˆBà—l‘l×/Ñ/×3Ñ3°MÓBˆÙØ—‘¨+�Ó6ˆBð —|‘|×0Ñ0×4Ñ4°[ÓAˆÙØ—‘¨�Ó5ˆBð —|‘|×0Ñ0×4Ñ4°YÓ?ˆÙØ—‘°<×3EÑ3EÓ3G�ÓHˆBð �\‰\×&Ñ&×*Ñ*¨3Ó/Ò5°2×<Ñ<Ó>ˆÙØ—‘Ü 1Ô%Ü¨Ô+ñ,ä°Ô3ñ4óˆBð �{‰{˜5Ó!Ð!r,   c                 óŽ  — | j                  «       }t        j                  «       5  |j                  || j                  j
                  ¬«      }t        j                  j                  d| j                  j
                  |d|j                  |j                  |j                  |j                  dœ¬«       d d d «       y # 1 sw Y   y xY w)N)r/   rj   ÚCASE_CREATEr   )r
   rV   ©r   rn   r/   ro   rp   rq   Úmetadata)r+   r   Úatomicrs   r'   r(   r   r`   ru   rv   Ú	referencer
   rV   rw   s       r*   rz   zCaseViewSet.perform_createü   s¡   € Ø—‘Ó"ˆä×ÑÓ!ñ 	Ø—/‘/ØØŸ<™<×,Ñ,ð "ó ˆCô ×Ñ×#Ñ#Ø$Ø—l‘l×'Ñ'ØØ"ØŸ&™&Ø Ÿ]™]Ø$'§J¡J¸C¿L¹LÑIð $ô ÷	÷ 	ñ 	ús   ¥BB;Â;Cc                 ó,  — | j                  «       }|j                  }| j                  j                  |_        |j                  «       }t        j                  j                  d| j                  j                  |d|j                  |j                  ¬«       y )NÚCASE_UPDATEr   rm   )r+   r…   r'   r(   Ú_updated_byrs   r   r`   ru   rv   r°   )r)   rx   r/   r…   ry   s        r*   r}   zCaseViewSet.perform_update  st   € Ø—‘Ó"ˆØ×&Ñ&ˆØ#Ÿ|™|×0Ñ0ˆÔØ�o‰oÓˆä×Ñ×ÑØ Ø—,‘,×#Ñ#ØØØ—f‘fØŸ™ð 	 õ 	
r,   c                 óH  — t        | j                  j                  «      }t        |«      st	        d«      ‚|j
                  }|j                  }|j                  }|j                  «        t        j                  j                  d| j                  j                  |d||¬«       y )Nr   ÚCASE_DELETEr   rm   )r   r'   r(   r   r   r/   r°   rv   rƒ   r   r`   ru   )r)   r…   r†   r/   Úrefrp   s         r*   rˆ   zCaseViewSet.perform_destroy  s…   € ä! $§,¡,×"3Ñ"3Ó4ˆÜ˜qÔ!Ü" >Ó2Ð2à—‘ˆØ× Ñ ˆØ—K‘Kˆ	Ø�‰Ôä×Ñ×ÑØ Ø—,‘,×#Ñ#ØØØØð 	 õ 	
r,   TÚGETÚPOSTÚnotes)ÚdetailÚmethodsÚurl_pathNc                 ó®  — | j                  «       }|j                  dk(  rX|j                  j                  d«      j	                  «       j                  d«      }t        t        |d¬«      j                  «      S t        |j                  d|i¬«      }|j                  d¬«       t        j                  j                  ||j                  |j                  d	   ¬
«      }t        j                  j                  d|j                  |j                   d|j"                  |j$                  ¬«       t        t        |«      j                  t&        j(                  ¬«      S )Nr·   Úauthorr¨   T)Úmanyr'   ©ÚdataÚcontext©Úraise_exceptionÚbody)Úcaser¾   rÅ   ÚCASE_NOTE_CREATEr   rm   r¡   )Ú
get_objectÚmethodr¹   ra   r’   rf   r   r!   rÁ   Úis_validr   r`   ru   r(   Úvalidated_datar   r/   rv   r°   r
   ÚHTTP_201_CREATED)r)   r'   ÚpkrÆ   r2   ÚserÚnotes          r*   r¹   zCaseViewSet.notes1  s  € à�‰Ó ˆà�>‰>˜UÒ"Ø—‘×*Ñ*¨8Ó4×8Ñ8Ó:×CÑCÀEÓJˆBÜÔ.¨r¸Ô=×BÑBÓCÐCä  g§l¡l¸YÈÐ<PÔQˆØ�‰ TˆÔ*ä×Ñ×&Ñ&ØØ—<‘<Ø×#Ñ# FÑ+ð 'ó 
ˆô 	×Ñ×ÑØ%Ø—,‘,Ø—;‘;Ø"Ø—g‘gØŸ™ð 	 ô 	
ô Ô*¨4Ó0×5Ñ5¼f×>UÑ>UÔVÐVr,   Ú	documents)rº   r»   r¼   Úparser_classesc                 ó„  — | j                  «       }|j                  dk(  r[|j                  j                  d«      j	                  «       j                  d«      }t        t        |dd|i¬«      j                  «      S t        |j                  d|i¬«      }|j                  d¬«       t        j                  j                  ||j                  |j                  |j                  d	   |j                  j!                  d
t        j"                  j$                  «      |j                  d   ¬«      }t&        j                  j                  d|j                  |j(                  d|j*                  |j,                  |j.                  |j0                  dœ¬«       t        t        |d|i¬«      j                  t2        j4                  ¬«      S )Nr·   Úuploaded_byr¨   Tr'   )r¿   rÂ   rÀ   rÃ   ÚtitleÚdoc_typeÚfile)rÆ   rŸ   rÓ   rÔ   rÕ   rÖ   ÚCASE_DOCUMENT_CREATEr   )rÔ   rÕ   r­   )rÂ   r¡   )rÈ   rÉ   rÐ   ra   r’   rf   r   r"   rÁ   rÊ   r   r`   ru   rŸ   r(   rË   rd   ÚDocTypeÚOTHERr   r/   rv   r°   rÔ   rÕ   r
   rÌ   )r)   r'   rÍ   rÆ   r2   rÎ   Údocs          r*   rÐ   zCaseViewSet.documentsM  sl  € ð �‰Ó ˆà�>‰>˜UÒ"Ø—‘×.Ñ.¨}Ó=×AÑAÓC×LÑLÈUÓSˆBÜÔ2°2¸DÈ9ÐV]ÐJ^Ô_×dÑdÓeÐeä$¨'¯,©,ÀÈGÐ@TÔUˆØ�‰ TˆÔ*ä×"Ñ"×)Ñ)ØØ—]‘]ØŸ™Ø×$Ñ$ WÑ-Ø×'Ñ'×+Ñ+¨J¼×8LÑ8L×8RÑ8RÓSØ×#Ñ# FÑ+ð *ó 
ˆô 	×Ñ×ÑØ)Ø—,‘,Ø—;‘;Ø&Ø—f‘fØŸ™Ø"Ÿy™y°c·l±lÑCð 	 ô 	
ô Ü" 3°¸GÐ0DÔE×JÑJÜ×*Ñ*ô
ð 	
r,   r&   )r9   r:   r;   r    r‰   r   r`   ra   r©   rh   rz   r}   rˆ   r   r¹   r   r   r   rÐ   rŠ   r,   r*   rœ   rœ   ×   sŽ   „ Ø%ÐØ�|‰|×*Ñ*¨8°X¸{ÈMÐ[eÓf€Hò"òBò$
ò
ñ( �4 %¨ ¸7ÔCòWó DðWñ6 ØØ˜�ØØ'¨°ZÐ@ô	ò 
óñ 
r,   rœ   c                   óJ   — e Zd ZdZegZdededefd„Zdedefd„Z	dedefd„Z
y)	ÚTenantCaseNoteDetailViewzÆ
    PATCH  /cases/{case_id}/notes/{note_id}/  -- modifier une note
    DELETE /cases/{case_id}/notes/{note_id}/  -- supprimer une note
    Seul l'auteur peut modifier/supprimer sa propre note.
    Úcase_idÚnote_idÚreturnc                 ó@  — ddl m}  ||j                  «      }|st        d«      ‚t        j
                  j                  ||¬«      j                  «       }|st        d«      ‚t        j
                  j                  ||¬«      j                  «       }|st        d«      ‚|S )Nr   )Úget_active_tenant_for_userzNo active tenant.)rv   r/   zCase not found.)rv   rÆ   zNote not found.)
Úaccounts.tenant_contextrá   r(   r   r   r`   r0   Úfirstr   r   )r)   r'   rÝ   rÞ   rá   r/   rÆ   rÏ   s           r*   Ú	_get_notez"TenantCaseNoteDetailView._get_note~  s‹   € ÝFÙ+¨G¯L©LÓ9ˆÙÜ"Ð#6Ó7Ð7Ü�|‰|×"Ñ" g°fÐ"Ó=×CÑCÓEˆÙÜÐ,Ó-Ð-Ü×Ñ×&Ñ&¨'¸Ð&Ó=×CÑCÓEˆÙÜÐ,Ó-Ð-Øˆr,   c                 ó�  — | j                  |||«      }|j                  r.|j                  |j                  j                  k7  rt	        d«      ‚|j
                  j                  d«      xs dj                  «       }|st        ddid¬«      S ||_	        |j                  ddg¬	«       d
dlm} t         ||«      j
                  «      S )Nz!You can only edit your own notes.rÅ   rW   rº   zbody is required.i�  r¡   Ú
updated_at)Úupdate_fieldsr   )r!   )rä   Ú	author_idr(   rv   r   rÁ   rd   re   r   rÅ   rs   Úcases.serializersr!   )r)   r'   rÝ   rÞ   rÏ   rÅ   r!   s          r*   ÚpatchzTenantCaseNoteDetailView.patch‹  s¦   € Ø�~‰~˜g w°Ó8ˆØ�>Š>˜dŸn™n°·±·±Ò?Ü"Ð#FÓGÐGØ—‘× Ñ  Ó(Ò.¨B×5Ñ5Ó7ˆÙÜ˜XÐ':Ð;ÀCÔHÐHØˆŒ	Ø�	‰	 ¨Ð 6ˆ	Ô7Ý8ÜÑ*¨4Ó0×5Ñ5Ó6Ð6r,   c                 óÔ   — | j                  |||«      }|j                  r.|j                  |j                  j                  k7  rt	        d«      ‚|j                  «        t        d¬«      S )Nz#You can only delete your own notes.éÌ   r¡   )rä   rè   r(   rv   r   rƒ   r   )r)   r'   rÝ   rÞ   rÏ   s        r*   rƒ   zTenantCaseNoteDetailView.delete—  sN   € Ø�~‰~˜g w°Ó8ˆØ�>Š>˜dŸn™n°·±·±Ò?Ü"Ð#HÓIÐIØ�‰ŒÜ˜sÔ#Ð#r,   N)r9   r:   r;   r<   r   r=   Úintr   rä   rê   rƒ   rŠ   r,   r*   rÜ   rÜ   v  sR   „ ñð
 *Ð*Ðð¨#ð ¸ð Àó ð
7 cð 
7°Có 
7ð$ sð $°Sô $r,   rÜ   N)5Ú	django.dbr   Údjango.db.modelsr   r   r   r   Údjango.utilsr   Úrest_frameworkr	   r
   Úrest_framework.decoratorsr   Úrest_framework.parsersr   r   r   Úrest_framework.permissionsr   Úrest_framework.responser   Úrest_framework.viewsr   Úrest_framework.exceptionsr   r   r   Úaccounts.modelsr   Úaccounts.tenant_ctxr   r   Úaccounts.permissionsr   Úcases.modelsr   r   r   r   r   ré   r   r   r    r!   r"   ÚModelViewSetr$   r@   rŒ   rœ   rÜ   rŠ   r,   r*   ú<module>rý      s”   ðå !Ý ß -Ó -Ý !ç +Ý ,ß JÑ JÝ 6Ý ,Ý (ß QÑ Qå $ß BÝ 6ç HÕ H÷õ ô˜(×/Ñ/ô ô(b
Ð*ô b
ôN<
Ð'ô <
ô~\
Ð%ô \
ô~&$˜wõ &$r,   