B
    eb#G                 @   s   d dl Z d dlmZ d dlmZ d dlmZ d dlmZ	 d dl
mZ d dlT d dlmZ 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mZmZmZmZ d dlmZ G dd dejZ G dd dejZ!dS )    N)get_user_model)models)Q)gettext_lazy)settings)*)DepartmentForeignKey)
Department)OperationNotAllowed)NODE_APPROVEDNODE_PENDINGNODE_REJECTEDNODE_STATES)ContentType)r   r   	NODE_VOIDr   NODE_REVOKENODE_WITHDRAW)workflow_approve_signalc               @   st  e Zd ZdZejddddejdZejdddZ	ej
d	d
dZejddddejdZejdddejdZejdddejdZej
edeeddZejedddZejedddZejddddZejdddZeeedddejdZdd Zd d! Zd>d#d$Zd?d%d&Zd@d'd(Z d)d* Z!d+d, Z"d-d. Z#d/d0 Z$d1d2 Z%d3d4 Z&d5d6 Z'd7d8 Z(d9d: Z)G d;d< d<Z*d=S )ANodeInstancezf
        Node instance will be create for every id node in the workflow template(worfklow_engine)
    zworkflow.WorkflowNodeZworkflow_nodeT)verbose_nameblanknull	on_deletename   )
max_lengthZnumber_orderr   )defaultzworkflow.WorkflowInstanceworkflow_instancezpersonnel.EmployeeZnode_approver_employee)r   r   r   zaccounts.MyUserZnode_approver_admin
node_stateF)r   choicesZeditableis_last_nodeis_next_noderemark   )r   r   
apply_time)r   departmentsc             C   s$   | j d k	r| j S | jd k	r | jS d S )N)approver_employeeapprover_admin)self r)   AG:\easytimepro\master/mysite/workflow\models\workflow_instance.pyget_approver*   s
    

zNodeInstance.get_approverc             C   s   t |t s|| _n|| _d S )N)
isinstancer   r&   r'   )r(   approverr)   r)   r*   set_approver2   s    zNodeInstance.set_approver c             C   sn   t j| jj}| }|jj| jjjd	 }|rj|jj
| jjjd}||_tj |_|j|_|  d S )N)id)r   objects
get_for_idr   content_typemodel_classfilter	exceptionr0   firstgetZaudit_reasondatetimenowZ
audit_timeaudit_user_idsave)r(   r-   r"   ctmodelobjZupdated_data_to_modelsr)   r)   r*   update_data_to_models8   s    z"NodeInstance.update_data_to_modelsc             C   s   |  |rt| _| | || _tj | _|   | 	|| t
|t rftjstj| j| jd n| j r| j  | j  tjstj| j| jd qtjt| jt|  d nttdtddS )zx
            Check if the user has has the role required to approve the node
            or raise an exception.
        )senderWorkflowInstance)rA   r   r   node_approverZ/the_user_is_not_allow_to_approve_this_task_nodeN)'is_user_allow_to_operate_over_this_noder   stater.   r"   r9   r:   r$   r<   r@   r,   r   r   ACTIVE_CELERYZ!on_approve_node_instance_by_adminsend	__class__r   is_approvedapprove_exceptiondo_after_approvedZon_approve_node_instancer   r   r+   r
   _)r(   r-   r"   r)   r)   r*   approveC   s*    





zNodeInstance.approvec             C   s   |  |rt| _| | || _tj | _|   |j	rF| 
|| | j  tjst|t rvtj| j| jd qtj| j| jd qtjt| jt|  d nttdtddS )zw
            Check if the user has has the role required to reject the node
            or raise an exception.
        )rA   rB   )rA   r   r   Zstate_approverZIthe_user_does_not_have_the_privileges_to_operate_over_this_workflows_nodeZ.the_user_is_not_allow_to_reject_this_task_nodeN)rD   r   rE   r.   r"   r9   r:   r$   r<   Zis_employeer@   r   reject_exceptionr   rF   r,   r   Z on_reject_node_instance_by_adminrG   rH   Zon_reject_node_instancer   r   r+   r
   rL   )r(   r-   r"   r)   r)   r*   rejectc   s$    



zNodeInstance.rejectc             C   s6   | j jdks| j jdkrdS t| j j jdddS )zW
            return all the roles that are able to approve or reject this node
        Nr/   r0   T)flat)node_enginer-   listallvalues_list)r(   r)   r)   r*   get_node_roles   s    zNodeInstance.get_node_rolesc             C   s   | j j jdddS )Nr0   T)rP   )rQ   ZnotifierrS   rT   )r(   r)   r)   r*   get_notifier_roles   s    zNodeInstance.get_notifier_rolesc             C   s   | j j jdddS )Nr0   T)rP   )rQ   r-   rS   rT   )r(   r)   r)   r*   get_approver_roles   s    zNodeInstance.get_approver_rolesc             C   s&   t |t s|jj|  dS dS dS )zO
            checks if the user has the role to operate over this node
        )Zid__inTN)r,   r   Z	flow_roler5   rU   )r(   r-   r)   r)   r*   rD      s    z4NodeInstance.is_user_allow_to_operate_over_this_nodec             C   s   | j d k	r| j dS dS )Nz%Y-%m-%d %H:%M:%S )r$   strftime)r(   r)   r)   r*   get_time_stamp_string_format   s    
z)NodeInstance.get_time_stamp_string_formatc             C   s
   | j tkS )N)rE   r   )r(   r)   r)   r*   
is_pending   s    zNodeInstance.is_pendingc             C   s
   | j tkS )N)rE   r   )r(   r)   r)   r*   rI      s    zNodeInstance.is_approvedc             C   s
   | j tkS )N)rE   r   )r(   r)   r)   r*   is_rejected   s    zNodeInstance.is_rejectedc             C   s   t t| jdS )Nr/   )dictr   r8   rE   )r(   r)   r)   r*   get_state_name   s    zNodeInstance.get_state_namec               @   s   e Zd ZdZedZdS )zNodeInstance.MetaworkflowZworkflow_node_instanceN)__name__
__module____qualname__	app_labelrL   r   r)   r)   r)   r*   Meta   s   rd   N)r/   )r/   )r/   )+r`   ra   rb   __doc__r   
ForeignKeyCASCADErQ   	CharFieldr   SmallIntegerFieldorderr   r&   r'   rL   r   r   rE   BooleanFieldr    r!   r"   ZDateTimeFieldr$   r   r	   r%   r+   r.   r@   rM   rO   rU   rV   rW   rD   rZ   r[   rI   r\   r^   rd   r)   r)   r)   r*   r      s>   




 
	r   c               @   s  e Zd ZejedddZejedddZeedZ	eedZ
ejeddd	Zejed
ddZeedZeedZejedddZejddejdZejddejdZejddddejdZdd Zdd Zdd Zdd Zd d! Zd"d# Zd$d% Zd&d' Z d(d) Z!d*d+ Z"d,d- Z#d.d/ Z$d0d1 Z%d2d3 Z&d4d5 Z'd6d7 Z(d8d9 Z)d:d; Z*dbd=d>Z+dcd?d@Z,dAdB Z-dCdD Z.dEdF Z/dGdH Z0dIdJ Z1dKdL Z2dMdN Z3dOdP Z4dQdR Z5dSdT Z6dUdV Z7dWdX Z8dYdZ Z9d[d\ Z:ddd^d_Z;G d`da daZ<d<S )erB   workflow_coder#   )r   workflow_name
start_dateend_date
issue_dateT)Zauto_now_addZworkflow_descriptionr3   inform_typedel_flagF)r   zpersonnel.EmployeeZworkflow_instance_user)r   r   zworkflow.AbstractException)r   r   zworkflow.WorkflowEngineworkflow_engine)r   r   r   r   c             C   s   | j jS )N)employeer0   )r(   r)   r)   r*   get_sender_id   s    zWorkflowInstance.get_sender_idc             C   s    |   }|rt| S d S d S )N)get_last_active_noderR   rV   )r(   noder)   r)   r*   #get_previous_node_notifier_roles_id   s    z4WorkflowInstance.get_previous_node_notifier_roles_idc             C   s   |   }|r|jjS dS d S )NF)rv   rQ   notify_by_overall)r(   rw   r)   r)   r*   #get_previous_node_notify_by_overall   s    z4WorkflowInstance.get_previous_node_notify_by_overallc             C   s   |   }|r|jjS dS d S )NF)get_next_noderQ   ry   )r(   rw   r)   r)   r*   get_next_node_notify_by_overall   s    z0WorkflowInstance.get_next_node_notify_by_overallc             C   s   |   }|r|jjS dS d S )NF)r{   rQ   approver_by_overall)r(   rw   r)   r)   r*   !get_next_node_approver_by_overall   s    z2WorkflowInstance.get_next_node_approver_by_overallc             C   s   |   }|r|jS d S d S )N)rv   Zdepartments_id)r(   rw   r)   r)   r*   get_previous_node_departments   s    z.WorkflowInstance.get_previous_node_departmentsc             C   s   |   }|r|jjS dS d S )NF)rv   rQ   r}   )r(   rw   r)   r)   r*   %get_previous_node_approver_by_overall   s    z6WorkflowInstance.get_previous_node_approver_by_overallc             C   s    |   }|rt| S d S d S )N)r{   rR   rV   )r(   rw   r)   r)   r*   get_next_node_notifier_roles_id   s    z0WorkflowInstance.get_next_node_notifier_roles_idc             C   s    |   }|rt| S d S d S )N)get_current_noderR   rW   )r(   rw   r)   r)   r*   "get_current_node_approver_roles_id   s    z3WorkflowInstance.get_current_node_approver_roles_idc             C   s    |   }|rt| S d S d S )N)r{   rR   rW   )r(   rw   r)   r)   r*   get_next_approver_roles_id   s    z+WorkflowInstance.get_next_approver_roles_idc             C   s    |   }|rt| S d S d S )N)r{   rR   rV   )r(   rw   r)   r)   r*   get_next_notifier_roles_id   s    z+WorkflowInstance.get_next_notifier_roles_idc             C   s   g }|   }| dk	sdr,|t|  }xB| jdj|jd D ]$}| dk	s\drH|t|  }qHW t|dkrtt	|S |S )z
            returns a list with the notifiers roles id without duplicates
            or an empty list if there is no defined notifiers roles for that node
        Nr/   rj   )Z	order__ltr   )
r   rW   rR   nodeinstance_setorder_byr5   rj   rS   lenset)r(   ZrolesZcurrent_noderw   r)   r)   r*   (get_all_previous_node_approvers_roles_id  s     z9WorkflowInstance.get_all_previous_node_approvers_roles_idc             C   sX   |    }t|t r$|j}d}n|r4|j}|j}|dk	r@|ndd |dk	rR|nd S )zy
            the employee might not have a first name or last name
            that is why I need the conditions
        ZAdministratorNr/   rX   )rv   r+   r,   r   ZusernameZ
first_name	last_name)r(   rC   Z	fist_namer   r)   r)   r*   get_last_approver  s    z"WorkflowInstance.get_last_approverc             C   s   |    S )N)r   r^   )r(   r)   r)   r*   get_current_state_name$  s    z'WorkflowInstance.get_current_state_namec             C   s   |    S )N)rv   r^   )r(   r)   r)   r*   get_last_operation_state_name'  s    z.WorkflowInstance.get_last_operation_state_namec             C   s   |    S )N)rv   rZ   )r(   r)   r)   r*   get_last_operation_timestamp*  s    z-WorkflowInstance.get_last_operation_timestampc             C   s   ddl m} |  rF|  r4| jjtdd S | jd	 S n@| 
 r`| jjtd	 S | j|td|tdB d S d S )Nr   )r   )rE   rj   )django.db.modelsr   r[   is_partially_approvedr   r5   r   r   Zlastr7   r\   r   r   )r(   r   r)   r)   r*   rv   .  s    z%WorkflowInstance.get_last_active_nodec             C   sB   t j| j}| }|jj| jjd }t	|dr>|
  d S )N)r0   after_approved)r   r1   r2   r3   r4   r5   r6   r0   r7   hasattrr   )r(   r=   r>   r?   r)   r)   r*   rK   >  s
    
z"WorkflowInstance.do_after_approvedNc             C   sT   t j| j}| }|jj| jjd }t	j
t| t|d t|drP|  d S )N)r0   )rA   r   r   rC   after_revoked)r   r1   r2   r3   r4   r5   r6   r0   r7   r   rG   r   r   r   r   )r(   r-   r=   r>   r?   r)   r)   r*   do_after_revokeE  s    

z WorkflowInstance.do_after_revokec             C   sD   t j| j}| }|jj| jjd }t	j
t| t|jd d S )N)r0   )rA   r   r   rC   )r   r1   r2   r3   r4   r5   r6   r0   r7   r   rG   r   r   r;   )r(   r-   r=   r>   r?   r)   r)   r*   do_after_withdrawN  s
    
z"WorkflowInstance.do_after_withdrawc             C   s   | j   d S )N)r6   rM   )r(   r)   r)   r*   rJ   U  s    z"WorkflowInstance.approve_exceptionc             C   s$   | j   tjs tj| j| d d S )N)rA   rB   )r6   rO   r   rF   Zon_reject_workflow_exceptionrG   rH   )r(   r)   r)   r*   rN   Y  s    
z!WorkflowInstance.reject_exceptionc             C   s
   | j  S )N)r6   rI   )r(   r)   r)   r*   is_exception_approved^  s    z&WorkflowInstance.is_exception_approvedc             C   s
   | j  S )N)r6   r\   )r(   r)   r)   r*   is_exception_rejecteda  s    z&WorkflowInstance.is_exception_rejectedc             C   s
   | j  S )N)r6   r[   )r(   r)   r)   r*   is_exception_pendingd  s    z%WorkflowInstance.is_exception_pendingc             C   sV   |   r| jjtd S |  r:| jjtdd S | jjtdd S d S )N)rE   rj   )	r\   r   r5   r   r7   r[   r   r   Zexclude)r(   r)   r)   r*   r   h  s
    z!WorkflowInstance.get_current_nodec             C   s(   |   r | jjtdd S dS d S )N)rE   rj   F)r[   r   r5   r   r   r7   )r(   r)   r)   r*   r{   r  s    zWorkflowInstance.get_next_nodec             C   s   | j jtd S )N)rE   )r   r5   r   exists)r(   r)   r)   r*   r\   z  s    zWorkflowInstance.is_rejectedc             C   s"   | j ttdttdB   S )N)rE   )r   r5   r   r   r   r   )r(   r)   r)   r*   rI   }  s    zWorkflowInstance.is_approvedc             C   s   |   p|   S )N)r\   rI   )r(   r)   r)   r*   r[     s    zWorkflowInstance.is_pendingc             C   s   | j jtd S )N)rE   )r   r5   r   r   )r(   r)   r)   r*   is_auditing  s    zWorkflowInstance.is_auditingc             C   s   | j jtd S )N)rE   )r   r5   r   r   )r(   r)   r)   r*   r     s    z&WorkflowInstance.is_partially_approvedc             C   s   | j jtd S )N)rE   )r   r5   r   count)r(   r)   r)   r*   get_approved_nodes_count  s    z)WorkflowInstance.get_approved_nodes_countc             C   s0   |   r|  || nttdtdd S )N=the_workflow_is_inactive_is_not_posible_to_realize_any_action)r[   r   rM   r
   rL   )r(   approver_auth_userr"   r)   r)   r*   approve_current_node_by  s    z(WorkflowInstance.approve_current_node_byr/   c             C   s0   |   r|  || nttdtdd S )Nr   )r[   r   rO   r
   rL   )r(   r   r"   r)   r)   r*   reject_current_node_by  s    z'WorkflowInstance.reject_current_node_byc               @   s   e Zd ZdZedZdS )zWorkflowInstance.Metar_   r   N)r`   ra   rb   rc   rL   r   r)   r)   r)   r*   rd     s   rd   )N)N)r/   )=r`   ra   rb   r   rh   rL   rl   rm   Z	DateFieldrn   ro   rp   descriptionZIntegerFieldr3   ri   rq   rk   rr   rf   rg   rt   ZOneToOneFieldr6   rs   ru   rx   rz   r|   r~   r   r   r   r   r   r   r   r   r   r   r   rv   rK   r   r   rJ   rN   r   r   r   r   r{   r\   rI   r[   r   r   r   r   r   rd   r)   r)   r)   r*   rB      sb   

	


rB   )"r9   Zdjango.contrib.authr   Z	django.dbr   r   r   Zdjango.utils.translationr   rL   Zdjango.confr   Z2mysite.notifications.notification_center.receiversZmysite.personnel.fieldsr   Zmysite.personnel.modelsr	   Z9mysite.workflow.exceptions.workflow_validation_exceptionsr
   Zmysite.workflow.models_choicesr   r   r   r   Z"django.contrib.contenttypes.modelsr   r   r   r   Zmysite.workflow.signalsr   ZModelr   rB   r)   r)   r)   r*   <module>   s      