U
    i5                     @   s  d dl Z d dlZd dlmZmZmZmZ d dlmZmZm	Z	 d dl
mZmZmZ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 d d	lmZmZmZmZmZm Z m!Z! ed
dgdZ"ej#$ej#%e&dddZ'e(dddZ)e"j*de ddd Z+dddddd dZ,eddeddedded dd!Z-ee(d"d#d$Z.e	e dd%d&Z/dKee0ed(d)d*Z1e"j*d+ee deefed,d-d.Z2e"j3d+eej4d/eefeed0d1d2Z5e"j*d3edeefe6ed4d5d6Z7e"j8d3edeefe6eed7d8d9Z9e"j:d3ej;d:eefe6ed4d;d<Z<e"j*d=edeefed,d>d?Z=e"j*d@ee deefe6ed4dAdBZ>e"j3d@eej4d/edCeefe6eedDdEdFZ?e"j:dGej;d:eefe6e6edHdIdJZ@dS )L    N)datedatetime	timedeltatimezone)DictListOptional)	APIRouterDependsFileHTTPException
UploadFilestatus)Session)get_db)
get_or_404)
InvestmentInvestmentAttachment)AttachmentOutDashboardOutInvestmentCreateInvestmentOutInvestmentUpdatePortfolioConfigOutUpcomingEventz/api/portfolio	portfolio)prefixtagsz..configzportfolio_config.json)returnc               
   C   s,   t td} t| W  5 Q R  S Q R X d S )Nr)open_CONFIG_PATHjsonload)f r&   ;/var/www/html/me.goteku.com/backend/app/routes/portfolio.py_load_config   s    r(   z/config)response_modelc                   C   s   t  S N)r(   r&   r&   r&   r'   get_portfolio_config$   s    r+               )monthly	quarterlysemi_annualannualat_maturitynone   days[      im  )r0   r1   r2   r3   )invr   c                 C   s   | j | j }t|| jd  | j }t| jd}|dkrpt|| jd  | }t|d| j	d   }|| }nd}d}d}|||||dS )zFReturn dict of runtime-calculated fields for an Investment ORM object.g      Y@r   g      ?)total_face_valuetotal_cost_idrZgross_coupon_per_periodnet_coupon_per_periodannual_net_income)
unitsface_value_per_unitintpurchase_price	kurs_beli_PERIODS_PER_YEARgetcoupon_frequencyinterest_ratetax_rate)r;   r<   r=   ZperiodsZgross_per_periodZnet_per_periodZ
annual_netr&   r&   r'   _calculated_fields<   s(    
rJ   c                 C   s"   | dkrdS t | tr|  S | S )z4Normalize a Date/DateTime ORM value to a plain date.N)
isinstancer   r   )valuer&   r&   r'   _as_dateX   s
    
rM   F)r;   include_attachmentsr   c                 C   s   t | }|rdd | jD nd }tf | j| j| j| j| j| j| j	| j
| jt| j| jt| j| j| j| j| j| j| jt| j| j| j| jt| j| j| j| j| j|d|S )Nc                 S   s   g | ]}t |qS r&   )r   model_validate).0ar&   r&   r'   
<listcomp>f   s     z&_to_investment_out.<locals>.<listcomp>)idbankplatforminvestment_numberinvestment_typeinvestment_namecurrencyrD   
owner_nameinvestment_datetenor_monthsmaturity_dater@   rA   rC   nominal_idrrH   rG   next_coupon_daterI   is_tax_inclusiver   	sold_date
sold_pricenotes
created_at
updated_atattachments)rJ   rf   r   rS   rT   rU   rV   rW   rX   rY   rD   rZ   rM   r[   r\   r]   r@   rA   rC   r^   rH   rG   r_   rI   r`   r   ra   rb   rc   rd   re   )r;   rN   calcrf   r&   r&   r'   _to_investment_outa   sJ    rh   z/investments)dbc                 C   s(   |  ttj  }dd |D S )Nc                 S   s   g | ]}t |qS r&   )rh   )rP   r;   r&   r&   r'   rR      s     z$list_investments.<locals>.<listcomp>)queryr   order_byr[   descall)ri   Zinvestmentsr&   r&   r'   list_investments   s
    
rn   )r)   status_code)bodyri   c                 C   s2   t f |  }|| |  || t|S r*   )r   
model_dumpaddcommitrefreshrh   )rp   ri   r;   r&   r&   r'   create_investment   s
    

ru   z/investments/{investment_id}investment_idri   c                 C   s   t |t| d}t|ddS )Nr   T)rN   )r   r   rh   )rw   ri   r;   r&   r&   r'   get_investment   s    rx   )rw   rp   ri   c                 C   s\   t |t| d}|jdd D ]\}}t||| qttj|_	|
  || t|S )Nr   T)exclude_none)r   r   rq   itemssetattrr   nowr   utcre   rs   rt   rh   )rw   rp   ri   r;   fieldrL   r&   r&   r'   update_investment   s    
r   )ro   c              	   C   sd   t |t| d}ddlm} t|jD ](}z||j W q$ tk
rJ   Y q$X q$|| |	  d S )Nr   r   delete_file)
r   r   app.helpers.file_storager   listrf   google_drive_file_id	Exceptiondeleters   )rw   ri   r;   r   attr&   r&   r'   delete_investment   s    
r   z
/dashboardc                 C   sR  |  ttjdk }t }|tdd }d}d}d}g }i }i }	i }
|D ]}t|}||j	7 }||d 7 }||d 7 }|
|jd|j	 ||j< |	
|jd|j	 |	|j< |

|jd|j	 |
|j< |j}|dkrV|tkrV|jd k	rVt|j}t| }||k r|| }q||krV|td|j|j|j||| j|d	 |jd
 |dkr|jd k	rt|j}||  kr|krn n0|td|j|j|j||| j|d	 |jd
 |jd k	rPt|j}||  kr|krPn qP|td|j|j|j||| j|j	|jd qP|jdd d t|||| |t||||	|
d	S )NactiveZ   r7   r   r=   r?   )r5   r4   NZcouponr>   )typerw   rX   rW   r   
days_until
net_amountrY   r4   Zmaturity)r   rw   rX   rW   r   r   r^   rY   c                 S   s   | j S r*   )r   )er&   r&   r'   <lambda>&      zget_dashboard.<locals>.<lambda>)key)	total_value_idrr=   Zunrealized_pnlr?   Zinvestment_countZupcoming_eventsallocation_by_typeallocation_by_currencyallocation_by_bank)rj   r   filterr   rm   r   todayr   rJ   r^   rF   rW   rY   rT   rG   _FREQ_DELTAr_   rM   appendr   rS   rX   r8   r]   sortr   len)ri   r   r   Zhorizonr   r=   r?   Zupcomingr   r   r   r;   rg   freqZ
event_datedeltaZmat_dater&   r&   r'   get_dashboard   s    







r   z(/investments/{investment_id}/attachmentsc                 C   s0   t |t| d |ttj| ktj S )Nr   )	r   r   rj   r   r   rw   rk   rd   rm   rv   r&   r&   r'   list_attachments7  s    
r   .)rw   fileri   c           	   
      s   t |t| d | I d H }z&ddlm} |||jp6dd\}}W n6 tk
rx } zttj	d| dW 5 d }~X Y nX t
| |||jpd|jpdt|d	}|| |  || |S )
Nr   r   )	save_file
attachment)	file_dataoriginal_filenamezFile upload failed: ro   detailzapplication/octet-stream)rw   r   Zgoogle_drive_view_urlr   content_type	file_size)r   r   readr   r   filenamer   r   r   HTTP_503_SERVICE_UNAVAILABLEr   r   r   rr   rs   rt   )	rw   r   ri   r   r   Zstored_filenameZview_urlexcr   r&   r&   r'   upload_attachmentE  s2    


r   z8/investments/{investment_id}/attachments/{attachment_id})rw   attachment_idri   c                 C   s|   t |t| d |t|}|r(|j| kr6ttjddzddlm	} ||j
 W n tk
rd   Y nX || |  d S )Nr   zAttachment not foundr   r   r   )r   r   rF   r   rw   r   r   HTTP_404_NOT_FOUNDr   r   r   r   r   rs   )rw   r   ri   r   r   r&   r&   r'   delete_attachmentn  s    	
r   )F)Ar#   osr   r   r   r   typingr   r   r   fastapir	   r
   r   r   r   r   sqlalchemy.ormr   app.core.databaser   app.helpers.crudr   Zapp.models.investmentr   r   Zapp.schemas.portfolior   r   r   r   r   r   r   routerpathjoindirname__file__r"   dictr(   rF   r+   rE   r   rJ   rM   boolrh   rn   postHTTP_201_CREATEDru   strrx   putr   r   HTTP_204_NO_CONTENTr   r   r   r   r   r&   r&   r&   r'   <module>   s    $

   


  ,	l
$