viruPVS/langchain-docs huggingface dataset:
Source code for langchain_community.chat_message_histories.neo4j
from typing import List, Optional, Union
from langchain_core.chat_history import BaseChatMessageHistory
from langchain_core.messages import BaseMessage, messages_from_dict
from langchain_core.utils import get_from_env
[docs]class Neo4jChatMessageHistory(BaseChatMessageHistory):
    """Chat message history stored in a Neo4j database."""
[docs]    def __init__(
        self,
        session_id: Union[str, int],
        url: Optional[str] = None,
        username: Optional[str] = None,
        password: Optional[str] = None,
        database: str = "neo4j",
        node_label: str = "Session",
        window: int = 3,
    ):
        try:
            import neo4j
        except ImportError:
            raise ValueError(
                "Could not import neo4j python package. "
                "Please install it with `pip install neo4j`."
            )
        # Make sure session id is not null
        if not session_id:
            raise ValueError("Please ensure that the session_id parameter is provided")
        url = get_from_env("url", "NEO4J_URI", url)
        username = get_from_env("username", "NEO4J_USERNAME", username)
        password = get_from_env("password", "NEO4J_PASSWORD", password)
        database = get_from_env("database", "NEO4J_DATABASE", database)
        self._driver = neo4j.GraphDatabase.driver(url, auth=(username, password))
        self._database = database
        self._session_id = session_id
        self._node_label = node_label
        self._window = window
        # Verify connection
        try:
self._window = window
        # Verify connection
        try:
            self._driver.verify_connectivity()
        except neo4j.exceptions.ServiceUnavailable:
            raise ValueError(
                "Could not connect to Neo4j database. "
                "Please ensure that the url is correct"
            )
        except neo4j.exceptions.AuthError:
            raise ValueError(
                "Could not connect to Neo4j database. "
                "Please ensure that the username and password are correct"
            )
        # Create session node
        self._driver.execute_query(
            f"MERGE (s:`{self._node_label}` {{id:$session_id}})",
            {"session_id": self._session_id},
        ).summary
    @property
    def messages(self) -> List[BaseMessage]:  # type: ignore
        """Retrieve the messages from Neo4j"""
        query = (
            f"MATCH (s:`{self._node_label}`)-[:LAST_MESSAGE]->(last_message) "
            "WHERE s.id = $session_id MATCH p=(last_message)<-[:NEXT*0.."
            f"{self._window*2}]-() WITH p, length(p) AS length "
            "ORDER BY length DESC LIMIT 1 UNWIND reverse(nodes(p)) AS node "
            "RETURN {data:{content: node.content}, type:node.type} AS result"
        )
        records, _, _ = self._driver.execute_query(
            query, {"session_id": self._session_id}
        )
        messages = messages_from_dict([el["result"] for el in records])
        return messages
[docs]    def add_message(self, message: BaseMessage) -> None:
        """Append the message to the record in Neo4j"""
        query = (
"""Append the message to the record in Neo4j"""
        query = (
            f"MATCH (s:`{self._node_label}`) WHERE s.id = $session_id "
            "OPTIONAL MATCH (s)-[lm:LAST_MESSAGE]->(last_message) "
            "CREATE (s)-[:LAST_MESSAGE]->(new:Message) "
            "SET new += {type:$type, content:$content} "
            "WITH new, lm, last_message WHERE last_message IS NOT NULL "
            "CREATE (last_message)-[:NEXT]->(new) "
            "DELETE lm"
        )
        self._driver.execute_query(
            query,
            {
                "type": message.type,
                "content": message.content,
                "session_id": self._session_id,
            },
        ).summary
[docs]    def clear(self) -> None:
        """Clear session memory from Neo4j"""
        query = (
            f"MATCH (s:`{self._node_label}`)-[:LAST_MESSAGE]->(last_message) "
            "WHERE s.id = $session_id MATCH p=(last_message)<-[:NEXT]-() "
            "WITH p, length(p) AS length ORDER BY length DESC LIMIT 1 "
            "UNWIND nodes(p) as node DETACH DELETE node;"
        )
        self._driver.execute_query(query, {"session_id": self._session_id}).summary
    def __del__(self) -> None:
        if self._driver:
            self._driver.close()
Source code for langchain_community.chat_message_histories.xata
import json
from typing import List
from langchain_core.chat_history import BaseChatMessageHistory
from langchain_core.messages import (
    BaseMessage,
    message_to_dict,
    messages_from_dict,
)
[docs]class XataChatMessageHistory(BaseChatMessageHistory):
    """Chat message history stored in a Xata database."""
[docs]    def __init__(
        self,
        session_id: str,
        db_url: str,
        api_key: str,
        branch_name: str = "main",
        table_name: str = "messages",
        create_table: bool = True,
    ) -> None:
        """Initialize with Xata client."""
        try:
            from xata.client import XataClient  # noqa: F401
        except ImportError:
            raise ValueError(
                "Could not import xata python package. "
                "Please install it with `pip install xata`."
            )
        self._client = XataClient(
            api_key=api_key, db_url=db_url, branch_name=branch_name
        )
        self._table_name = table_name
        self._session_id = session_id
        if create_table:
            self._create_table_if_not_exists()
    def _create_table_if_not_exists(self) -> None:
        r = self._client.table().get_schema(self._table_name)
        if r.status_code <= 299:
            return
        if r.status_code != 404:
            raise Exception(
                f"Error checking if table exists in Xata: {r.status_code} {r}"
            )
        r = self._client.table().create(self._table_name)
        if r.status_code > 299:
if r.status_code > 299:
            raise Exception(f"Error creating table in Xata: {r.status_code} {r}")
        r = self._client.table().set_schema(
            self._table_name,
            payload={
                "columns": [
                    {"name": "sessionId", "type": "string"},
                    {"name": "type", "type": "string"},
                    {"name": "role", "type": "string"},
                    {"name": "content", "type": "text"},
                    {"name": "name", "type": "string"},
                    {"name": "additionalKwargs", "type": "json"},
                ]
            },
        )
        if r.status_code > 299:
            raise Exception(f"Error setting table schema in Xata: {r.status_code} {r}")
[docs]    def add_message(self, message: BaseMessage) -> None:
        """Append the message to the Xata table"""
        msg = message_to_dict(message)
        r = self._client.records().insert(
            self._table_name,
            {
                "sessionId": self._session_id,
                "type": msg["type"],
                "content": message.content,
                "additionalKwargs": json.dumps(message.additional_kwargs),
                "role": msg["data"].get("role"),
                "name": msg["data"].get("name"),
            },
        )
        if r.status_code > 299:
            raise Exception(f"Error adding message to Xata: {r.status_code} {r}")
    @property
    def messages(self) -> List[BaseMessage]:  # type: ignore
        r = self._client.data().query(
            self._table_name,
            payload={
                "filter": {
self._table_name,
            payload={
                "filter": {
                    "sessionId": self._session_id,
                },
                "sort": {"xata.createdAt": "asc"},
            },
        )
        if r.status_code != 200:
            raise Exception(f"Error running query: {r.status_code} {r}")
        msgs = messages_from_dict(
            [
                {
                    "type": m["type"],
                    "data": {
                        "content": m["content"],
                        "role": m.get("role"),
                        "name": m.get("name"),
                        "additional_kwargs": json.loads(m["additionalKwargs"]),
                    },
                }
                for m in r["records"]
            ]
        )
        return msgs
[docs]    def clear(self) -> None:
        """Delete session from Xata table."""
        while True:
            r = self._client.data().query(
                self._table_name,
                payload={
                    "columns": ["id"],
                    "filter": {
                        "sessionId": self._session_id,
                    },
                },
            )
            if r.status_code != 200:
                raise Exception(f"Error running query: {r.status_code} {r}")
            ids = [rec["id"] for rec in r["records"]]
            if len(ids) == 0:
                break
            operations = [
                {"delete": {"table": self._table_name, "id": id}} for id in ids
            ]
            self._client.records().transaction(payload={"operations": operations})
Source code for langchain_community.chat_message_histories.zep
from __future__ import annotations
import logging
from typing import TYPE_CHECKING, Any, Dict, List, Optional
from langchain_core.chat_history import BaseChatMessageHistory
from langchain_core.messages import (
    AIMessage,
    BaseMessage,
    HumanMessage,
    SystemMessage,
)
if TYPE_CHECKING:
    from zep_python import Memory, MemorySearchResult, Message, NotFoundError
logger = logging.getLogger(__name__)
[docs]class ZepChatMessageHistory(BaseChatMessageHistory):
    """Chat message history that uses Zep as a backend.
    Recommended usage::
        # Set up Zep Chat History
        zep_chat_history = ZepChatMessageHistory(
            session_id=session_id,
            url=ZEP_API_URL,
            api_key=<your_api_key>,
        )
        # Use a standard ConversationBufferMemory to encapsulate the Zep chat history
        memory = ConversationBufferMemory(
            memory_key="chat_history", chat_memory=zep_chat_history
        )
    Zep provides long-term conversation storage for LLM apps. The server stores,
    summarizes, embeds, indexes, and enriches conversational AI chat
    histories, and exposes them via simple, low-latency APIs.
    For server installation instructions and more, see:
    https://docs.getzep.com/deployment/quickstart/
    This class is a thin wrapper around the zep-python package. Additional
    Zep functionality is exposed via the `zep_summary` and `zep_messages`
    properties.
    For more information on the zep-python package, see:
    https://github.com/getzep/zep-python
    """
[docs]    def __init__(
        self,
        session_id: str,
[docs]    def __init__(
        self,
        session_id: str,
        url: str = "http://localhost:8000",
        api_key: Optional[str] = None,
    ) -> None:
        try:
            from zep_python import ZepClient
        except ImportError:
            raise ImportError(
                "Could not import zep-python package. "
                "Please install it with `pip install zep-python`."
            )
        self.zep_client = ZepClient(base_url=url, api_key=api_key)
        self.session_id = session_id
    @property
    def messages(self) -> List[BaseMessage]:  # type: ignore
        """Retrieve messages from Zep memory"""
        zep_memory: Optional[Memory] = self._get_memory()
        if not zep_memory:
            return []
        messages: List[BaseMessage] = []
        # Extract summary, if present, and messages
        if zep_memory.summary:
            if len(zep_memory.summary.content) > 0:
                messages.append(SystemMessage(content=zep_memory.summary.content))
        if zep_memory.messages:
            msg: Message
            for msg in zep_memory.messages:
                metadata: Dict = {
                    "uuid": msg.uuid,
                    "created_at": msg.created_at,
                    "token_count": msg.token_count,
                    "metadata": msg.metadata,
                }
                if msg.role == "ai":
                    messages.append(
                        AIMessage(content=msg.content, additional_kwargs=metadata)
                    )
                else:
                    messages.append(
                        HumanMessage(content=msg.content, additional_kwargs=metadata)
                    )
        return messages
    @property
    def zep_messages(self) -> List[Message]:
@property
    def zep_messages(self) -> List[Message]:
        """Retrieve summary from Zep memory"""
        zep_memory: Optional[Memory] = self._get_memory()
        if not zep_memory:
            return []
        return zep_memory.messages
    @property
    def zep_summary(self) -> Optional[str]:
        """Retrieve summary from Zep memory"""
        zep_memory: Optional[Memory] = self._get_memory()
        if not zep_memory or not zep_memory.summary:
            return None
        return zep_memory.summary.content
    def _get_memory(self) -> Optional[Memory]:
        """Retrieve memory from Zep"""
        from zep_python import NotFoundError
        try:
            zep_memory: Memory = self.zep_client.memory.get_memory(self.session_id)
        except NotFoundError:
            logger.warning(
                f"Session {self.session_id} not found in Zep. Returning None"
            )
            return None
        return zep_memory
[docs]    def add_user_message(
        self, message: str, metadata: Optional[Dict[str, Any]] = None
    ) -> None:
        """Convenience method for adding a human message string to the store.
        Args:
            message: The string contents of a human message.
            metadata: Optional metadata to attach to the message.
        """
        self.add_message(HumanMessage(content=message), metadata=metadata)
[docs]    def add_ai_message(
        self, message: str, metadata: Optional[Dict[str, Any]] = None
    ) -> None:
        """Convenience method for adding an AI message string to the store.
        Args:
            message: The string contents of an AI message.
Args:
            message: The string contents of an AI message.
            metadata: Optional metadata to attach to the message.
        """
        self.add_message(AIMessage(content=message), metadata=metadata)
[docs]    def add_message(
        self, message: BaseMessage, metadata: Optional[Dict[str, Any]] = None
    ) -> None:
        """Append the message to the Zep memory history"""
        from zep_python import Memory, Message
        zep_message = Message(
            content=message.content, role=message.type, metadata=metadata
        )
        zep_memory = Memory(messages=[zep_message])
        self.zep_client.memory.add_memory(self.session_id, zep_memory)
[docs]    def search(
        self, query: str, metadata: Optional[Dict] = None, limit: Optional[int] = None
    ) -> List[MemorySearchResult]:
        """Search Zep memory for messages matching the query"""
        from zep_python import MemorySearchPayload
        payload: MemorySearchPayload = MemorySearchPayload(
            text=query, metadata=metadata
        )
        return self.zep_client.memory.search_memory(
            self.session_id, payload, limit=limit
        )
[docs]    def clear(self) -> None:
        """Clear session memory from Zep. Note that Zep is long-term storage for memory
        and this is not advised unless you have specific data retention requirements.
        """
        try:
            self.zep_client.memory.delete_memory(self.session_id)
        except NotFoundError:
            logger.warning(
                f"Session {self.session_id} not found in Zep. Skipping delete."
            )
Source code for langchain_community.chat_message_histories.astradb
"""Astra DB - based chat message history, based on astrapy."""
from __future__ import annotations
import json
import time
import typing
from typing import List, Optional
if typing.TYPE_CHECKING:
    from astrapy.db import AstraDB as LibAstraDB
from langchain_core.chat_history import BaseChatMessageHistory
from langchain_core.messages import (
    BaseMessage,
    message_to_dict,
    messages_from_dict,
)
DEFAULT_COLLECTION_NAME = "langchain_message_store"
[docs]class AstraDBChatMessageHistory(BaseChatMessageHistory):
    """Chat message history that stores history in Astra DB.
    Args (only keyword-arguments accepted):
        session_id: arbitrary key that is used to store the messages
            of a single chat session.
        collection_name (str): name of the Astra DB collection to create/use.
        token (Optional[str]): API token for Astra DB usage.
        api_endpoint (Optional[str]): full URL to the API endpoint,
            such as "https://<DB-ID>-us-east1.apps.astra.datastax.com".
        astra_db_client (Optional[Any]): *alternative to token+api_endpoint*,
            you can pass an already-created 'astrapy.db.AstraDB' instance.
        namespace (Optional[str]): namespace (aka keyspace) where the
            collection is created. Defaults to the database's "default namespace".
    """
[docs]    def __init__(
        self,
        *,
        session_id: str,
        collection_name: str = DEFAULT_COLLECTION_NAME,
        token: Optional[str] = None,
        api_endpoint: Optional[str] = None,
api_endpoint: Optional[str] = None,
        astra_db_client: Optional[LibAstraDB] = None,  # type 'astrapy.db.AstraDB'
        namespace: Optional[str] = None,
    ) -> None:
        """Create an Astra DB chat message history."""
        try:
            from astrapy.db import AstraDB as LibAstraDB
        except (ImportError, ModuleNotFoundError):
            raise ImportError(
                "Could not import a recent astrapy python package. "
                "Please install it with `pip install --upgrade astrapy`."
            )
        # Conflicting-arg checks:
        if astra_db_client is not None:
            if token is not None or api_endpoint is not None:
                raise ValueError(
                    "You cannot pass 'astra_db_client' to AstraDB if passing "
                    "'token' and 'api_endpoint'."
                )
        self.session_id = session_id
        self.collection_name = collection_name
        self.token = token
        self.api_endpoint = api_endpoint
        self.namespace = namespace
        if astra_db_client is not None:
            self.astra_db = astra_db_client
        else:
            self.astra_db = LibAstraDB(
                token=self.token,
                api_endpoint=self.api_endpoint,
                namespace=self.namespace,
            )
        self.collection = self.astra_db.create_collection(self.collection_name)
    @property
    def messages(self) -> List[BaseMessage]:  # type: ignore
        """Retrieve all session messages from DB"""
        message_blobs = [
            doc["body_blob"]
            for doc in sorted(
                self.collection.paginated_find(
                    filter={
                        "session_id": self.session_id,
                    },
filter={
                        "session_id": self.session_id,
                    },
                    projection={
                        "timestamp": 1,
                        "body_blob": 1,
                    },
                ),
                key=lambda _doc: _doc["timestamp"],
            )
        ]
        items = [json.loads(message_blob) for message_blob in message_blobs]
        messages = messages_from_dict(items)
        return messages
[docs]    def add_message(self, message: BaseMessage) -> None:
        """Write a message to the table"""
        self.collection.insert_one(
            {
                "timestamp": time.time(),
                "session_id": self.session_id,
                "body_blob": json.dumps(message_to_dict(message)),
            }
        )
[docs]    def clear(self) -> None:
        """Clear session memory from DB"""
        self.collection.delete_many(filter={"session_id": self.session_id})
Source code for langchain_community.chat_message_histories.mongodb
import json
import logging
from typing import List
from langchain_core.chat_history import BaseChatMessageHistory
from langchain_core.messages import (
    BaseMessage,
    message_to_dict,
    messages_from_dict,
)
logger = logging.getLogger(__name__)
DEFAULT_DBNAME = "chat_history"
DEFAULT_COLLECTION_NAME = "message_store"
[docs]class MongoDBChatMessageHistory(BaseChatMessageHistory):
    """Chat message history that stores history in MongoDB.
    Args:
        connection_string: connection string to connect to MongoDB
        session_id: arbitrary key that is used to store the messages
            of a single chat session.
        database_name: name of the database to use
        collection_name: name of the collection to use
    """
[docs]    def __init__(
        self,
        connection_string: str,
        session_id: str,
        database_name: str = DEFAULT_DBNAME,
        collection_name: str = DEFAULT_COLLECTION_NAME,
    ):
        from pymongo import MongoClient, errors
        self.connection_string = connection_string
        self.session_id = session_id
        self.database_name = database_name
        self.collection_name = collection_name
        try:
            self.client: MongoClient = MongoClient(connection_string)
        except errors.ConnectionFailure as error:
            logger.error(error)
        self.db = self.client[database_name]
        self.collection = self.db[collection_name]
        self.collection.create_index("SessionId")
    @property
    def messages(self) -> List[BaseMessage]:  # type: ignore
        """Retrieve the messages from MongoDB"""
        from pymongo import errors
        try:
            cursor = self.collection.find({"SessionId": self.session_id})
        except errors.OperationFailure as error:
            logger.error(error)
except errors.OperationFailure as error:
            logger.error(error)
        if cursor:
            items = [json.loads(document["History"]) for document in cursor]
        else:
            items = []
        messages = messages_from_dict(items)
        return messages
[docs]    def add_message(self, message: BaseMessage) -> None:
        """Append the message to the record in MongoDB"""
        from pymongo import errors
        try:
            self.collection.insert_one(
                {
                    "SessionId": self.session_id,
                    "History": json.dumps(message_to_dict(message)),
                }
            )
        except errors.WriteError as err:
            logger.error(err)
[docs]    def clear(self) -> None:
        """Clear session memory from MongoDB"""
        from pymongo import errors
        try:
            self.collection.delete_many({"SessionId": self.session_id})
        except errors.WriteError as err:
            logger.error(err)