Ë
    tPêj_(  ã                   ó´   — U d dl mZmZ d dlmZmZ d dlmZ  G d„ de«      Z G d„ dee«      Z	dZ
eed	<   d
Zeed<   dedededdfd„Zde	ddfd„Zde	defd„Zy)é    )ÚMappingÚSequence)ÚFinalÚProtocol)Úverbose_loggerc                   ó$   — e Zd ZdZdededefd„Zy)ÚSupportsExecuteRawz=The one database operation create_view_tolerating_race needs.ÚqueryÚargsÚreturnc              ‡   ó   K  — y ­w©N© ©Úselfr
   r   s      úb/home/oem/CyberBrain26-unified/.venv/lib/python3.12/site-packages/litellm/proxy/db/create_views.pyÚexecute_rawzSupportsExecuteRaw.execute_raw
   ó   è ø� ùó   ‚N)Ú__name__Ú
__module__Ú__qualname__Ú__doc__ÚstrÚobjectÚintr   r   ó    r   r	   r	      s   „ ÙGàF sÐF°6ÐF¸cÔFr   r	   c            	       ó4   — e Zd ZdZdededeeeef      fd„Zy)ÚSupportsRawQuerieszSThe database operations the view bootstrap needs: probe a relation, then create it.r
   r   r   c              ‡   ó   K  — y ­wr   r   r   s      r   Ú	query_rawzSupportsRawQueries.query_raw   r   r   N)	r   r   r   r   r   r   r   r   r!   r   r   r   r   r      s&   „ Ù]à_ SÐ_°Ð_¸HÀWÈSÐRXÈ[ÑEYÑ<ZÔ_r   r   )zdoes not existzno such tablezundefined tableÚ_VIEW_NOT_FOUND_MARKERS)zalready existszduplicate objectzduplicate tableÚ_VIEW_ALREADY_EXISTS_MARKERSÚdbÚ	view_nameÚddlr   Nc              ƒ   óü   ‡K  — 	 | j                  |«      ƒ d{  –—†  t        j                  d|«       y7 Œ# t        $ r9Št	        ˆfd„t
        D «       «      s‚ t        j                  d|«       Y dŠ‹ydŠ‹ww xY w­w)aÁ  
    Create a view, treating "a concurrent creator won" as success.

    Every replica booting against the same fresh database observes the view as
    absent and issues the CREATE; Postgres fails all but one with a
    duplicate-object error. The desired end state is still reached, so losing
    that race is success. Without this, the loser's exception propagates out of
    a detached startup task and the remaining views are never created.
    Nz%s Created!c              3   óT   •K  — | ]  }|t        ‰«      j                  «       v –— Œ! y ­wr   )r   Úlower)Ú.0ÚmarkerÚes     €r   ú	<genexpr>z.create_view_tolerating_race.<locals>.<genexpr>,   s    øè ø€ ÒW°�6œS ›VŸ\™\›^Ô+ÑWùs   ƒ%(z*%s already created by a concurrent replica)r   r   ÚdebugÚ	ExceptionÚanyr#   )r$   r%   r&   r,   s      @r   Úcreate_view_tolerating_racer1      sk   øè ø€ ðVØ�n‰n˜SÓ!×!Ð!Ü×Ñ˜]¨IÕ6ð 	"ùäò VÜÓWÔ:VÔWÔWØÜ×ÑÐIÈ9×UÑUûðVüs7   ƒA<…7 ™5š7 ´A<µ7 ·	A9Á /A4Á/A<Á4A9Á9A<c              ƒ   ó8	  ‡K  — 	 | j                  d«      ƒ d{  –—†  t        j                  d«       	 | j                  d«      ƒ d{  –—†  t        j                  d«       	 | j                  d«      ƒ d{  –—†  t        j                  d«       	 | j                  d«      ƒ d{  –—†  t        j                  d«       	 | j                  d«      ƒ d{  –—†  t        j                  d«       	 | j                  d«      ƒ d{  –—†  t        j                  d«       	 | j                  d «      ƒ d{  –—†  t        j                  d!«       	 | j                  d%«      ƒ d{  –—†  t        j                  d&«       y7 �Œd# t        $ rS}t	        |«      j                  «       Št        ˆfd„t        D «       «      s‚ t        | dd«      ƒ d{  –—†7   Y d}~�Œ¤d}~ww xY w7 �Œ—# t        $ rU}t	        |«      j                  «       Št        ˆfd	„t        D «       «      s‚ d
}t        | d|«      ƒ d{  –—†7   Y d}~�ŒÙd}~ww xY w7 �ŒÌ# t        $ rU}t	        |«      j                  «       Št        ˆfd„t        D «       «      s‚ d}t        | d|«      ƒ d{  –—†7   Y d}~�Œd}~ww xY w7 �Œ# t        $ rU}t	        |«      j                  «       Št        ˆfd„t        D «       «      s‚ d}t        | d|«      ƒ d{  –—†7   Y d}~�ŒCd}~ww xY w7 �Œ6# t        $ rU}t	        |«      j                  «       Št        ˆfd„t        D «       «      s‚ d}t        | d|«      ƒ d{  –—†7   Y d}~�Œxd}~ww xY w7 �Œk# t        $ rU}t	        |«      j                  «       Št        ˆfd„t        D «       «      s‚ d}t        | d|«      ƒ d{  –—†7   Y d}~�Œ­d}~ww xY w7 �Œ # t        $ rU}t	        |«      j                  «       Št        ˆfd"„t        D «       «      s‚ d#}t        | d$|«      ƒ d{  –—†7   Y d}~�Œâd}~ww xY w7 �ŒÕ# t        $ rT}t	        |«      j                  «       Št        ˆfd'„t        D «       «      s‚ d(}t        | d)|«      ƒ d{  –—†7   Y d}~yd}~ww xY w­w)*a  
    --------------------------------------------------
    NOTE: Copy of `litellm/db_scripts/create_views.py`.
    --------------------------------------------------
    Checks if the LiteLLM_VerificationTokenView and MonthlyGlobalSpend exists in the user's db.

    LiteLLM_VerificationTokenView: This view is used for getting the token + team data in user_api_key_auth

    MonthlyGlobalSpend: This view is used for the admin view to see global spend for this month

    If the view doesn't exist, one will be created.
    z5SELECT 1 FROM "LiteLLM_VerificationTokenView" LIMIT 1Nz%LiteLLM_VerificationTokenView Exists!c              3   ó&   •K  — | ]  }|‰v –— Œ
 y ­wr   r   ©r*   r+   Ú	error_msgs     €r   r-   z'create_missing_views.<locals>.<genexpr>E   ó   øè ø€ ÒM¨6�6˜YÔ&ÑMùó   ƒÚLiteLLM_VerificationTokenViewa.  
                CREATE VIEW "LiteLLM_VerificationTokenView" AS
                SELECT
                v.*,
                t.spend AS team_spend,
                t.max_budget AS team_max_budget,
                t.tpm_limit AS team_tpm_limit,
                t.rpm_limit AS team_rpm_limit,
                p.project_alias AS project_alias
                FROM "LiteLLM_VerificationToken" v
                LEFT JOIN "LiteLLM_TeamTable" t ON v.team_id = t.team_id
                LEFT JOIN "LiteLLM_ProjectTable" p ON v.project_id = p.project_id;
            z*SELECT 1 FROM "MonthlyGlobalSpend" LIMIT 1zMonthlyGlobalSpend Exists!c              3   ó&   •K  — | ]  }|‰v –— Œ
 y ­wr   r   r4   s     €r   r-   z'create_missing_views.<locals>.<genexpr>_   r6   r7   a5  
        CREATE OR REPLACE VIEW "MonthlyGlobalSpend" AS 
        SELECT
        DATE("startTime") AS date, 
        SUM("spend") AS spend 
        FROM 
        "LiteLLM_SpendLogs" 
        WHERE 
        "startTime" >= (CURRENT_DATE - INTERVAL '30 days')
        GROUP BY 
        DATE("startTime");
        ÚMonthlyGlobalSpendz*SELECT 1 FROM "Last30dKeysBySpend" LIMIT 1zLast30dKeysBySpend Exists!c              3   ó&   •K  — | ]  }|‰v –— Œ
 y ­wr   r   r4   s     €r   r-   z'create_missing_views.<locals>.<genexpr>t   r6   r7   a   
        CREATE OR REPLACE VIEW "Last30dKeysBySpend" AS
        SELECT 
        L."api_key", 
        V."key_alias",
        V."key_name",
        SUM(L."spend") AS total_spend
        FROM
        "LiteLLM_SpendLogs" L
        LEFT JOIN 
        "LiteLLM_VerificationToken" V
        ON
        L."api_key" = V."token"
        WHERE
        L."startTime" >= (CURRENT_DATE - INTERVAL '30 days')
        GROUP BY
        L."api_key", V."key_alias", V."key_name"
        ORDER BY
        total_spend DESC;
        ÚLast30dKeysBySpendz,SELECT 1 FROM "Last30dModelsBySpend" LIMIT 1zLast30dModelsBySpend Exists!c              3   ó&   •K  — | ]  }|‰v –— Œ
 y ­wr   r   r4   s     €r   r-   z'create_missing_views.<locals>.<genexpr>‘   r6   r7   a^  
        CREATE OR REPLACE VIEW "Last30dModelsBySpend" AS
        SELECT
        "model",
        SUM("spend") AS total_spend
        FROM
        "LiteLLM_SpendLogs"
        WHERE
        "startTime" >= (CURRENT_DATE - INTERVAL '30 days')
        AND "model" != ''
        GROUP BY
        "model"
        ORDER BY
        total_spend DESC;
        ÚLast30dModelsBySpendz0SELECT 1 FROM "MonthlyGlobalSpendPerKey" LIMIT 1z MonthlyGlobalSpendPerKey Exists!c              3   ó&   •K  — | ]  }|‰v –— Œ
 y ­wr   r   r4   s     €r   r-   z'create_missing_views.<locals>.<genexpr>¨   r6   r7   a—  
            CREATE OR REPLACE VIEW "MonthlyGlobalSpendPerKey" AS 
            SELECT
            DATE("startTime") AS date, 
            SUM("spend") AS spend,
            api_key as api_key
            FROM 
            "LiteLLM_SpendLogs" 
            WHERE 
            "startTime" >= (CURRENT_DATE - INTERVAL '30 days')
            GROUP BY 
            DATE("startTime"),
            api_key;
        ÚMonthlyGlobalSpendPerKeyz7SELECT 1 FROM "MonthlyGlobalSpendPerUserPerKey" LIMIT 1z'MonthlyGlobalSpendPerUserPerKey Exists!c              3   ó&   •K  — | ]  }|‰v –— Œ
 y ­wr   r   r4   s     €r   r-   z'create_missing_views.<locals>.<genexpr>¾   r6   r7   aÐ  
            CREATE OR REPLACE VIEW "MonthlyGlobalSpendPerUserPerKey" AS 
            SELECT
            DATE("startTime") AS date, 
            SUM("spend") AS spend,
            api_key as api_key,
            "user" as "user"
            FROM 
            "LiteLLM_SpendLogs" 
            WHERE 
            "startTime" >= (CURRENT_DATE - INTERVAL '30 days')
            GROUP BY 
            DATE("startTime"),
            "user",
            api_key;
        ÚMonthlyGlobalSpendPerUserPerKeyz%SELECT 1 FROM "DailyTagSpend" LIMIT 1zDailyTagSpend Exists!c              3   ó&   •K  — | ]  }|‰v –— Œ
 y ­wr   r   r4   s     €r   r-   z'create_missing_views.<locals>.<genexpr>×   r6   r7   ar  
        CREATE OR REPLACE VIEW "DailyTagSpend" AS
        SELECT
            jsonb_array_elements_text(request_tags) AS individual_request_tag,
            DATE(s."startTime") AS spend_date,
            COUNT(*) AS log_count,
            SUM(spend) AS total_spend
        FROM "LiteLLM_SpendLogs" s
        GROUP BY individual_request_tag, DATE(s."startTime");
        ÚDailyTagSpendz/SELECT 1 FROM "Last30dTopEndUsersSpend" LIMIT 1zLast30dTopEndUsersSpend Exists!c              3   ó&   •K  — | ]  }|‰v –— Œ
 y ­wr   r   r4   s     €r   r-   z'create_missing_views.<locals>.<genexpr>ê   r6   r7   af  
        CREATE VIEW "Last30dTopEndUsersSpend" AS
        SELECT end_user, COUNT(*) AS total_events, SUM(spend) AS total_spend
        FROM "LiteLLM_SpendLogs"
        WHERE end_user <> '' AND end_user <> user
        AND "startTime" >= CURRENT_DATE - INTERVAL '30 days'
        GROUP BY end_user
        ORDER BY total_spend DESC
        LIMIT 100;
        ÚLast30dTopEndUsersSpend)	r!   r   r.   r/   r   r)   r0   r"   r1   )r$   r,   Ú	sql_queryr5   s      @r   Úcreate_missing_viewsrH   1   sí  øè ø€ ð
à�l‰lÐVÓW×WÐWÜ×ÑÐDÔEð0OØ�l‰lÐKÓL×LÐLÜ×ÑÐ9Ô:ð&OØ�l‰lÐKÓL×LÐLÜ×ÑÐ9Ô:ð6QØ�l‰lÐMÓN×NÐNÜ×ÑÐ;Ô<ð*UØ�l‰lÐQÓR×RÐRÜ×ÑÐ?Ô@ð(\Ø�l‰lÐXÓY×YÐYÜ×ÑÐFÔGð.JØ�l‰lÐFÓG×GÐGÜ×ÑÐ4Ô5ð"TØ�l‰lÐPÓQ×QÐQÜ×ÑÐ>Õ?ðM 	Xúäò 
Ü˜“F—L‘L“Nˆ	ÜÓMÔ5LÔMÔMØä)ØØ+ðó
÷ 	
÷ 	
ûð
úð0 	Múäò OÜ˜“F—L‘L“Nˆ	ÜÓMÔ5LÔMÔMØðˆ	ô *¨"Ð.BÀIÓN×N×Nûð!Oúð& 	Múäò OÜ˜“F—L‘L“Nˆ	ÜÓMÔ5LÔMÔMØðˆ	ô( *¨"Ð.BÀIÓN×N×Nûð1Oúð6 	Oúäò QÜ˜“F—L‘L“Nˆ	ÜÓMÔ5LÔMÔMØðˆ	ô *¨"Ð.DÀiÓP×P×Pûð'Qúð* 	Súäò UÜ˜“F—L‘L“Nˆ	ÜÓMÔ5LÔMÔMØðˆ	ô *¨"Ð.HÈ)ÓT×T×Tûð%Uúð( 	Zúäò \Ü˜“F—L‘L“Nˆ	ÜÓMÔ5LÔMÔMØðˆ	ô  *¨"Ð.OÐQZÓ[×[×[ûð)\úð. 	Húäò JÜ˜“F—L‘L“Nˆ	ÜÓMÔ5LÔMÔMØð	ˆ	ô *¨"¨o¸yÓI×I×IûðJúð" 	Rúäò TÜ˜“F—L‘L“Nˆ	ÜÓMÔ5LÔMÔMØð	ˆ	ô *¨"Ð.GÈÓS×SÖSûðTüs  ƒR…F  ™E=šF  ´G" ÁGÁ	G" Á#I Á7IÁ8I ÂJ* Â&J'Â'J* ÃL ÃLÃL Ã0M2 ÄM/ÄM2 ÄO Ä3OÄ4O ÅP: Å"P7Å#P: Å<RÅ=F  Æ 	GÆ	AGÇGÇGÇRÇGÇRÇG" Ç"	I Ç+AH;È/H2È0H;È5RÈ;I É RÉI É	J$ÉAJÊJÊJÊRÊJ$Ê$RÊ'J* Ê*	LÊ3ALË7K:Ë8LË=RÌLÌRÌL Ì	M,ÌAM'ÍMÍM'Í!RÍ'M,Í,RÍ/M2 Í2	OÍ;AOÎ?OÏ OÏRÏOÏRÏO Ï	P4ÏAP/Ð#P&Ð$P/Ð)RÐ/P4Ð4RÐ7P: Ð:	RÑARÒR
ÒRÒRÒRÒRc              ƒ   óP  K  — d}| j                  |¬«      ƒ d{  –—† }t        j                  d|«       |rlt        |t        «      r\t        |«      dkD  rNt        |d   t        «      r;d|d   v r4|d   d   �,|d   d   dk(  s|d   d   dk(  rt        j                  d«       y	y
7 Œ‰­w)zy
    Run only on first time startup.

    If SpendLogs table already has values, then don't create views on startup.
    ze
    SELECT reltuples::BIGINT
    FROM pg_class
    WHERE oid = '"LiteLLM_SpendLogs"'::regclass;
    )r
   Nz-Estimated Row count of LiteLLM_SpendLogs = %sr   Ú	reltupleséÿÿÿÿzShould create viewsTF)r!   r   r.   Ú
isinstanceÚlistÚlenÚdict)r$   rG   Úresults      r   Úshould_create_missing_viewsrQ   ù   s¯   è ø€ ð€Ið Ÿ,™,¨Y˜,Ó7×7€Fä×ÑÐHÈ&ÔQáÜ�vœtÔ$Ü�‹K˜!ŠOÜ�v˜a‘y¤$Ô'Ø˜6 !™9Ñ$Ø�1‰I�kÑ"Ð.Ø�A‰Y�{Ñ# qÒ(¨F°1©I°kÑ,BÀbÒ,Hä×ÑÐ2Ô3Øàð 8ús   ‚B&šB$›B
B&)Úcollections.abcr   r   Útypingr   r   Úlitellmr   r	   r   r"   Ú__annotations__r#   r   r1   rH   ÚboolrQ   r   r   r   ú<module>rW      s¤   ðß -Ð -ß "å "ôG˜ô Gô`Ð+¨Xô `ð "XÐ ˜Ó Wð '`Ð ˜eÓ _ðVÐ*<ð VÈð VÐSVð VÐ[_ó Vð&ETÐ#5ð ET¸$ó ETðPÐ*<ð Àô r   