U
    hI                     @   sD  d dl mZmZmZ d dlmZ d dlmZmZm	Z	 d dl
m
Z
mZmZ d dlZ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mZ d dlmZ d dlmZ d dlZe e!Z"e Z#G dd dZ$e#%dddddeefe&e&e&e&edddZ'e#%dddeefe(e	e( e	e( edddZ)dS )    )	APIRouterDependsHTTPException)Session)ListDictOptional)datetime	timedeltatimezoneN)get_db)ActivityRecord)Config)DeveloperDiscovery)FixedDeveloperDiscovery)DynamicActivityWatchClient)ActivityCategorizer)extract_project_infoc                   @   s~   e Zd ZdZedddZdeeeeeddd	Zed
ddZ	eeeeedddZ
eedddZeee dddZdS ) EnvironmentBasedDeveloperServicezMService to handle developer list based on environment - Fixed for existing DB)dbc                 C   s   || _ t|| _d S )N)r   r   	discovery)selfr    r    ./fixed_dynamic_developer_api.py__init__   s    z)EnvironmentBasedDeveloperService.__init__FT)scan_network
scan_localscan_databaseforce_refreshreturnc                 C   s$   t  r|  S | ||||S dS )z>Get developers list based on environment (local vs production)N)r   Zis_local_get_local_developer_only_get_all_developers)r   r   r   r   r   r   r   r   get_developers_list   s    z4EnvironmentBasedDeveloperService.get_developers_list)r   c                 C   s6  zt  }tjp|}ddlm} | j|dd|i }|rR|d }|d }n|}t	
d| d | j }g }|r|D ]v}|d|d	  |||d
 |d	 ddd|d| d|d	  || |ttj |dd|ddd q~n~| |}	|d| ||dd|	dkr$dnd|	dkr4dnd|	dkrLd|	 dnd|||	| ||	dkrjdnddd |dt|ttj |dt kr|n|dW S  tk
r0 }
 zht	d|
  d tjt  ddddd!t  tjdd"dddgddttj tjt|
d# W Y S d"}
~
X Y nX d"S )$z'Return only the current local developerr   textz
                SELECT developer_id, name 
                FROM developers 
                WHERE name = :dev_name OR developer_id = :dev_name
                LIMIT 1
            dev_name   zLocal developer 'z' not found in developers tableZlocal_porthostonlinelocalzLocal ActivityWatch instance	device_id_versionunknownbucket_count)idnameZhostnamer(   r'   statussourcedescriptionr+   developer_idactivity_count	last_seenr-   r/   Z	local_db_Z	localhosti  Zdatabase_onlyZofflinedatabasezLocal developer (z activities in database)zLocal developer (no data yet)local_developer_id)
developersenvironmenttotal_countdiscovered_atlocal_developerr9   zError getting local developer: Zlocal_fallbackz Local developer (database error)N)r:   r;   r<   r=   r>   error)socketZgethostnamer   ZLOCAL_DEVELOPER_NAME
sqlalchemyr$   r   executefetchoneloggerwarningr   Zdiscover_local_instancesappendget_get_activity_count_safer	   nowr   utc	isoformat_get_last_activity_time_safelenlocals	Exceptionr?   str)r   Zlocal_hostnameZlocal_developer_namer$   
dev_resultr9   Zlocal_instancesr:   instanceZdb_activity_counter   r   r   r    '   s    
 





	z:EnvironmentBasedDeveloperService._get_local_developer_onlyc           	   
   C   s   zt d | jj|||d}|D ]l}|dp8|d}| ||d< |ds"| ||d< |d r"t|d tr|d 	 n|d |d< q"|dt
|ttj	 dd	W S  tk
r } z*t d
|  tddt| dW 5 d}~X Y nX dS )z5Get all developers from all sources (production mode)z&Performing full developer discovery...)r   r   r   r5   r0   r6   r7   Z
productionF)r:   r;   r<   r=   Z
from_cachez"Error discovering all developers:   zError discovering developers: Zstatus_codeZdetailN)rD   infor   Zdiscover_all_developersrG   rH   rL   
isinstancer	   rK   rM   rI   r   rJ   rO   r?   r   rP   )	r   r   r   r   r   Zdiscovered_developersZdevdev_idrS   r   r   r   r!      s.    

(z4EnvironmentBasedDeveloperService._get_all_developers)developer_id_or_namer   c           
   
   C   s   zjddl m}m} | j|d||d }|rb|d }| j|dd|i}| }|p^dW S W dS W n tk
r } zjt	d| d|  z:| j|d	}| }	t
d
|	  |	pdW  W Y S    Y W Y 
dS X W 5 d}~X Y nX dS )z)Safely get activity count for a developerr   )funcr$   
                SELECT developer_id 
                FROM developers 
                WHERE developer_id = :dev_id OR name = :dev_name
                LIMIT 1
            rX   r%   z
                    SELECT COUNT(*) 
                    FROM activity_records 
                    WHERE developer_id = :dev_id
                rX   z!Error getting activity count for : z%SELECT COUNT(*) FROM activity_recordsz Returning total activity count: N)rA   rZ   r$   r   rB   rC   scalarrO   rD   rE   rV   )
r   rY   rZ   r$   rQ   r5   resultcountrS   totalr   r   r   rH      s4    
 

z9EnvironmentBasedDeveloperService._get_activity_count_safec              
   C   s   znddl m} | j|d||d }|rf|d }| j|dd|i}| }|r`| ndW S W dS W n> tk
r } z t	d| d	|  W Y dS d}~X Y nX dS )
z-Safely get last activity time for a developerr   r#   r[   r\   z
                    SELECT MAX(timestamp)
                    FROM activity_records 
                    WHERE developer_id = :dev_id
                rX   Nz%Error getting last activity time for r]   )
rA   r$   r   rB   rC   r^   rK   rO   rD   rE   )r   rY   r$   rQ   r5   r_   Z	last_timerS   r   r   r   rL      s(    
 
z=EnvironmentBasedDeveloperService._get_last_activity_time_safeN)FTTF)__name__
__module____qualname____doc__r   r   boolr   r"   r    r!   rP   intrH   r   rL   r   r   r   r   r      s(        k  "+r   z/developersFT)r   r   r   r   r   c                    s   t |}|| |||S )z(Get developers list based on environment)r   r"   )r   r   r   r   r   servicer   r   r   r"     s    	r"   z/activity-data/{developer_id})r5   
start_dateend_dater   c              
      s  zt  }|r"t|dd}nttjjddddd}|rTt|dd}nttj}t|}| }t	fdd|d D d  st
d	d
dg }	d}
 d dkr6zDt }| r|||}	d}
td d  dt|	 d W n> tk
r4 } ztd d  d|  W 5 d}~X Y nX |	szrddlm} ||d dpf d ||d } fdd|D }	d}
td d  dt|	 d W n8 tk
r } ztd|  g }	W 5 d}~X Y nX |	D ]}|ds@t|}|dpd|d< |dp&d |d< |d!p:d"|d!< ||d#d$|d%d$}|d& |d&< |d' |d'< |d( |d)< qddd*ddd*ddd*ddd*ddd*d+}|	D ]L}|d&d,}||kr|| d-  d.7  < || d/  |d/d7  < qtd0d |	D }|D ]@}|dkrLt|| d/ | d1 d.|| d2< nd|| d2< q|	 |
|| | d3t|	|d4W S  tk
r } z0td5 d|  t
d6d7t| dW 5 d}~X Y nX dS )8z*Get activity data for a specific developerZz+00:00r   )ZhourZminutesecondZmicrosecondc                 3   s   | ]}|d   kr|V  qdS )r0   Nr   ).0d)r5   r   r   	<genexpr>+  s      z.get_developer_activity_data.<locals>.<genexpr>r:   Ni  zDeveloper not foundrU   r8   r2   r)   ZactivitywatchzRetrieved live data for r1   r]   z activitieszFailed to get live data for r#   a  
                    SELECT 
                        ar.application_name,
                        ar.window_title,
                        ar.duration,
                        ar.timestamp,
                        ar.category,
                        ar.detailed_activity,
                        ar.url,
                        ar.file_path,
                        ar.developer_id,
                        ar.project_name,
                        ar.project_type,
                        ar.project_file,
                        d.name as developer_name
                    FROM activity_records ar
                    LEFT JOIN developers d ON ar.developer_id = d.developer_id
                    WHERE ar.developer_id = :dev_id
                    AND ar.timestamp >= :start_date
                    AND ar.timestamp <= :end_date
                    ORDER BY ar.duration DESC
                    LIMIT 1000
                r5   )rX   ri   rj   c                    sr   g | ]j}|j |jp d  |j|j|jp(d|jr8|j nd|jpBd|jpL|j|j	pTd|j
p\d|j|j|jdqS )r1   r   NZOther )r5   developer_nameapplication_namewindow_titleduration	timestampcategorydetailed_activityurl	file_pathproject_nameproject_typeproject_file)r5   rq   rr   rs   rt   ru   rK   rv   rw   rx   ry   rz   r{   r|   )rm   record)	developerr   r   
<listcomp>`  s   
z/get_developer_activity_data.<locals>.<listcomp>zRetrieved database data for z Error getting database records: rz   Z
Unassignedr{   ZGeneralr|   ZActivityrs   rp   rr   rv   ZsubcategoryZ
confidenceZcategory_confidence)r`   rt   )Z
productiveZbrowserZserverznon-workuncategorizedr   r`   r&   rt   c                 s   s   | ]}|d  V  qdS )rt   Nr   )rm   itemr   r   r   ro     s     d   Z
percentage)startend)datar~   data_sourceZ
total_timeZ
date_ranger6   category_summaryz Error getting activity data for rT   zError getting activity data: )r   r	   ZfromisoformatreplacerI   r   rJ   r   r"   nextr   r   Ztest_connectionZget_activity_datarD   rV   rM   rO   rE   rA   r$   rB   rG   Zfetchallr?   r   Zget_detailed_categorysumroundrK   rP   )r5   ri   rj   r   Zcategorizerr   r   rh   Zdevelopers_resultZactivity_datar   ZclientrS   r$   Z
db_recordsZactivityZproject_infoZcategory_infor   catZtotal_durationr   )r~   r5   r   get_developer_activity_data  s    $,

$


 
$
r   )*Zfastapir   r   r   Zsqlalchemy.ormr   typingr   r   r   r	   r
   r   osZloggingr8   r   Zmodelsr   Zconfigr   Zdeveloper_discoveryr   Zfixed_developer_discoveryr   Zdynamic_activitywatch_clientr   Zactivity_categorizerr   Zimproved_project_extractorr   r@   Z	getLoggerrb   rD   Zrouterr   rG   rf   r"   rP   r   r   r   r   r   <module>   sR   
 p