U
    h1                  E   @   s^  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
 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eeZe Zdd	 Zd
dddddddddddddddddddddd d!d"d#d$d%d&d'd(d)d*d+d,d-d.d/d0d1d2d3d4d5d6d7d8d9d:d;d<d=d>d?d@dAdBdCdDdEdFdGdHdIdJdKdLdMdNgEdOdPdQdRdSdTdUdVdWg	dXdYdZd[d\d]d^d_d`dadbdcdddedfdgdhdidjdkdldmdndodpdqdrdsgdtdudvdwdxdydzd{d|d}d~ddddddddddddddddddddddg!dZdeeeedddZeddddeefeee ee ee edddZedddeefeee ee edddZ e!deefedddZ"dS )    )	APIRouterDependsHTTPExceptionQuery)Session)textand_func)get_db)datetimetimezone	timedelta)OptionalListDictNc                 C   sF   | d }t |d }t |d d }t |d }| d| d| dS )z/Convert milliseconds to hours, minutes, seconds    <   zh zm s)int)millisecondstotal_secondshoursminutesseconds r   8/var/www/html/timesheet/backend/enhanced_activity_api.pyformat_duration   s
    r   zcode.execodez
cursor.execursorz
devenv.exeznotepad++.exezsublime_text.exezatom.exezbrackets.exevimemacszpycharm.exezpycharm64.exezidea.exez
idea64.exezwebstorm.exezphpstorm.exezrubymine.exez
goland.exez	clion.exez	rider.exezdatagrip.exezstudio64.exezeclipse.exeznetbeans.exezword.exezwinword.exez	excel.exezpowerpnt.exezoutlook.exez	teams.exez	slack.exezdiscord.exezzoom.exez	skype.exez
notion.exezobsidian.exezonenote.exezevernote.exeztodoist.exez
trello.exez	asana.exezclickup.exeterminalzcmd.exezpowershell.exebashzgit-bash.exez
conemu.exez	hyper.exeZiterm2ZwarpZ	alacrittyzpostman.exezinsomnia.exezfiddler.exeztableplus.exezdbeaver.exezheidisql.exeznavicat.exezgit.exezgitkraken.exezsourcetree.exezfork.exez
docker.exezdockerdesktop.exezvirtualbox.exez
vmware.exezfilezilla.exez
chrome.exezfirefox.exez
msedge.exez	opera.exez	brave.exezvivaldi.exesafariziexplore.exebrowserz
winscp.exez	putty.exezmobaxterm.exezsecurecrt.exez
xshell.exez	royal tsxztermius.exezcyberduck.exeZtransmitZforkliftzexpandrive.exez	mysql.exezpsql.exez	mongo.exezredis-cli.exezpgadmin4.exe
phpmyadminZadminerz
sequel prozmongodb compass.exezrobo 3t.exezredis desktop manager.exeapachenginxZhttpdznode.exezphp.exez
python.exezspotify.exezvlc.exezmpv.exezwmplayer.exez
itunes.exeznetflix.exezdisney+.exezprime videozyoutube musicz	steam.exezepicgameslauncher.exez
origin.exez	uplay.exezleagueoflegends.exezvalorant.exezminecraft.exez
roblox.exezobs.exez	obs64.exezstreamlabs obs.exez
xsplit.exezphotoshop.exezillustrator.exezpremiere.exezaftereffects.exezblender.exezmaya.exez
3dsmax.exezcinema4d.exezwhatsapp.exeztelegram.exez
signal.exezmessenger.exe)productivityr%   servernon-work )app_namewindow_titleurlreturnc                    s   | sdS |    |r|  ndt D ]f\}}t fdd|D r(|dkrrdddd	d
dddddg
}tfdd|D r dS |  S q(dksdkrdS tfdddD rdS tfdddD rdS dS )zDCategorize activity based on application name, window title, and URLuncategorizedr,   c                 3   s   | ]}| kV  qd S Nr   ).0app)	app_lowerr   r   	<genexpr>M   s     z&categorize_activity.<locals>.<genexpr>r%   githubstackoverflowdocsapi	localhostjira
confluenceawsazurezgoogle cloudc                 3   s   | ]}|   kV  qd S r2   )lower)r3   domain)r/   r   r   r6   S   s     r)   youtubenetflixr+   c                 3   s   | ]}| kV  qd S r2   r   r3   Ztermtitle_lowerr   r   r6   [   s     )sshr"   Zconsolecommandr*   c                 3   s   | ]}| kV  qd S r2   r   rD   rE   r   r   r6   ^   s     )z.pyz.jsz.htmlz.cssz.javaz.cpp)r@   APP_CATEGORIESitemsany)r-   r.   r/   categoryappswork_domainsr   )r5   rF   r/   r   categorize_activityC   s0    
    
rO   z!/api/activity-data/{developer_id})developer_id
start_dateend_daterL   dbc                    s\  z|rt |dd}nt tjjddddd}|rNt |dd}nt tj}td}||| ||d}g }	d}
dddddd}|D ]}|d pd	}|d
 pd	}|d pd	}|d pd}i }|d rz(t|d t	rt
|d n|d }W n   Y nX |d r |d }nt|||}|r>||kr>q|d |d |||||d rh|d  nd||d |d
}|	| |
|7 }
||  |7  < qi }| D ]@\}}|t|
dkr||
 d nddt|d dd||< q|	t|
t|	|| | ddW S  tk
rV } z$td|  tdt	|dW 5 d}~X Y nX dS )z6Get categorized activity data for a specific developerZz+00:00r   )hourminutesecondmicroseconda  
            SELECT 
                id,
                developer_id,
                application_name,
                window_title,
                url,
                duration,
                timestamp,
                activity_data,
                category,
                project_name
            FROM activity_records
            WHERE developer_id = :dev_id
              AND timestamp >= :start_date
              AND timestamp <= :end_date
            ORDER BY timestamp DESC
        )dev_idrQ   rR   r)   r%   r*   r+   r1      r,                        N	   )
idrP   application_namer.   r/   duration	timestamprL   project_nameactivity_detailsd   r   )rf   
percentager   )startend)data
total_timetotal_activitiescategory_breakdown
date_rangezError fetching activity data:   status_codedetail)r   fromisoformatreplacenowr   utcr   execute
isinstancestrjsonloadsrO   	isoformatappendrJ   roundr   len	Exceptionloggererrorr   )rP   rQ   rR   rL   rS   rl   rm   queryresult
activitiestotal_durationrq   rowr-   r.   r/   rf   ri   Zactivity_categoryactivityZcategory_percentagescater   r   r   get_developer_activity_datac   s    	

(


r   z'/api/activity-categories/{developer_id})rP   rQ   rR   rS   c              
      s`  zt | ||d|I dH  g g g g g d} d D ]"}|d }||kr2|| | q2i }| D ]\}}i }	|D ]0}|d }
|
|	krd|	|
< |	|
  |d 7  < qrt|	 dd	 d
ddd }|dd t|tdd |D d  fdd|D d||< qb| d  d dW S  tk
rZ } z$td|  t	dt
|dW 5 d}~X Y nX dS )z'Get activity data grouped by categoriesNrZ   rn   rL   re   r   rf   c                 S   s   | d S )Nra   r   )xr   r   r   <lambda>      z,get_activity_by_categories.<locals>.<lambda>T)keyreverse
   rj   c                 s   s   | ]}|d  V  qdS )rf   Nr   )r3   ar   r   r   r6     s     z-get_activity_by_categories.<locals>.<genexpr>r   c                    s>   g | ]6\}}||t  d  dkr.| d   d ndddqS )ro   r   rj   ra   )namerf   rk   )r   )r3   r4   rf   Zall_datar   r   
<listcomp>  s
   $z.get_activity_by_categories.<locals>.<listcomp>)r   rp   r   top_applicationsrq   rr   )
categoriessummaryrr   z'Error fetching categorized activities: rs   rt   )r   r   rJ   sortedr   sumr   r   r   r   r}   )rP   rQ   rR   rS   Zcategorized_datar   rL   category_statsr   Zapp_durationsr-   Ztop_appsr   r   r   r   get_activity_by_categories   s^        


r   z/api/update-activity-categories)rS   c              
      s   zt d}| |}d}|D ]^}|d }|d p2d}|d p>d}|d pJd}t|||}	t d}
| |
|	|d |d7 }q|   d	|d
| ddW S  tk
r } z,|   td|  tdt	|dW 5 d}~X Y nX dS )z:Update all uncategorized activities with proper categoriesz
            SELECT id, application_name, window_title, url
            FROM activity_records
            WHERE category IS NULL OR category = ''
        r   ra   r,   r[   r\   z}
                UPDATE activity_records
                SET category = :category
                WHERE id = :id
            )rL   rd   TzSuccessfully categorized z activities)successupdated_countmessagezError updating categories: rs   rt   N)
r   r{   rO   commitr   rollbackr   r   r   r}   )rS   r   r   r   r   Zactivity_idr-   r.   r/   rL   Zupdate_queryr   r   r   r   update_activity_categories#  s2    


r   )r,   r,   )#fastapir   r   r   r   sqlalchemy.ormr   
sqlalchemyr   r   r	   databaser
   r   r   r   typingr   r   r   r~   logging	getLogger__name__r   routerr   rI   r}   rO   getr   r   postr   r   r   r   r   <module>   sf  
                                                                                 
                         , zD