o
    5)i<                     @   sb   d Z ddlmZmZmZmZmZ ddlZddl	m	Z	m
Z
 ddlmZ ddlmZ G dd dZdS )	zS
OMS Data Service
Service for extracting time series data from OMS database tables
    )ListDictAnyOptionalTupleN)datetime	timedelta)DatabaseService)
get_loggerc                   @   sf  e Zd ZdZdd Z				d%dedee dee d	eeeef  d
ee de	eeef  fddZ
deeef dee dee d
edef
ddZde	e fddZdedeeeef  fddZ				d&dedededededee	e  dee d	eeeef  fddZdedeeef fdd Z	!		d'ded"edee dee de	eeef  f
d#d$ZdS )(OMSDataServicez9Service for extracting time series data from OMS databasec                 C   s   t  | _td| _dddddgi ddddd	dgi dd
dddddgi dddddddgi ddddddgi dddddddgi ddddddgi dd| _d S )Noms_data_serviceorders
order_dateorder_totalSUMzdeleted_at IS NULLtabledate_columnvalue_column
value_funcextra_conditionsfiltersidCOUNTtransaction_sales	bill_datez
status = 1zdeleted_by IS NULL
collectioncredited_dateamountzstatus = 17zcredited_date IS NOT NULLtransaction_cnzstatus IN (12, 13, 14)product_stock
created_atchange_stockzstock_type = 2zentity_type = 2purchase_orderquantityzstatus != 9)r   order_countrevenuecollectionscredit_notesstock_outwardpurchase_orders)r	   
db_servicer
   loggertable_configsself r0   ;/var/www/html/oms-prod-mcp/app/services/oms_data_service.py__init__   sh   
zOMSDataService.__init__Ndaily	table_key
start_dateend_dater   aggregationreturnc           
   
   C   s   zd|| j vrtd| dt| j   | j |  }i |di |p&i |d< | ||||}| jd| d|  | j	
|}|sS| jd| d g W S | jdt| d	| d
 |W S  ty }	 z| jd| dt|	   d}	~	ww )a  
        Extract time series data from an OMS table.

        Args:
            table_key:   Key in table_configs (e.g. 'revenue', 'collections')
            start_date:  Inclusive lower bound on the date column (YYYY-MM-DD)
            end_date:    Inclusive upper bound on the date column (YYYY-MM-DD)
            filters:     Additional col=value conditions merged at request time.
                         Pass {"company_id": <id>} for per-company scoping.
                         Omit or pass {} for all-companies (collective) data.
            aggregation: 'daily' | 'weekly' | 'monthly'

        Returns:
            List of {"ds": <date_str>, "y": <float>} dicts ready for Prophet.
        Unknown table configuration: 'z'. Available: r   zExecuting query for '': zNo data found for 'z' with the given filtersz
Retrieved z records for ''z'Error extracting time series data for 'N)r-   
ValueErrorlistkeyscopyget_build_queryr,   infor+   execute_mysql_querywarninglen	Exceptionerrorstr)
r/   r4   r5   r6   r   r7   configqueryresultser0   r0   r1   get_time_series_data   s(   

z#OMSDataService.get_time_series_datarI   c              	   C   s  |d }|d }|d }| dd}|dkr)d| d| d	| d
}	d| d}
n>|dkrCd| d| d| d	| d
	}	d| d}
n$|dkr]d| d| d	| d
}	d| d| d}
n
| d| d}	d}
d|	 d| }g }| dg D ]}|| qw|r|| d| d |r|| d | d | d!i  D ]:\}}t|trd"d#d$ |D }|| d%| d qt|tr|| d&| d q|| d'|  q|r|d(d)| 7 }|
r|d*|
 7 }|d+7 }|S ),ul  
        Build a parameterised aggregation query for Prophet input.

        Aggregation levels:
            daily   → DATE(date_col)                        GROUP BY DATE(date_col)
            weekly  → Monday of ISO week                    GROUP BY YEARWEEK(date_col)
            monthly → first day of month                    GROUP BY YEAR, MONTH
        r   r   r   r   r   r3   zDATE(z	) AS ds, (z) AS yzGROUP BY DATE()weeklyzDATE(DATE_SUB(z, INTERVAL WEEKDAY(z) DAY)) AS ds, zGROUP BY YEARWEEK(z, 1)monthlyzDATE_FORMAT(z, '%Y-%m-01') AS ds, zGROUP BY YEAR(z	), MONTH( AS ds, z AS y SELECT z FROM r    >= 'r;    <= 'r   z, c                 s   s.    | ]}t |trd | d nt|V  qdS )r;   N)
isinstancerH   ).0vr0   r0   r1   	<genexpr>   s   , z.OMSDataService._build_query.<locals>.<genexpr>z IN (z = 'z =  WHERE  AND  z ORDER BY ds)r@   appenditemsrW   r=   joinrH   )r/   rI   r5   r6   r7   r   date_col	value_colr   select_clausegroup_clauserJ   where_conditionscondkeyvaluevalsr0   r0   r1   rA      s\   

zOMSDataService._build_queryc                 C   s   t | j S )z)Return the list of configured table keys.)r=   r-   r>   r.   r0   r0   r1   get_available_tables   s   z#OMSDataService.get_available_tablesc                 C   s   || j v r| j |  S dS )z2Return a copy of the config for a given table key.N)r-   r?   )r/   r4   r0   r0   r1   get_table_info  s   
zOMSDataService.get_table_infor   rg   r   r   r   r   r   group_byc	           	      C   s<   |||||pg |p
i d| j |< | jd| d|  dS )a9  
        Register a custom table configuration at runtime.

        Args:
            key:               Lookup key used in API calls
            table:             Physical table name
            date_column:       Column used as the time axis
            value_column:      Column to aggregate
            value_func:        'SUM' or 'COUNT'
            extra_conditions:  List of raw SQL predicates always added to WHERE
            group_by:          Unused legacy parameter (kept for compatibility)
            filters:           Default col=value filters
        r   z!Registered table configuration: 'u   ' → N)r-   r,   rB   )	r/   rg   r   r   r   r   r   rl   r   r0   r0   r1   add_table_config  s   zOMSDataService.add_table_configc              
   C   s   z7|| j vrt| j  }dd| d| fW S | j | }| jd|d  }|s5dd|d  dfW S W dS  tyR } zdd	t| fW  Y d
}~S d
}~ww )z
        Validate that a table key exists and its underlying table is reachable.

        Returns:
            (True, "") on success, (False, reason) on failure.
        FzTable configuration 'z' not found. Available: zSELECT COUNT(*) AS cnt FROM r   zTable 'z&' does not exist or returned no result)TrS   zValidation error: N)r-   r=   r>   r+   rC   rF   rH   )r/   r4   	availablerI   resultrL   r0   r0   r1   validate_table_config)  s"   



z$OMSDataService.validate_table_config
   limitc           
   
   C   s  zk|| j vrtd| d| j | }t|dg }|r*||d  d| d |r9||d  d| d d|d  d|d	  d
|d  }|rU|dd| 7 }|d|d  d| 7 }| j|}|pjg W S  ty }	 z| j	
d| dt|	   d}	~	ww )uL  
        Return a raw (non-aggregated) preview of the most recent rows for a table key.
        extra_conditions from the config are applied so the preview reflects the same
        filtered dataset that would be used for training.

        Args:
            table_key:   Configured table key
            limit:       Number of rows to return (1–100)
            start_date:  Optional lower bound on the date column
            end_date:    Optional upper bound on the date column

        Returns:
            List of {"ds": <value>, "y": <value>} dicts (raw, not aggregated).
        r9   r;   r   r   rU   rV   rT   rR   r   z AS y FROM r   r[   r\   z
 ORDER BY z DESC LIMIT z Error getting data preview for 'r:   N)r-   r<   r=   r@   r^   r`   r+   rC   rF   r,   rG   rH   )
r/   r4   rr   r5   r6   rI   re   rJ   rK   rL   r0   r0   r1   get_data_previewC  s.   


zOMSDataService.get_data_preview)NNNr3   )r   NNN)rq   NN)__name__
__module____qualname____doc__r2   rH   r   r   r   r   rM   rA   rj   rk   rm   r   boolrp   intrs   r0   r0   r0   r1   r      s    v
1

I
	
"r   )rw   typingr   r   r   r   r   pandaspdr   r   app.services.database_servicer	   app.utils.helpersr
   r   r0   r0   r0   r1   <module>   s    