o
    Zhc                     @  s   d Z ddlmZ ddlZddlZddlZddlZddl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 ddlmZ ddlmZ eeZG d	d
 d
eZdZG dd dZdS )z,Module providing Infinispan as a VectorStore    )annotationsN)AnyIterableListOptionalTupleTypeUnioncast)Response)Document)
Embeddings)VectorStorec                   @  s  e Zd ZdZ		dWdXd	d
ZdYddZdZddZd[ddZd\ddZd]ddZ	d^d_d!d"Z
d]d#d$Zd]d%d&Zd`d(d)Zd]d*d+Zd]d,d-Z		dWdad5d6Z	7dbdcd;d<Z	7dbddd>d?Z	7dbdedAdBZ	7dbdfdCdDZdgdFdGZdhdJdKZdidLdMZe			N	NdjdkdUdVZdS )lInfinispanVSa  `Infinispan` VectorStore interface.

        This class exposes the method to present Infinispan as a
        VectorStore. It relies on the Infinispan class (below) which takes care
        of the REST interface with the server.

    Example:
        ... code-block:: python
            from langchain_community.vectorstores import InfinispanVS
            from mymodels import RGBEmbeddings
            ...
            vectorDb = InfinispanVS.from_documents(docs,
                            embedding=RGBEmbeddings(),
                            output_fields=["texture", "color"],
                            lambda_key=lambda text,meta: str(meta["_key"]),
                            lambda_content=lambda item: item["color"])

        or an empty InfinispanVS instance can be created if preliminary setup
        is required before populating the store

        ... code-block:: python
            from langchain_community.vectorstores import InfinispanVS
            from mymodels import RGBEmbeddings
            ...
            ispnVS = InfinispanVS()
            # configure Infinispan here
            # i.e. create cache and schema

            # then populate the store
            vectorDb = InfinispanVS.from_documents(docs,
                            embedding=RGBEmbeddings(),
                            output_fields: ["texture", "color"],
                            lambda_key: lambda text,meta: str(meta["_key"]),
                            lambda_content: lambda item: item["color"])
    N	embeddingOptional[Embeddings]idsOptional[List[str]]kwargsr   c                   s   t di | _| _t jdd _t jdd _| _ jdd _ jdkr8 jdd _nt	
dt  jd	d _ jdkrT jd
d _nt	
dt  jd fdd _ jd fdd _ jd _| _dS )at  
        Parameters
        ----------
        cache_name: str
            Embeddings cache name. Default "vector"
        entity_name: str
            Protobuf entity name for the embeddings. Default "vector"
        text_field: str
            Protobuf field name for text. Default "text"
        vector_field: str
            Protobuf field name for vector. Default "vector"
        lambda_content: lambda
            Lambda returning the content part of an item. Default returns text_field
        lambda_metadata: lambda
            Lambda returning the metadata part of an item. Default returns items
            fields excepts text_field, vector_field, _type
        output_fields: List[str]
            List of fields to be returned from item, if None return all fields.
            Default None
        kwargs: Any
            Rest of arguments passed to Infinispan. See docs
cache_namevectorentity_nameZ	textfield Z
text_fieldtextz9`textfield` is deprecated. Please use `text_field` param.ZvectorfieldZvector_fieldz=`vectorfield` is deprecated. Please use `vector_field` param.Zlambda_contentc                   
     | S N)_default_contentitemself d/var/www/html/lang_env/lib/python3.10/site-packages/langchain_community/vectorstores/infinispanvs.py<lambda>i      
 z'InfinispanVS.__init__.<locals>.<lambda>Zlambda_metadatac                   r   r   )_default_metadatar   r   r!   r"   r#   l   r$   Zoutput_fieldsNr!   )
Infinispanispn_configurationstrget_cache_name_entity_name
_embedding
_textfieldwarningswarnDeprecationWarning_vectorfield_to_content_to_metadata_output_fields_ids)r    r   r   r   r!   r   r"   __init__8   s6   


zInfinispanVS.__init__r   dictreturnc                 C  s4   t |}|| jd  || jd  |dd  |S )N_type)r8   popr2   r.   )r    r   metar!   r!   r"   r%   q   s
   zInfinispanVS._default_metadatadict[str, Any]c                 C  s   | | jS r   )r*   r.   )r    r   r!   r!   r"   r   x   s   zInfinispanVS._default_contenttempl	dimensionintr)   c                 C  s  d}|| j || jf }d}| D ]r\}}t|tr)|d| d t| d 7 }nVt|tr=|d| d t| d 7 }nBt|trQ|d| d t| d 7 }n.t|tre|d| d t| d 7 }nt|try|d	| d t| d 7 }nt	d
| |d7 }q|d7 }|S )NzV
/**
* @Indexed
*/
message %s {
/**
* @Vector(dimension=%d)
*/
repeated float %s = 1;
   zoptional string z = z;
zoptional int64 zoptional double zoptional bytes zoptional bool zEUnable to build proto schema for metadata. Unhandled type for field:    z}
)
r,   r2   items
isinstancer)   r@   floatbytesbool	Exception)r    r>   r?   Zmetadata_proto_tplZmetadata_protoidxfvr!   r!   r"   schema_builder{   s4   






zInfinispanVS.schema_builderprotor   c                 C  s   | j | jd |S )zDeploy the schema for the vector db
        Args:
            proto(str): protobuf schema
        Returns:
            An http Response containing the result of the operation
        .proto)r'   schema_postr,   )r    rM   r!   r!   r"   schema_create   s   zInfinispanVS.schema_createc                 C  s   | j | jd S )zDelete the schema for the vector db
        Returns:
            An http Response containing the result of the operation
        rN   )r'   schema_deleter,   r   r!   r!   r"   rQ      s   zInfinispanVS.schema_deleter   configc                 C  s&   |dkrd| j  d }| j| j|S )zCreate the cache for the vector db
        Args:
            config(str): configuration of the cache.
        Returns:
            An http Response containing the result of the operation
        r   aZ  
            {
  "distributed-cache": {
    "owners": "2",
    "mode": "SYNC",
    "statistics": true,
    "encoding": {
      "media-type": "application/x-protostream"
    },
    "indexing": {
      "enabled": true,
      "storage": "filesystem",
      "startup-mode": "AUTO",
      "indexing-mode": "AUTO",
      "indexed-entities": [
        "z"
      ]
    }
  }
}
)r,   r'   
cache_postr+   )r    rR   r!   r!   r"   cache_create   s   zInfinispanVS.cache_createc                 C     | j | jS )zDelete the cache for the vector db
        Returns:
            An http Response containing the result of the operation
        )r'   cache_deleter+   r   r!   r!   r"   rV         zInfinispanVS.cache_deletec                 C  rU   )zClear the cache for the vector db
        Returns:
            An http Response containing the result of the operation
        )r'   cache_clearr+   r   r!   r!   r"   rX      rW   zInfinispanVS.cache_clearrG   c                 C  rU   )zOChecks if the cache exists
        Returns:
            true if exists
        )r'   cache_existsr+   r   r!   r!   r"   rY      rW   zInfinispanVS.cache_existsc                 C  rU   )zClear the index for the vector db
        Returns:
            An http Response containing the result of the operation
        )r'   index_clearr+   r   r!   r!   r"   cache_index_clear   rW   zInfinispanVS.cache_index_clearc                 C  rU   )z{Rebuild the for the vector db
        Returns:
            An http Response containing the result of the operation
        )r'   index_reindexr+   r   r!   r!   r"   cache_index_reindex   rW   z InfinispanVS.cache_index_reindextextsIterable[str]	metadatasOptional[List[dict]]last_vectorOptional[List[float]]	List[str]c                 K  s   g }t |}|r|  | j|}|r|| |s"dd |D }| jp+dd |D }t t|||}	|	D ]%\}
}}d| j| j|i}|	|
 t
|}| j||| j || q6|S )Nc                 S  s   g | ]}i qS r!   r!   .0_r!   r!   r"   
<listcomp>  s    z*InfinispanVS.add_texts.<locals>.<listcomp>c                 S  s   g | ]}t t qS r!   )r)   uuiduuid4re   r!   r!   r"   rh         r:   )listr;   r-   Zembed_documentsappendr6   zipr,   r2   updatejsondumpsr'   putr+   )r    r^   r`   rb   r   resultZtexts_lZembedsr   Z
data_inputmetadataembedkeydataZdata_strr!   r!   r"   	add_texts   s$   


zInfinispanVS.add_texts   querykList[Document]c                 K  s   | j ||d}dd |D S )z"Return docs most similar to query.)rz   r{   c                 S     g | ]\}}|qS r!   r!   rf   docrg   r!   r!   r"   rh         z2InfinispanVS.similarity_search.<locals>.<listcomp>)similarity_search_with_score)r    rz   r{   r   	documentsr!   r!   r"   similarity_search  s   zInfinispanVS.similarity_searchList[Tuple[Document, float]]c                 K  s   | j |}| j||d}|S )a  Perform a search on a query string and return results with score.

        Args:
            query (str): The text being searched.
            k (int, optional): The amount of results to return. Defaults to 4.

        Returns:
            List[Tuple[Document, float]]
        )r   r{   )r-   embed_query&similarity_search_with_score_by_vector)r    rz   r{   r   ru   r   r!   r!   r"   r     s   z)InfinispanVS.similarity_search_with_scoreList[float]c                 K  s   |  ||}dd |D S )Nc                 S  r}   r!   r!   r~   r!   r!   r"   rh   +  r   z<InfinispanVS.similarity_search_by_vector.<locals>.<listcomp>)r   )r    r   r{   r   resr!   r!   r"   similarity_search_by_vector'  s   z(InfinispanVS.similarity_search_by_vectorc                 C  s   | j du rd| j d | j d t| d t| }n6d}| j dd D ]
}|d | d	 }q&|d | j d  }|d
 | j d | j d t| d t| }| j|| j}t	|j
}| |S )a$  Return docs most similar to embedding vector.

        Args:
            embedding: Embedding to look up documents similar to.
            k: Number of Documents to return. Defaults to 4.

        Returns:
            List of pair (Documents, score) most similar to the query vector.
        Nzselect v, score(v) from z v where v.z <-> ~zselect zv.,z, score(v) from )r5   r,   r2   rp   rq   r)   r'   	req_queryr+   loadsr   _query_result_to_docs)r    r   r{   	query_strZ
query_projfieldZ	query_resrs   r!   r!   r"   r   -  sT   

z3InfinispanVS.similarity_search_with_score_by_vectorrs   c                   st   g }|d D ]1}|d pi  | j d u r d }n
 fdd| j D }t| || |d}|| d f q|S )Nhitshit*c                   s   i | ]}|  |qS r!   )r*   )rf   rv   r   r!   r"   
<dictcomp>a  rk   z6InfinispanVS._query_result_to_docs.<locals>.<dictcomp>)Zpage_contentrt   zscore())r5   r   r3   r4   rm   )r    rs   r   rowentityr   r!   r   r"   r   X  s   

z"InfinispanVS._query_result_to_docsrt   Nonec                 C  s   |  ||}| |}|j| jjjksJ d	 t|jd d u s$J | 	 s?| 
 }|j| jjjks8J d	 |   d S d S )Nz)Unable to create schema. Already exists? errorz(Unable to create cache. Already exists? )rL   rP   status_coder'   CodesOKrp   r   r   rY   rT   r[   )r    rt   r?   schemaoutputr!   r!   r"   	configurei  s   
zInfinispanVS.configurec                 C  s   |    |   d S r   )rQ   rV   r   r!   r!   r"   config_clearz  s   zInfinispanVS.config_clearTclsType[InfinispanVS]r   	clear_oldOptional[bool]auto_configc           
      K  s   | d||d|}|r7t |pg dkr7|r|  ||t |d  }	ttt |}||d t |	 n|r=|  ||t |d  }	|rR|j|||	d |S )a  Return VectorStore initialized from texts and embeddings.

        In addition to parameters described by the super method, this
        implementation provides other configuration params if different
        configuration from default is needed.

        Parameters
        ----------
        ids : List[str]
            Additional list of keys associated to the embedding. If not
            provided UUIDs will be generated
        clear_old : bool
            Whether old data must be deleted. Default True
        auto_config: bool
            Whether to do a complete server setup (caches,
            protobuf definition...). Default True
        kwargs: Any
            Rest of arguments passed to InfinispanVS. See docs)r   r   r   rB   )r   Nr!   )	lenr   r   r
   r   r8   r   rX   rx   )
r   r^   r   r`   r   r   r   r   ZinfinispanvsZvecr!   r!   r"   
from_texts~  s   zInfinispanVS.from_texts)NN)r   r   r   r   r   r   )r   r8   r9   r8   )r   r=   r9   r   )r>   r8   r?   r@   r9   r)   )rM   r)   r9   r   )r9   r   )r   )rR   r)   r9   r   )r9   rG   )
r^   r_   r`   ra   rb   rc   r   r   r9   rd   )ry   )rz   r)   r{   r@   r   r   r9   r|   )rz   r)   r{   r@   r   r   r9   r   )r   r   r{   r@   r   r   r9   r|   )r   r   r{   r@   r9   r   )rs   r=   r9   r   )rt   r8   r?   r@   r9   r   )r9   r   )NNTT)r   r   r^   rd   r   r   r`   ra   r   r   r   r   r   r   r   r   r9   r   )__name__
__module____qualname____doc__r7   r%   r   rL   rP   rQ   rT   rV   rX   rY   r[   r]   rx   r   r   r   r   r   r   r   classmethodr   r!   r!   r!   r"   r      sH    &
9


%
	
#





+

r   
   c                	   @  s   e Zd ZdZddddgdddddf	dDddZdEdFddZ	dEdGd!d"Z	dEdGd#d$ZdHd'd(ZdHd)d*Z	dId+d,Z
dJd/d0ZdKd2d3ZdLd4d5ZdLd6d7ZdMd8d9ZdNd:d;ZdOd=d>ZdMd?d@ZdMdAdBZdCS )Pr&   a>  Helper class for `Infinispan` REST interface.

    This class exposes the Infinispan operations needed to
    create and set up a vector db.

    You need a running Infinispan (15+) server without authentication.
    You can easily start one, see:
    https://github.com/rigazilla/infinispan-vector#run-infinispan
    httpr   z127.0.0.1:11222z/rest/v2/cachesz/rest/v2/schemasTr   r)   userpasswordhostsrd   	cache_url
schema_urluse_post_for_queryrG   http2verifyr   r   c
                 K  s   zddl }W n ty   tdw |j| _|
| _|| _|| _|| _|d | _| jd | j | _	|| _
|| _|| _|| _| jrf| jrf| jdkrQ|j| j| jd}n| j| jf}|j| j| j ||	d| _dS |j| j| j |	d| _dS )	aK  
        Parameters
        ----------
        schema: str
            Schema for HTTP request: "http" or "https". Default "http"
        user, password: str
            User and password if auth is required. Default None
        hosts: List[str]
            List of server addresses. Default ["127.0.0.1:11222"]
        cache_url: str
            URL endpoint for cache API. Default "/rest/v2/caches"
        schema_url: str
            URL endpoint for schema API. Default "/rest/v2/schemas"
        use_post_for_query: bool
            Whether POST method should be used for query. Default True
        http2: bool
            Whether HTTP/2 protocol should be used. `pip install "httpx[http2]"` is
            needed for HTTP/2. Default True
        verify:  bool
            Whether TLS certificate must be verified. Default True
        r   NzCould not import httpx python package. Please install it with `pip install httpx`or `pip install "httpx[http2]"` if you need HTTP/2.z://r   )usernamer   )r   http1authr   )r   r   r   )httpxImportErrorcodesr   r(   Z_schema_userZ	_passwordZ_host_default_node
_cache_url_schema_url_use_post_for_queryZ_http2Z
DigestAuthZClient_h2c)r    r   r   r   r   r   r   r   r   r   r   r   r   r!   r!   r"   r7     sF   #

zInfinispan.__init__Frz   r   localr9   r   c                 C  s"   | j r
| |||S | |||S )a  Request a query
        Args:
            query(str): query requested
            cache_name(str): name of the target cache
            local(boolean): whether the query is local to clustered
        Returns:
            An http Response containing the result set or errors
        )r   _query_post
_query_get)r    rz   r   r   r!   r!   r"   r     s   	zInfinispan.req_queryr   c                 C  sN   | j | j d | d t| }d|i}t|}| jj||dditd}|S )N/z?action=search&local=rz   Content-Typeapplication/jsoncontentheaderstimeout)r   r   r)   rp   rq   r   postREST_TIMEOUT)r    r   r   r   api_urlrw   Z	data_jsonresponser!   r!   r"   r     s*   
zInfinispan._query_postc                 C  s<   | j | j d | d | d t| }| jj|td}|S )Nr   z?action=search&query=z&local=r   )r   r   r)   r   r*   r   )r    r   r   r   r   r   r!   r!   r"   r   '  s$   
zInfinispan._query_getrv   rw   c                 C  8   | j | j d | d | }| jj||dditd}|S )a  Post an entry
        Args:
            key(str): key of the entry
            data(str): content of the entry in json format
            cache_name(str): target cache
        Returns:
            An http Response containing the result of the operation
        r   r   r   r   r   r   r   r   r   r    rv   rw   r   r   r   r!   r!   r"   r   7     	zInfinispan.postc                 C  r   )a  Put an entry
        Args:
            key(str): key of the entry
            data(str): content of the entry in json format
            cache_name(str): target cache
        Returns:
            An http Response containing the result of the operation
        r   r   r   r   )r   r   r   rr   r   r   r!   r!   r"   rr   I  r   zInfinispan.putc                 C  s6   | j | j d | d | }| jj|dditd}|S )zGet an entry
        Args:
            key(str): key of the entry
            cache_name(str): target cache
        Returns:
            An http Response containing the entry or errors
        r   r   r   )r   r   )r   r   r   r*   r   )r    rv   r   r   r   r!   r!   r"   r*   [  s
   
zInfinispan.getnamerM   c                 C  s*   | j | j d | }| jj||td}|S )zDeploy a schema
        Args:
            name(str): name of the schema. Will be used as a key
            proto(str): protobuf schema
        Returns:
            An http Response containing the result of the operation
        r   )r   r   )r   r   r   r   r   )r    r   rM   r   r   r!   r!   r"   rO   i  s   zInfinispan.schema_postrR   c                 C  s0   | j | j d | }| jj||dditd}|S )zCreate a cache
        Args:
            name(str): name of the cache.
            config(str): configuration of the cache.
        Returns:
            An http Response containing the result of the operation
        r   r   r   r   r   )r    r   rR   r   r   r!   r!   r"   rS   u  s   zInfinispan.cache_postc                 C  (   | j | j d | }| jj|td}|S )zDelete a schema
        Args:
            name(str): name of the schema.
        Returns:
            An http Response containing the result of the operation
        r   r   )r   r   r   deleter   r    r   r   r   r!   r!   r"   rQ        zInfinispan.schema_deletec                 C  r   )zDelete a cache
        Args:
            name(str): name of the cache.
        Returns:
            An http Response containing the result of the operation
        r   r   )r   r   r   r   r   r   r!   r!   r"   rV     r   zInfinispan.cache_deletec                 C  s,   | j | j d | d }| jj|td}|S )zClear a cache
        Args:
            cache_name(str): name of the cache.
        Returns:
            An http Response containing the result of the operation
        r   ?action=clearr   r   )r    r   r   r   r!   r!   r"   rX     s   zInfinispan.cache_clearc                 C  s"   | j | j d | d }| |S )zCheck if a cache exists
        Args:
            cache_name(str): name of the cache.
        Returns:
            True if cache exists
        r   r   )r   r   resource_existsr    r   r   r!   r!   r"   rY     s   
zInfinispan.cache_existsr   c                 C  s   | j j|td}|j| jjkS )zCheck if a resource exists
        Args:
            api_url(str): url of the resource.
        Returns:
            true if resource exists
        r   )r   headr   r   r   r   )r    r   r   r!   r!   r"   r     s   zInfinispan.resource_existsc                 C  (   | j | j d | d }| jj|tdS )zClear an index on a cache
        Args:
            cache_name(str): name of the cache.
        Returns:
            An http Response containing the result of the operation
        r   z/search/indexes?action=clearr   r   r   r!   r!   r"   rZ        zInfinispan.index_clearc                 C  r   )zRebuild index on a cache
        Args:
            cache_name(str): name of the cache.
        Returns:
            An http Response containing the result of the operation
        r   z/search/indexes?action=reindexr   r   r   r!   r!   r"   r\     r   zInfinispan.index_reindexN)r   r)   r   r)   r   r)   r   rd   r   r)   r   r)   r   rG   r   rG   r   rG   r   r   )F)rz   r)   r   r)   r   rG   r9   r   )r   r)   r   r)   r   rG   r9   r   )rv   r)   rw   r)   r   r)   r9   r   )rv   r)   r   r)   r9   r   )r   r)   rM   r)   r9   r   )r   r)   rR   r)   r9   r   )r   r)   r9   r   )r   r)   r9   r   )r   r)   r9   rG   )r   r)   r9   rG   )r   r   r   r   r7   r   r   r   r   rr   r*   rO   rS   rQ   rV   rX   rY   r   rZ   r\   r!   r!   r!   r"   r&     s:    L











r&   )r   
__future__r   rp   loggingri   r/   typingr   r   r   r   r   r   r	   r
   r   r   Zlangchain_core.documentsr   Zlangchain_core.embeddingsr   Zlangchain_core.vectorstoresr   	getLoggerr   loggerr   r   r&   r!   r!   r!   r"   <module>   s$    (
   