
    h                         S SK r S SKrS SKrS SKrS SKrS SKrS SKJr  S SKJr  S SK	J
r
  S SKJr  SrSrSrS	r " S
 S5      rS rS rS rS rS rS rS rS rg)    N)datetime)AttendanceLog)RegisteredUser)Staffzscheduler_state.jsonzuser_data.jsoninsightface_embeddingsg     r@c                   &    \ rS rSrS rS rS rSrg)TimerScheduler   c                 8    S U l         Xl        X l        SU l        g NF)_timerintervaltask
is_running)selfr   r   s      */var/www/fran/franai/services/scheduler.py__init__TimerScheduler.__init__   s     	    c                 R    SU l         U R                  5         U R                  5         g r   )r   startr   r   s    r   _runTimerScheduler._run   s    

		r   c                     U R                   (       dc  [        R                  " U R                  U R                  5      U l        SU R
                  l        U R
                  R                  5         SU l         g g )NT)r   	threadingTimerr   r   r   daemonr   r   s    r   r   TimerScheduler.start   sK    #//$--CDK!%DKKKK"DO	 r   )r   r   r   r   N)__name__
__module____qualname____firstlineno__r   r   r   __static_attributes__ r   r   r	   r	      s     
#r   r	   c                  T   [         R                  R                  [        5      (       d  g [	        [        S5       n [
        R                  " U 5      n[        R                  " US   5      sSSS5        $ ! , (       d  f       g= f! [        [
        R                  [        4 a     gf = f)z2Reads the last sync timestamp from the state file.Nrlast_sync_timestamp)ospathexists
STATE_FILEopenjsonloadr   fromisoformatIOErrorJSONDecodeErrorKeyError)fdatas     r   get_last_sync_timer6   $   sv    77>>*%%*c"a99Q<D))$/D*EF #"" T))84 s.   B /A4*	B 4
B>B B B'&B'c                      [        [        S5       n[        R                  " SU R	                  5       0U5        SSS5        g! , (       d  f       g= f! [
         a  n[        SU 35         SnAgSnAff = f)z1Writes the last sync timestamp to the state file.wr(   Nu!   ❌ Error writing to state file: )r-   r,   r.   dump	isoformatr1   print)	sync_timer4   es      r   set_last_sync_timer>   /   s^    7*c"aII,i.A.A.CDaH #"" 71!5667s3   A (AA 
AA A 
A6A11A6c                     [        S5         [        R                  " 5       n U c  [        S5        g0 nU  HJ  n[        US   5      nUR	                  SS5      UR	                  SS5      UR	                  SS5      S	S
.X'   ML     0 n[
        R                  R                  [        5      (       a0   [        [        S5       n[        R                  " U5      nSSS5        X:w  aO   [        [        S5       n[        R                  " XSS9  SSS5        [        S[         S[        U5       S35        g[        S5        g! , (       d  f       Nn= f! [        [        R                  4 a    [        S[         S35         Nf = f! , (       d  f       N~= f! [         a  n[        S[         SU 35         SnAgSnAff = f! [          a  n[        SU 35         SnAgSnAff = f)z?Fetches all users from the database and updates user_data.json.z-Scheduler: Waking up to run user sync task...Nz=Scheduler: Could not fetch users from DB. Skipping user sync.pidnamezN/Aemail	team_nameactive)rA   rB   teamstatusr'   z#Scheduler: Could not read existing z. Overwriting.r8      )indentu%   🔄 User Sync: Successfully updated z with z users.u   ❌ Error writing to : z1Scheduler: No changes in user data. Sync skipped.u-   ❌ An error occurred in the user sync task: )r;   r   get_all_with_hris_infostrgetr)   r*   r+   USER_DATA_FILEr-   r.   r/   r1   r2   r9   len	Exception)users_from_dbnew_user_datauserr@   existing_user_datar4   r=   s          r   user_sync_taskrT   7   s   	
9:$C&==? QR!Dd5k"C/'51e4"	"M "  77>>.))\.#.!)-1& /
 .E.#.!IImq9 /=n=MVTWXeTfSggnop EF /.T112 \;N;K>Z[\
 /.  E-n-=RsCDDE
  C=aSABBCs   #F> A<F> .E >D=E F> #F 3F	'F 1F> =
EE 
F> E -E>;F> =E>>F> 
FF 
F;F61F> 6F;;F> >
G GG c                      [        S5         [        5       n [        R                  " U S9nU(       a(  [	        U5        [        SUR                  5        35        gg! [         a  n[        SU 35         SnAgSnAff = f)zc
The task to be run by the scheduler. It performs an incremental sync
based on the last sync time.
z4Scheduler: Waking up to run incremental sync task...)last_sync_timez0Scheduler: State updated. Last sync time is now u4   ❌ An error occurred in the incremental sync task: N)r;   r6   r   sync_from_csv_incrementalr>   r:   rO   )rV   new_latest_timestampr=   s      r   incremental_sync_taskrY   a   s    
 

@A
J+-,FFVde34DEYEcEcEeDfgh    JDQCHIIJs   AA 
A=%A88A=c                  &   [        S5         [        R                  " 5       n U (       d  [        S5        gU  Vs0 s H  n[        US   5      U_M     nn[        R
                  R                  [        5      (       d  [        S[         S35        g[        R                  " [        5       Vs/ s H  o3R                  S5      (       d  M  UPM     nnSnU GH-  n[        R
                  R                  [        U5      n [        US	5       n[        R                  " U5      nSSS5        [        WR                  S
5      5      n	UR                  S5      n
UR                  S5      nX;   a  X)   nUS    SUS    3nUR                  SS5      nX:w  d  X:w  aV  [        SU	 SU
 SU SU SU S35        XS'   XS'   [        US5       n[        R                  " X5        SSS5        US-  nGM  GM  [        SU	 SU S35        GM0     [        SU S35        gs  snf s  snf ! , (       d  f       GN= f! , (       d  f       N\= f! [          a  n[        SU SU 35         SnAGM  SnAff = f! [          a  n[        S U 35         SnAgSnAff = f)!ze
Periodically updates name and department in .pkl files with the latest info
from the HRIS database.
u/   🔄 Starting scheduled update of .pkl files...u=   ⚠️ No hired staff found in the database. Aborting update.Nr@   u   ⚠️ Embeddings directory 'z' not found. Aborting.z.pklr   rbuser_idrA   
department
first_name 	last_namerC    u   🔄 Updating user z: Name 'z' -> 'z	', Dept ''wb   u   ⚠️ User ID z from 'z+' not found in the list of hired employees.u   ❌ Error processing file rI   u'   ✅ Scheduled update finished. Updated z files.u>   ❌ An unexpected error occurred during the scheduled update: )r;   r   get_all_hired_staff_for_updaterK   r)   r*   r+   EMBEDDINGS_DIRlistdirendswithjoinr-   pickler/   rL   r9   rO   )all_hired_staffstaff
staff_dictr4   embedding_filesupdated_filesfilename	file_pathr5   r\   current_namecurrent_departmentemployeenew_namenew_departmentr=   s                   r   update_pkl_filesrw   s   s   
 

;<5T>>@QR =LLO5c%,'.O
L ww~~n--1.1AAWXY&(jj&@W&@JJvDV1&@W'H^X>ID)T*a!;;q>D + dhhy12#xx/%)XXl%;" ()2H"*<"8!98K;P:QRH%-\\+r%BN  />3W 3G9H\NRXYaXbbkl~k  @F  GU  FV  VW  X  Y'/V-;\* ")T2a"KK0 3%* 4X OG9GH:Epqr7 (@ 	7gNOU M X +*( 32  D28*BqcBCCD
  TNqcRSSTs   'I. I. H=I. I. ,H	H.I. >I
H!!B%IH3I*I. 0II. 
I. !
H0	+I3
I	=I
I+I&I. &I++I. .
J8JJc                  ,    [        5         [        5         g)z2Runs both the user sync and attendance sync tasks.N)rT   rY   r%   r   r   combined_sync_taskry      s    r   c                  ^     [         R                  " 5         [        R                  " S5        M-  )z*Runs the scheduler in a background thread.rd   )schedulerun_pendingtimesleepr%   r   r   run_schedulerr      s#    
 

1 r   c                  b    [         R                  " [        S9n SU l        U R	                  5         g)zH
Initializes and starts the background scheduler using threading.Timer.
)targetTN)r   Threadr   r   r   )scheduler_threads    r   start_schedulerr      s*     !''}="r   )r}   r   r.   r)   rj   r{   r   franai.models.attendance_modelr   #franai.models.registered_user_modelr   franai.models.staff_modelr   r,   rM   rf   INTERVAL_SECONDSr	   r6   r>   rT   rY   rw   ry   r   r   r%   r   r   <module>r      so       	    8 > +#
!) # #&	7'CTJ$<T|
r   