
    j"                        U d Z ddlmZ ddlmZ ddlmZmZmZmZm	Z	m
Z
mZmZmZ ddlmZ ddlmZmZ ddlmZ ddlmZ erdd	lmZ dd
lmZ ddlmZmZmZm Z  ddl!m"Z"m#Z#m$Z$m%Z%m&Z& ddl'm(Z(m)Z) ddl*m+Z+ ddl,m-Z- i Z.ee/e
d         f         e0d<    G d d          Z1 G d de1          Z2 G d de1          Z3 G d de1          Z4 G d de1          Z5 G d de1          Z6 G d de1          Z7 G d d e1          Z8 G d! d"e1          Z9 G d# d$e1          Z: G d% d&e1          Z;e.<                    e2e3e5e6e7e8e:e9e;d'	           d(S ))a{  OTEL span wrapper for Langfuse.

This module defines custom span classes that extend OpenTelemetry spans with
Langfuse-specific functionality. These wrapper classes provide methods for
creating, updating, and scoring various types of spans used in AI application tracing.

Classes:
- LangfuseObservationWrapper: Abstract base class for all Langfuse spans
- LangfuseSpan: Implementation for general-purpose spans
- LangfuseGeneration: Specialized span implementation for LLM generations

All span classes provide methods for media processing, attribute management,
and scoring integration specific to Langfuse's observability platform.
    )datetime)time_ns)	TYPE_CHECKINGAnyDictLiteralOptionalTypeUnioncastoverload)trace)Status
StatusCode)_AgnosticContextManager)PromptClient)Langfuse)
deprecated)LangfuseOtelSpanAttributescreate_generation_attributescreate_span_attributescreate_trace_attributes)ObservationTypeGenerationLikeObservationTypeLiteralObservationTypeLiteralNoEventObservationTypeSpanLikeget_observation_types_list)MapValueScoreDataType)langfuse_logger)	SpanLevelLangfuseObservationWrapper_OBSERVATION_CLASS_MAPc            $       V   e Zd ZdZddddddddddddddddej        dddedee         d	ee         d
ee         dee	         dee	         dee	         dee
         dee	         dee         dee	         deee	ef                  deee	ef                  deee	ef                  dee         f"dZdddee         dd fdZ ed          ddddee         d	ee         dd fd            ZdidZedddddddd e	d!ed"ee	         d#eeej        ej        f                  d$ee	         d%ee	         d&ee         d
ee         ddfd'            Zedej        dddddd e	d!e	d"ee	         d#eeej        ej        f                  d$ee	         d%ee	         d&ee         d
ee         ddfd(            Zdddddddd e	d!eee	f         d"ee	         d#ee         d$ee	         d%ee	         d&ee         d
ee         ddfd)Zedddddddd e	d!ed"ee	         d#eeej        ej        f                  d$ee	         d%ee	         d&ee         d
ee         ddfd*            Zedej        dddddd e	d!e	d"ee	         d#eeej        ej        f                  d$ee	         d%ee	         d&ee         d
ee         ddfd+            Zdddddddd e	d!eee	f         d"ee	         d#ee         d$ee	         d%ee	         d&ee         d
ee         ddfd,Zddddd-d.ej        dee         dee         d	ee         d
ee         ddfd/Z dd0d1ee         d.ej        d2eed         ed	         ed
         f         dee         fd3Z!d1edefd4Z"dd0d1ee         d2eed         ed	         ed
         f         dee         fd5Z#ddd6dee
         dee	         ddfd7Z$dddddddddddddd8d ee	         dee         d	ee         d
ee         dee	         dee
         dee	         dee         dee	         deee	ef                  deee	ef                  deee	ef                  dee         d9edd fd:Z%eddddddd;d e	ded.         dee         d	ee         d
ee         dee	         dee
         dee	         dd<fd=            Z&eddddddddddddd>d e	ded?         dee         d	ee         d
ee         dee	         dee
         dee	         dee         dee	         deee	ef                  deee	ef                  deee	ef                  dee         dd@fdA            Z&eddddddd;d e	dedB         dee         d	ee         d
ee         dee	         dee
         dee	         ddCfdD            Z&eddddddd;d e	dedE         dee         d	ee         d
ee         dee	         dee
         dee	         ddFfdG            Z&eddddddd;d e	dedH         dee         d	ee         d
ee         dee	         dee
         dee	         ddIfdJ            Z&eddddddd;d e	dedK         dee         d	ee         d
ee         dee	         dee
         dee	         ddLfdM            Z&eddddddd;d e	dedN         dee         d	ee         d
ee         dee	         dee
         dee	         ddOfdP            Z&eddddddddddddd>d e	dedQ         dee         d	ee         d
ee         dee	         dee
         dee	         dee         dee	         deee	ef                  deee	ef                  deee	ef                  dee         ddRfdS            Z&eddddddd;d e	dedT         dee         d	ee         d
ee         dee	         dee
         dee	         ddUfdV            Z&eddddddd;d e	dedW         dee         d	ee         d
ee         dee	         dee
         dee	         ddXfdY            Z&d.dddddddddddddZd e	dedee         d	ee         d
ee         dee	         dee
         dee	         dee         dee	         deee	ef                  deee	ef                  deee	ef                  dee         ded[         fd\Z&eddddddd;d e	ded.         dee         d	ee         d
ee         dee	         dee
         dee	         de'd<         fd]            Z(eddddddddddddd>d e	ded?         dee         d	ee         d
ee         dee	         dee
         dee	         dee         dee	         deee	ef                  deee	ef                  deee	ef                  dee         de'd@         fd^            Z(eddddddddddddd>d e	dedQ         dee         d	ee         d
ee         dee	         dee
         dee	         dee         dee	         deee	ef                  deee	ef                  deee	ef                  dee         de'dR         fd_            Z(eddddddd;d e	dedB         dee         d	ee         d
ee         dee	         dee
         dee	         de'dC         fd`            Z(eddddddd;d e	dedE         dee         d	ee         d
ee         dee	         dee
         dee	         de'dF         fda            Z(eddddddd;d e	dedH         dee         d	ee         d
ee         dee	         dee
         dee	         de'dI         fdb            Z(eddddddd;d e	dedK         dee         d	ee         d
ee         dee	         dee
         dee	         de'dL         fdc            Z(eddddddd;d e	dedN         dee         d	ee         d
ee         dee	         dee
         dee	         de'dO         fdd            Z(eddddddd;d e	dedT         dee         d	ee         d
ee         dee	         dee
         dee	         de'dU         fde            Z(d.dddddddddddddZd e	de)dee         d	ee         d
ee         dee	         dee
         dee	         dee         dee	         deee	ef                  deee	ef                  deee	ef                  dee         de'edf                  fdgZ(ddddddd;d e	dee         d	ee         d
ee         dee	         dee
         dee	         ddXfdhZ*dS )jr"   a  Abstract base class for all Langfuse span types.

    This class provides common functionality for all Langfuse span types, including
    media processing, attribute management, and scoring. It wraps an OpenTelemetry
    span and extends it with Langfuse-specific features.

    Attributes:
        _otel_span: The underlying OpenTelemetry span
        _langfuse_client: Reference to the parent Langfuse client
        trace_id: The trace ID for this span
        observation_id: The observation ID (span ID) for this span
    Ninputoutputmetadataenvironmentreleaseversionlevelstatus_messagecompletion_start_timemodelmodel_parametersusage_detailscost_detailsprompt	otel_spanlangfuse_clientr   as_typer&   r'   r(   r)   r*   r+   r,   r-   r.   r/   r0   r1   r2   r3   c                *   || _         | j                             t          j        |           || _        || _        | j                            |          | _        | j                            |          | _	        |p| j        j
        | _
        | j
        *| j                             t          j        | j
                   |p| j        j        | _        | j        *| j                             t          j        | j                   | j                                         rx|                     |d| j                   }|                     |d| j                   }|                     |d| j                   }i }|t!          t"                    v r0t%          ||||	|
|||||||t'          t"          |                    }njt)          ||||	|
|t'          t*          t,          t.          t0          d         f                  |t!          t.                    v s|dk    r|nd                    }|                    t          j        d           | j                             d	 |                                D                        |                     |
|
           dS dS )a  Initialize a new Langfuse span wrapper.

        Args:
            otel_span: The OpenTelemetry span to wrap
            langfuse_client: Reference to the parent Langfuse client
            as_type: The type of span ("span" or "generation")
            input: Input data for the span (any JSON-serializable object)
            output: Output data from the span (any JSON-serializable object)
            metadata: Additional metadata to associate with the span
            environment: The tracing environment
            release: Release identifier for the application
            version: Version identifier for the code or component
            level: Importance level of the span (info, warning, error)
            status_message: Optional status message for the span
            completion_start_time: When the model started generating the response
            model: Name/identifier of the AI model used (e.g., "gpt-4")
            model_parameters: Parameters used for the model (e.g., temperature, max_tokens)
            usage_details: Token usage information (e.g., prompt_tokens, completion_tokens)
            cost_details: Cost information for the model call
            prompt: Associated prompt template from Langfuse prompt management
        Nr&   datafieldspanr'   r(   )r&   r'   r(   r+   r,   r-   r.   r/   r0   r1   r2   r3   observation_typeeventr&   r'   r(   r+   r,   r-   r<   c                     i | ]
\  }}|||S N ).0kvs      e/lsinfo/ai/hellotax_ai/data_center/backend/venv/lib/python3.11/site-packages/langfuse/_client/span.py
<dictcomp>z7LangfuseObservationWrapper.__init__.<locals>.<dictcomp>   s    FFF$!QA    r,   r-   )
_otel_spanset_attributer   OBSERVATION_TYPE_langfuse_client_observation_type_get_otel_trace_idtrace_id_get_otel_span_idid_environmentENVIRONMENT_releaseRELEASEis_recording_process_media_and_apply_maskr   r   r   r   r   r	   r   r   r   popset_attributesitems_set_otel_span_status_if_error)selfr4   r5   r6   r&   r'   r(   r)   r*   r+   r,   r-   r.   r/   r0   r1   r2   r3   media_processed_inputmedia_processed_outputmedia_processed_metadata
attributess                         rE   __init__z#LangfuseObservationWrapper.__init__N   s   T $%%&7	
 	
 	
 !0!(-@@KK'99)DD'M4+@+M(O))*68I    A4#8#A=$O))*2DM  
 ?'')) =	$($F$F' %G % %! &*%G%G8$/ &H & &" (,'I'IZdo (J ( ($ J45RSSSS9/15##1*?%5"/!-!%)5& &  

* 4/15##1%) '>@P'P!QR"56MNNO O"g--   "& &  
$ NN5FMMMO**FF*"2"2"4"4FFF   //N 0     w=	 =	rG   end_timerc   returnc                <    | j                             |           | S )a_  End the span, marking it as completed.

        This method ends the wrapped OpenTelemetry span, marking the end of the
        operation being traced. After this method is called, the span is considered
        complete and can no longer be modified.

        Args:
            end_time: Optional explicit end time in nanoseconds since epoch
        rb   )rI   end)r\   rc   s     rE   rf   zLangfuseObservationWrapper.end   s"     	X...rG   zTrace-level input/output is deprecated. For trace attributes (user_id, session_id, tags, etc.), use propagate_attributes() instead. This method will be removed in a future major version.r&   r'   c                   | j                                         s| S |                     |d| j                   }|                     |d| j                   }t          ||          }| j                             |           | S )a  Set trace-level input and output for the trace this span belongs to.

        .. deprecated::
            This is a legacy method for backward compatibility with Langfuse platform
            features that still rely on trace-level input/output (e.g., legacy LLM-as-a-judge
            evaluators). It will be removed in a future major version.

            For setting other trace attributes (user_id, session_id, metadata, tags, version),
            use :meth:`Langfuse.propagate_attributes` instead.

        Args:
            input: Input data to associate with the trace.
            output: Output data to associate with the trace.

        Returns:
            The span instance for method chaining.
        r&   r8   r'   rg   )rI   rV   rW   r   rY   )r\   r&   r'   r]   r^   r`   s         rE   set_trace_ioz'LangfuseObservationWrapper.set_trace_io   s    8 ++-- 	K $ B BgDO !C !
 !
 "&!C!Cxdo "D "
 "
 -')
 
 


 	&&z222rG   c                     | j                                         s| S t          d          }| j                             |           | S )a  Make this trace publicly accessible via its URL.

        When a trace is published, anyone with the trace link can view the full trace
        without needing to be logged in to Langfuse. This action cannot be undone
        programmatically - once any span in a trace is published, the entire trace
        becomes public.

        Returns:
            The span instance for method chaining.
        T)public)rI   rV   r   rY   )r\   r`   s     rE   set_trace_as_publicz.LangfuseObservationWrapper.set_trace_as_public  sJ     ++-- 	K,D999
&&z222rG   )score_id	data_typecomment	config_id	timestampr(   namevaluerm   rn   ro   rp   rq   c                    d S r@   rA   	r\   rr   rs   rm   rn   ro   rp   rq   r(   s	            rE   scorez LangfuseObservationWrapper.score  	     srG   c                    d S r@   rA   ru   s	            rE   rv   z LangfuseObservationWrapper.score/  rw   rG   c                    | j                             |t          t          |          | j        | j        |t          t          d         |          ||||
  
         dS )a  Create a score for this specific span.

        This method creates a score associated with this specific span (observation).
        Scores can represent any kind of evaluation, feedback, or quality metric.

        Args:
            name: Name of the score (e.g., "relevance", "accuracy")
            value: Score value (numeric for NUMERIC/BOOLEAN, string for CATEGORICAL/TEXT)
            score_id: Optional custom ID for the score (auto-generated if not provided)
            data_type: Type of score (NUMERIC, BOOLEAN, CATEGORICAL, or TEXT)
            comment: Optional comment or explanation for the score
            config_id: Optional ID of a score config defined in Langfuse
            timestamp: Optional timestamp for the score (defaults to current UTC time)
            metadata: Optional metadata to be attached to the score

        Example:
            ```python
            with langfuse.start_as_current_observation(name="process-query") as span:
                # Do work
                result = process_data()

                # Score the span
                span.score(
                    name="accuracy",
                    value=0.95,
                    data_type="NUMERIC",
                    comment="High accuracy result"
                )
            ```
        CATEGORICALTEXT)
rr   rs   rO   observation_idrm   rn   ro   rp   rq   r(   N)rL   create_scorer   strrO   rQ   r   ru   s	            rE   rv   z LangfuseObservationWrapper.score?  sk    T 	**sE""]77#899EE 	+ 	
 	
 	
 	
 	
rG   c                    d S r@   rA   ru   s	            rE   score_tracez&LangfuseObservationWrapper.score_tracev  rw   rG   c                    d S r@   rA   ru   s	            rE   r   z&LangfuseObservationWrapper.score_trace  rw   rG   c                    | j                             |t          t          |          | j        |t          t
          d         |          ||||	  	         dS )a  Create a score for the entire trace that this span belongs to.

        This method creates a score associated with the entire trace that this span
        belongs to, rather than the specific span. This is useful for overall
        evaluations that apply to the complete trace.

        Args:
            name: Name of the score (e.g., "user_satisfaction", "overall_quality")
            value: Score value (numeric for NUMERIC/BOOLEAN, string for CATEGORICAL/TEXT)
            score_id: Optional custom ID for the score (auto-generated if not provided)
            data_type: Type of score (NUMERIC, BOOLEAN, CATEGORICAL, or TEXT)
            comment: Optional comment or explanation for the score
            config_id: Optional ID of a score config defined in Langfuse
            timestamp: Optional timestamp for the score (defaults to current UTC time)
            metadata: Optional metadata to be attached to the score

        Example:
            ```python
            with langfuse.start_as_current_observation(name="handle-request") as span:
                # Process the complete request
                result = process_request()

                # Score the entire trace (not just this span)
                span.score_trace(
                    name="overall_quality",
                    value=0.9,
                    data_type="NUMERIC",
                    comment="Good overall experience"
                )
            ```
        rz   )	rr   rs   rO   rm   rn   ro   rp   rq   r(   N)rL   r~   r   r   rO   r   ru   s	            rE   r   z&LangfuseObservationWrapper.score_trace  sf    V 	**sE""]7#899EE 	+ 
	
 
	
 
	
 
	
 
	
rG   )r6   r&   r'   r(   r;   c                   |                      ||d          }|                      ||d          }|                      ||d          }|dk    rt          |||          nt          |||          }	|                    |	           dS )a  Set span attributes after processing media and applying masks.

        Internal method that processes media in the input, output, and metadata
        and applies any configured masking before setting them as span attributes.

        Args:
            span: The OpenTelemetry span to set attributes on
            as_type: The type of span ("span" or "generation")
            input: Input data to process and set
            output: Output data to process and set
            metadata: Metadata to process and set
        r&   )r;   r9   r:   r'   r(   
generation)r&   r'   r(   N)rW   r   r   rY   )
r\   r;   r6   r&   r'   r(   processed_inputprocessed_outputprocessed_metadatamedia_processed_attributess
             rE   _set_processed_span_attributesz9LangfuseObservationWrapper._set_processed_span_attributes  s    * << = 
 

  == > 
 

 "?? @ 
 
 ,&& )%'+    (%'+   	# 	677777rG   r9   r9   r:   c                X    |                      |                     ||                    S )a  Process media in an attribute and apply masking.

        Internal method that processes any media content in the data and applies
        the configured masking function to the result.

        Args:
            data: The data to process
            span: The OpenTelemetry span context
            field: Which field this data represents (input, output, or metadata)

        Returns:
            The processed and masked data
        )r9   r:   r   )_mask_attribute_process_media_in_attribute)r\   r9   r;   r:   s       rE   rW   z8LangfuseObservationWrapper._process_media_and_apply_mask  s7    ( ##11t51II $ 
 
 	
rG   c                    | j         j        s|S 	 | j                             |          S # t          $ r"}t          j        d|            Y d}~dS d}~ww xY w)aR  Apply the configured mask function to data.

        Internal method that applies the client's configured masking function to
        the provided data, with error handling and fallback.

        Args:
            data: The data to mask

        Returns:
            The masked data, or the original data if no mask is configured
        r   ziMasking error: Custom mask function threw exception when processing data. Using fallback masking. Error: Nz*<fully masked due to failed mask function>)rL   _mask	Exceptionr    error)r\   r9   es      rE   r   z*LangfuseObservationWrapper._mask_attribute  s     $* 	K	@(..D.999 	@ 	@ 	@!|}   @?????	@s   + 
AAAc                    | j         j        2| j         j        j                            ||| j        | j                  S |S )a  Process any media content in the attribute data.

        Internal method that identifies and processes any media content in the
        provided data, using the client's media manager.

        Args:
            data: The data to process for media content
            span: The OpenTelemetry span context
            field: Which field this data represents (input, output, or metadata)

        Returns:
            The data with any media content processed
        N)r9   r:   rO   r}   )rL   
_resources_media_manager_find_and_process_mediarO   rQ   )r\   r9   r:   s      rE   r   z6LangfuseObservationWrapper._process_media_in_attribute2  sN    &  +7%0?WW!]#'7	 X   rG   rH   c                    |dk    r`| j                                         rI	 | j                             t          t          j        |                     dS # t          $ r Y dS w xY wdS dS )a  Set OpenTelemetry span status to ERROR if level is ERROR.

        This method sets the underlying OpenTelemetry span status to ERROR when the
        Langfuse observation level is set to ERROR, ensuring consistency between
        Langfuse and OpenTelemetry error states.

        Args:
            level: The span level to check
            status_message: Optional status message to include as description
        ERROR)descriptionN)rI   rV   
set_statusr   r   r   r   )r\   r,   r-   s      rE   r[   z9LangfuseObservationWrapper._set_otel_span_status_if_errorQ  s     G < < > >**:+HHH         s   3A 
A$#A$rr   r&   r'   r(   r+   r,   r-   r.   r/   r0   r1   r2   r3   kwargsc                   | j                                         s| S |                     |d| j                   }|                     |d| j                   }|                     |d| j                   }|r| j                             |           | j        t          t                    v r5t          ||||||t          t          | j                  ||	|
|||          }nyt          ||||||t          t          t          t          t          d         f                  | j        t          t                    v s| j        dk    r| j        nd                    }| j                             |	           |                     ||
           | S )a  Update this observation with new information.

        This method updates the observation with new information that becomes available
        during execution, such as outputs, metadata, or status changes.

        Args:
            name: Observation name
            input: Updated input data for the operation
            output: Output data from the operation
            metadata: Additional metadata to associate with the observation
            version: Version identifier for the code or component
            level: Importance level of the observation (info, warning, error)
            status_message: Optional status message for the observation
            completion_start_time: When the generation started (for generation types)
            model: Model identifier used (for generation types)
            model_parameters: Parameters passed to the model (for generation types)
            usage_details: Token or other usage statistics (for generation types)
            cost_details: Cost breakdown for the operation (for generation types)
            prompt: Reference to the prompt used (for generation types)
            **kwargs: Additional keyword arguments (ignored)
        r&   r8   r'   r(   )r&   r'   r(   r+   r,   r-   r<   r.   r/   r0   r1   r2   r3   r=   Nr>   )r`   rH   )rI   rV   rW   update_namerM   r   r   r   r   r   r	   r   r   r   rY   r[   )r\   rr   r&   r'   r(   r+   r,   r-   r.   r/   r0   r1   r2   r3   r   r   r   r   r`   s                      rE   updatez!LangfuseObservationWrapper.updateg  s   N ++-- 	K<<gDO = 
 
  ==xdo > 
 
 "??$/ @ 
 
  	.O''---!%?)&
 &
 
 
 6%'+-!%1*" " '<!1+)!  JJ( 0%'+-!%U#:GG<L#LMN-12IJJK K-88 ** " "  J" 	&&*&===++%+WWWrG   )r&   r'   r(   r+   r,   r-   LangfuseSpanc                    d S r@   rA   	r\   rr   r6   r&   r'   r(   r+   r,   r-   s	            rE   start_observationz,LangfuseObservationWrapper.start_observation  	     rG   )r&   r'   r(   r+   r,   r-   r.   r/   r0   r1   r2   r3   r   LangfuseGenerationc                    d S r@   rA   r\   rr   r6   r&   r'   r(   r+   r,   r-   r.   r/   r0   r1   r2   r3   s                  rE   r   z,LangfuseObservationWrapper.start_observation  s	    $  #srG   agentLangfuseAgentc                    d S r@   rA   r   s	            rE   r   z,LangfuseObservationWrapper.start_observation  	     #rG   toolLangfuseToolc                    d S r@   rA   r   s	            rE   r   z,LangfuseObservationWrapper.start_observation  r   rG   chainLangfuseChainc                    d S r@   rA   r   s	            rE   r   z,LangfuseObservationWrapper.start_observation
  r   rG   	retrieverLangfuseRetrieverc                    d S r@   rA   r   s	            rE   r   z,LangfuseObservationWrapper.start_observation  	     "crG   	evaluatorLangfuseEvaluatorc                    d S r@   rA   r   s	            rE   r   z,LangfuseObservationWrapper.start_observation&  r   rG   	embeddingLangfuseEmbeddingc                    d S r@   rA   r   s                  rE   r   z,LangfuseObservationWrapper.start_observation4  s	    $ "crG   	guardrailLangfuseGuardrailc                    d S r@   rA   r   s	            rE   r   z,LangfuseObservationWrapper.start_observationH  r   rG   r=   LangfuseEventc                    d S r@   rA   r   s	            rE   r   z,LangfuseObservationWrapper.start_observationV  r   rG   )r6   r&   r'   r(   r+   r,   r-   r.   r/   r0   r1   r2   r3   )
r   r   r   r   r   r   r   r   r   r   c                   |dk    r~t                      }| j        j                            ||          }t	          t
          t          || j        |||| j        | j        |||
  
                            |                    S t          
                    |          }|st          j        d| d           t          }t          j        | j                  5  | j        j                            |          }ddd           n# 1 swxY w Y   || j        | j        | j        ||||||d	
}|t#          t$                    v r|                    |	|
||||d
            |di |S )aE  Create a new child observation of the specified type.

        This is the generic method for creating any type of child observation.
        Unlike start_as_current_observation(), this method does not set the new
        observation as the current observation in the context.

        Args:
            name: Name of the observation
            as_type: Type of observation to create
            input: Input data for the operation
            output: Output data from the operation
            metadata: Additional metadata to associate with the observation
            version: Version identifier for the code or component
            level: Importance level of the observation (info, warning, error)
            status_message: Optional status message for the observation
            completion_start_time: When the model started generating (for generation types)
            model: Name/identifier of the AI model used (for generation types)
            model_parameters: Parameters used for the model (for generation types)
            usage_details: Token usage information (for generation types)
            cost_details: Cost information (for generation types)
            prompt: Associated prompt template (for generation types)

        Returns:
            A new observation of the specified type that must be ended with .end()
        r=   rr   
start_time
r4   r5   r&   r'   r(   r)   r*   r+   r,   r-   rb   zUnknown observation type: z, falling back to LangfuseSpan)rr   N)
r4   r5   r)   r*   r&   r'   r(   r+   r,   r-   )r.   r/   r0   r1   r2   r3   rA   )r   rL   _otel_tracer
start_spanr   r   rR   rT   rf   r#   getr    warningr   otel_trace_apiuse_spanrI   r   r   r   )r\   rr   r6   r&   r'   r(   r+   r,   r-   r.   r/   r0   r1   r2   r3   rq   
event_spanobservation_classnew_otel_spancommon_argss                       rE   r   z,LangfuseObservationWrapper.start_observationd  s   l g		I.;FFi G  J ($($9!% $ 1 M##1   #y#))    366w??  	-#TWTTT   !-$T_55 	U 	U 1>IItITTM	U 	U 	U 	U 	U 	U 	U 	U 	U 	U 	U 	U 	U 	U 	U '#4,} ,
 
 01NOOOO-B"(8%2$0$ 	 	 	 ! //;///s   !DD
D
c                    d S r@   rA   r   s	            rE   start_as_current_observationz7LangfuseObservationWrapper.start_as_current_observation  	     36#rG   c                    d S r@   rA   r   s                  rE   r   z7LangfuseObservationWrapper.start_as_current_observation  s	    $ 9<rG   c                    d S r@   rA   r   s                  rE   r   z7LangfuseObservationWrapper.start_as_current_observation  s	    $ 8;srG   c                    d S r@   rA   r   s	            rE   r   z7LangfuseObservationWrapper.start_as_current_observation
  	     473rG   c                    d S r@   rA   r   s	            rE   r   z7LangfuseObservationWrapper.start_as_current_observation  r   rG   c                    d S r@   rA   r   s	            rE   r   z7LangfuseObservationWrapper.start_as_current_observation&  r   rG   c                    d S r@   rA   r   s	            rE   r   z7LangfuseObservationWrapper.start_as_current_observation4  	     8;srG   c                    d S r@   rA   r   s	            rE   r   z7LangfuseObservationWrapper.start_as_current_observationB  r   rG   c                    d S r@   rA   r   s	            rE   r   z7LangfuseObservationWrapper.start_as_current_observationP  r   rG   )	r   r   r   r   r   r   r   r   r   c                `    | j                             ||d| j        |||||||	|
||||          S )a@  Create a new child observation and set it as the current observation in a context manager.

        This is the generic method for creating any type of child observation with
        context management. It delegates to the client's _create_span_with_parent_context method.

        Args:
            name: Name of the observation
            as_type: Type of observation to create
            input: Input data for the operation
            output: Output data from the operation
            metadata: Additional metadata to associate with the observation
            version: Version identifier for the code or component
            level: Importance level of the observation (info, warning, error)
            status_message: Optional status message for the observation
            completion_start_time: When the model started generating (for generation types)
            model: Name/identifier of the AI model used (for generation types)
            model_parameters: Parameters used for the model (for generation types)
            usage_details: Token usage information (for generation types)
            cost_details: Cost information (for generation types)
            prompt: Associated prompt template (for generation types)

        Returns:
            A context manager that yields a new observation of the specified type
        N)rr   r6   remote_parent_spanparentr&   r'   r(   r+   r,   r-   r.   r/   r0   r1   r2   r3   )rL    _create_span_with_parent_contextrI   r   s                  rE   r   z7LangfuseObservationWrapper.start_as_current_observation^  sX    n $EE#?)"7-'%! F 
 
 	
rG   c                V   t                      }t          j        | j                  5  | j        j                            ||          }	ddd           n# 1 swxY w Y   t          dt          |	| j        |||| j	        | j
        |||
  
                            |                    S )a  Create a new Langfuse observation of type 'EVENT'.

        Args:
            name: Name of the span (e.g., function or operation name)
            input: Input data for the operation (can be any JSON-serializable object)
            output: Output data from the operation (can be any JSON-serializable object)
            metadata: Additional metadata to associate with the span
            version: Version identifier for the code or component
            level: Importance level of the span (info, warning, error)
            status_message: Optional status message for the span

        Returns:
            The LangfuseEvent object

        Example:
            ```python
            event = langfuse.create_event(name="process-event")
            ```
        r   Nr   r   rb   )r   r   r   rI   rL   r   r   r   r   rR   rT   rf   )
r\   rr   r&   r'   r(   r+   r,   r-   rq   r   s
             rE   create_eventz'LangfuseObservationWrapper.create_event  s    < II	$T_55 	 	 1>IIi J  M	 	 	 	 	 	 	 	 	 	 	 	 	 	 	
 ' $ 5! --   c9c%%
 
 	
s   "AAA)rd   r"   )+__name__
__module____qualname____doc__r   Spanr   r	   r   r   r!   r   r   r   intfloatr   ra   rf   r   ri   rl   r   r   r   NUMERICBOOLEANrv   r{   r|   r   r   r   rW   r   r   r[   r   r   r   r   r   r   rA   rG   rE   r"   r"   @   s        &  $ $"&%)!%!%%)(,48#:>2637)-'~ ~ ~ "&~ $	~
 (~ }~ ~ 3-~ c]~ #~ #~ 	"~ !~  (1~ }~  #4X#67!~"  S#X/#~$ tCJ/0%~& &'~ ~ ~ ~@ 04   x} 8T     Z	A   $ $	( ( ( }( 	(
 
&( ( ( 
(T   (  #' !%#'(,"&    	
 3- M)=+@@A
 # C= H% 3- 
   X  #' %!%#'(,"&    	
 3- M-}/AAB
 # C= H% 3- 
   X( #'-1!%#'(,"&5
 5
 5
 5
 UCZ 	5

 3-5
 M*5
 #5
 C=5
 H%5
 3-5
 
5
 5
 5
 5
n  #' !%#'(,"&    	
 3- M)=+@@A
 # C= H% 3- 
   X  #' %!%#'(,"&    	
 3- M-}/AAB
 # C= H% 3- 
   X( #'-1!%#'(,"&5
 5
 5
 5
 UCZ 	5

 3-5
 M*5
 #5
 C=5
 H%5
 3-5
 
5
 5
 5
 5
v 59# $"&38 38 38 !38 01	38
 }38 38 3-38 
38 38 38 38p #
 
 
 sm
 !	

 WW%wx'8'*:MMN
 
#
 
 
 
0@s @s @ @ @ @6 #   sm WW%wx'8'*:MMN	
 
#   @ /3TX   +DLSM	   2 ## $"&!%%)(,48#:>2637)-c c c smc }	c
 c 3-c #c 	"c !c  (1c }c #4X#67c  S#X/c tCJ/0c &c  !c" 
&#c c c cJ   $ $"&!%%)(,    	
 }  3- # 	" ! 
   X   $ $"&!%%)(,48#:>2637)-!# # # # &	#
 }# # 3-# ## 	"# !#  (1# }# #4X#67#  S#X/# tCJ/0#  &!#" 
## # # X#&   $ $"&!%%)(,    !	
 }  3- # 	" ! 
   X   $ $"&!%%)(,    	
 }  3- # 	" ! 
   X   $ $"&!%%)(,    !	
 }  3- # 	" ! 
   X   $ $"&!%%)(," " " " %	"
 }" " 3-" #" 	"" !" 
" " " X"   $ $"&!%%)(," " " " %	"
 }" " 3-" #" 	"" !" 
" " " X"   $ $"&!%%)(,48#:>2637)-!" " " " %	"
 }" " 3-" #" 	"" !"  (1" }" #4X#67"  S#X/" tCJ/0"  &!"" 
#" " " X"&   $ $"&!%%)(," " " " %	"
 }" " 3-" #" 	"" !" 
" " " X"   $ $"&!%%)(,    !	
 }  3- # 	" ! 
   X" +1# $"&!%%)(,48#:>2637)-!n0 n0 n0 n0 (	n0
 }n0 n0 3-n0 #n0 	"n0 !n0  (1n0 }n0 #4X#67n0  S#X/n0 tCJ/0n0  &!n0" 
		
#n0 n0 n0 n0`   $ $"&!%%)(,6 6 6 6 	6
 }6 6 3-6 #6 	"6 !6 
!	06 6 6 X6   $ $"&!%%)(,48#:>2637)-!< < < < &	<
 }< < 3-< #< 	"< !<  (1< }< #4X#67<  S#X/< tCJ/0<  &!<" 
!!5	6#< < < X<&   $ $"&!%%)(,48#:>2637)-!; ; ; ; %	;
 }; ; 3-; #; 	"; !;  (1; }; #4X#67;  S#X/; tCJ/0;  &!;" 
!!4	5#; ; ; X;&   $ $"&!%%)(,7 7 7 7 !	7
 }7 7 3-7 #7 	"7 !7 
!	17 7 7 X7   $ $"&!%%)(,6 6 6 6 	6
 }6 6 3-6 #6 	"6 !6 
!	06 6 6 X6   $ $"&!%%)(,7 7 7 7 !	7
 }7 7 3-7 #7 	"7 !7 
!	17 7 7 X7   $ $"&!%%)(,; ; ; ; %	;
 }; ; 3-; #; 	"; !; 
!!4	5; ; ; X;   $ $"&!%%)(,; ; ; ; %	;
 }; ; 3-; #; 	"; !; 
!!4	5; ; ; X;   $ $"&!%%)(,; ; ; ; %	;
 }; ; 3-; #; 	"; !; 
!!4	5; ; ; X;" 28# $"&!%%)(,48#:>2637)-!H
 H
 H
 H
 /	H

 }H
 H
 3-H
 #H
 	"H
 !H
  (1H
 }H
 #4X#67H
  S#X/H
 tCJ/0H
  &!H
$ 
!!
	

%H
 H
 H
 H
\  $ $"&!%%)(,3
 3
 3
 3
 }	3

 3
 3-3
 #3
 	"3
 !3
 
3
 3
 3
 3
 3
 3
rG   c                        e Zd ZdZddddddddddej        dddee         dee         d	ee         d
ee         dee         dee         dee	         dee         f fdZ
 xZS )r   a  Standard span implementation for general operations in Langfuse.

    This class represents a general-purpose span that can be used to trace
    any operation in your application. It extends the base LangfuseObservationWrapper
    with specific methods for creating child spans, generations, and updating
    span-specific attributes. If possible, use a more specific type for
    better observability and insights.
    Nr&   r'   r(   r)   r*   r+   r,   r-   r4   r5   r   r&   r'   r(   r)   r*   r+   r,   r-   c       
         `    t                                          |d||||||||	|
           dS )a  Initialize a new LangfuseSpan.

        Args:
            otel_span: The OpenTelemetry span to wrap
            langfuse_client: Reference to the parent Langfuse client
            input: Input data for the span (any JSON-serializable object)
            output: Output data from the span (any JSON-serializable object)
            metadata: Additional metadata to associate with the span
            environment: The tracing environment
            release: Release identifier for the application
            version: Version identifier for the code or component
            level: Importance level of the span (info, warning, error)
            status_message: Optional status message for the span
        r;   r4   r6   r5   r&   r'   r(   r)   r*   r+   r,   r-   Nsuperra   r\   r4   r5   r&   r'   r(   r)   r*   r+   r,   r-   	__class__s              rE   ra   zLangfuseSpan.__init__  sQ    8 	+#) 	 	
 	
 	
 	
 	
rG   )r   r   r   r   r   r   r	   r   r   r!   ra   __classcell__r   s   @rE   r   r     s           $ $"&%)!%!%%)(,(
 (
 (
 "&(
 $	(

 }(
 (
 3-(
 c](
 #(
 #(
 	"(
 !(
 (
 (
 (
 (
 (
 (
 (
 (
 (
rG   r   c            "       f    e Zd ZdZddddddddddddddddej        dddee         dee         d	ee         d
ee         dee         dee         dee	         dee         dee
         dee         deeeef                  deeeef                  deeeef                  dee         f  fdZ xZS )r   a+  Specialized span implementation for AI model generations in Langfuse.

    This class represents a generation span specifically designed for tracking
    AI/LLM operations. It extends the base LangfuseObservationWrapper with specialized
    attributes for model details, token usage, and costs.
    Nr%   r4   r5   r   r&   r'   r(   r)   r*   r+   r,   r-   r.   r/   r0   r1   r2   r3   c                l    t                                          d|||||||||	|
||||||           dS )a  Initialize a new LangfuseGeneration span.

        Args:
            otel_span: The OpenTelemetry span to wrap
            langfuse_client: Reference to the parent Langfuse client
            input: Input data for the generation (e.g., prompts)
            output: Output from the generation (e.g., completions)
            metadata: Additional metadata to associate with the generation
            environment: The tracing environment
            release: Release identifier for the application
            version: Version identifier for the model or component
            level: Importance level of the generation (info, warning, error)
            status_message: Optional status message for the generation
            completion_start_time: When the model started generating the response
            model: Name/identifier of the AI model used (e.g., "gpt-4")
            model_parameters: Parameters used for the model (e.g., temperature, max_tokens)
            usage_details: Token usage information (e.g., prompt_tokens, completion_tokens)
            cost_details: Cost information for the model call
            prompt: Associated prompt template from Langfuse prompt management
        r   )r6   r4   r5   r&   r'   r(   r)   r*   r+   r,   r-   r.   r/   r0   r1   r2   r3   Nr   )r\   r4   r5   r&   r'   r(   r)   r*   r+   r,   r-   r.   r/   r0   r1   r2   r3   r   s                    rE   ra   zLangfuseGeneration.__init__  sd    P 	 +#)"7-'%# 	 	
 	
 	
 	
 	
rG   )r   r   r   r   r   r   r	   r   r   r!   r   r   r   r   r   r   ra   r   r   s   @rE   r   r     sx          $ $"&%)!%!%%)(,48#:>2637)-%:
 :
 :
 "&:
 $	:

 }:
 :
 3-:
 c]:
 #:
 #:
 	":
 !:
  (1:
 }:
 #4X#67:
   S#X/!:
" tCJ/0#:
$ &%:
 :
 :
 :
 :
 :
 :
 :
 :
 :
rG   r   c                       e Zd ZdZddddddddddej        dddee         dee         d	ee         d
ee         dee         dee         dee	         dee         f fdZ
dddddddddddddddee         dee         dee         d	ee         dee         dee	         dee         dee         dee         deeeef                  deeeef                  deeeef                  dee         dedd fdZ xZS )r   z4Specialized span implementation for Langfuse Events.Nr   r4   r5   r   r&   r'   r(   r)   r*   r+   r,   r-   c       
         `    t                                          |d||||||||	|
           dS )a  Initialize a new LangfuseEvent span.

        Args:
            otel_span: The OpenTelemetry span to wrap
            langfuse_client: Reference to the parent Langfuse client
            input: Input data for the event
            output: Output from the event
            metadata: Additional metadata to associate with the generation
            environment: The tracing environment
            release: Release identifier for the application
            version: Version identifier for the model or component
            level: Importance level of the generation (info, warning, error)
            status_message: Optional status message for the generation
        r=   r   Nr   r   s              rE   ra   zLangfuseEvent.__init__[  sQ    8 	+#) 	 	
 	
 	
 	
 	
rG   r   rr   r.   r/   r0   r1   r2   r3   r   rd   c                .    t          j        d           | S )zUpdate is not allowed for LangfuseEvent because events cannot be updated.

        This method logs a warning and returns self without making changes.

        Returns:
            self: Returns the unchanged LangfuseEvent instance
        zWAttempted to update LangfuseEvent observation. Events cannot be updated after creation.)r    r   )r\   rr   r&   r'   r(   r+   r,   r-   r.   r/   r0   r1   r2   r3   r   s                  rE   r   zLangfuseEvent.update  s#    2 	e	
 	
 	
 rG   )r   r   r   r   r   r   r	   r   r   r!   ra   r   r   r   r   r   r   r   r   r   s   @rE   r   r   X  s!       >>  $ $"&%)!%!%%)(,(
 (
 (
 "&(
 $	(

 }(
 (
 3-(
 c](
 #(
 #(
 	"(
 !(
 (
 (
 (
 (
 (
Z ## $"&!%%)(,48#:>2637)-   sm }	
  3- # 	" !  (1 } #4X#67  S#X/ tCJ/0 &  !" 
#       rG   r   c                   ,     e Zd ZdZdeddf fdZ xZS )r   zLAgent observation for reasoning blocks that act on tools using LLM guidance.r   rd   Nc                 D    d|d<    t                      j        di | dS )z$Initialize a new LangfuseAgent span.r   r6   NrA   r   r\   r   r   s     rE   ra   zLangfuseAgent.__init__  0    #y""6"""""rG   r   r   r   r   r   ra   r   r   s   @rE   r   r     sQ        VV# # # # # # # # # # # #rG   r   c                   ,     e Zd ZdZdeddf fdZ xZS )r   zOTool observation representing external tool calls, e.g., calling a weather API.r   rd   Nc                 D    d|d<    t                      j        di | dS )z#Initialize a new LangfuseTool span.r   r6   NrA   r   r   s     rE   ra   zLangfuseTool.__init__  s0    "y""6"""""rG   r   r   s   @rE   r   r     Q        YY# # # # # # # # # # # #rG   r   c                   ,     e Zd ZdZdeddf fdZ xZS )r   zcChain observation for connecting LLM application steps, e.g. passing context from retriever to LLM.r   rd   Nc                 D    d|d<    t                      j        di | dS )z$Initialize a new LangfuseChain span.r   r6   NrA   r   r   s     rE   ra   zLangfuseChain.__init__  r   rG   r   r   s   @rE   r   r     sQ        mm# # # # # # # # # # # #rG   r   c                   ,     e Zd ZdZdeddf fdZ xZS )r   zVRetriever observation for data retrieval steps, e.g. vector store or database queries.r   rd   Nc                 D    d|d<    t                      j        di | dS )z(Initialize a new LangfuseRetriever span.r   r6   NrA   r   r   s     rE   ra   zLangfuseRetriever.__init__  0    'y""6"""""rG   r   r   s   @rE   r   r     sQ        ``# # # # # # # # # # # #rG   r   c                   ,     e Zd ZdZdeddf fdZ xZS )r   zOEmbedding observation for LLM embedding calls, typically used before retrieval.r   rd   Nc                 D    d|d<    t                      j        di | dS )z(Initialize a new LangfuseEmbedding span.r   r6   NrA   r   r   s     rE   ra   zLangfuseEmbedding.__init__  r  rG   r   r   s   @rE   r   r     r  rG   r   c                   ,     e Zd ZdZdeddf fdZ xZS )r   zZEvaluator observation for assessing relevance, correctness, or helpfulness of LLM outputs.r   rd   Nc                 D    d|d<    t                      j        di | dS )z(Initialize a new LangfuseEvaluator span.r   r6   NrA   r   r   s     rE   ra   zLangfuseEvaluator.__init__  r  rG   r   r   s   @rE   r   r     sQ        dd# # # # # # # # # # # #rG   r   c                   ,     e Zd ZdZdeddf fdZ xZS )r   zRGuardrail observation for protection e.g. against jailbreaks or offensive content.r   rd   Nc                 D    d|d<    t                      j        di | dS )z(Initialize a new LangfuseGuardrail span.r   r6   NrA   r   r   s     rE   ra   zLangfuseGuardrail.__init__  r  rG   r   r   s   @rE   r   r     sQ        \\# # # # # # # # # # # #rG   r   )	r;   r   r   r   r   r   r   r   r   N)=r   r   timer   typingr   r   r   r   r	   r
   r   r   r   opentelemetryr   r   opentelemetry.trace.statusr   r   opentelemetry.util._decoratorr   langfuse.modelr   langfuse._client.clientr   typing_extensionsr   langfuse._client.attributesr   r   r   r   langfuse._client.constantsr   r   r   r   r   langfuse.apir   r   langfuse.loggerr    langfuse.typesr!   r#   r   __annotations__r"   r   r   r   r   r   r   r   r   r   r   r   rA   rG   rE   <module>r     sD                
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 2 1 1 1 1 1 9 9 9 9 9 9 9 9 A A A A A A ' ' ' ' ' ' 1000000 ( ( ( ( ( (                         1 0 0 0 0 0 0 0 + + + + + + $ $ $ $ $ $
 IK S$'C"DDE J J J[
 [
 [
 [
 [
 [
 [
 [
|$2
 2
 2
 2
 2
- 2
 2
 2
jB
 B
 B
 B
 B
3 B
 B
 B
JI I I I I. I I IX# # # # #. # # ## # # # #- # # ## # # # #. # # ## # # # #2 # # ## # # # #2 # # ## # # # #2 # # ## # # # #2 # # #   (&&&&
 
    rG   