diff --git a/libs/core/langchain_core/_api/__init__.py b/libs/core/langchain_core/_api/__init__.py index 57a94aa472a..3e533bd96df 100644 --- a/libs/core/langchain_core/_api/__init__.py +++ b/libs/core/langchain_core/_api/__init__.py @@ -16,6 +16,7 @@ from .beta_decorator import ( ) from .deprecation import ( LangChainDeprecationWarning, + caller_aware_warn, deprecated, suppress_langchain_deprecation_warning, surface_langchain_deprecation_warnings, @@ -35,4 +36,5 @@ __all__ = [ "suppress_langchain_deprecation_warning", "surface_langchain_deprecation_warnings", "warn_deprecated", + "caller_aware_warn", ] diff --git a/libs/core/langchain_core/_api/deprecation.py b/libs/core/langchain_core/_api/deprecation.py index 52c4e9c8dfa..b5d783623d7 100644 --- a/libs/core/langchain_core/_api/deprecation.py +++ b/libs/core/langchain_core/_api/deprecation.py @@ -13,6 +13,7 @@ https://github.com/matplotlib/matplotlib/blob/main/lib/matplotlib/_api/deprecati import contextlib import functools import inspect +import os import warnings from typing import Any, Callable, Generator, Type, TypeVar @@ -27,6 +28,45 @@ class LangChainPendingDeprecationWarning(PendingDeprecationWarning): """A class for issuing deprecation warnings for LangChain users.""" +def is_warning_internal() -> bool: + """Check if the warning is internal to LangChain libraries.""" + # Get the current stack frame + try: + stack = inspect.stack(context=1) + for idx, frame in enumerate(stack): + if frame.filename.split("/")[-1] != "deprecation.py": + break + + # Here we will be looking at the first frame which is not in deprecation.py + # This frame is the caller of the warning, and it will be the + # @deprecated decorator usually (i.e., the file that uses the decorator) + # We want to step another frame back to get the actual caller of the function + # that uses the decorator. + idx += 1 + + caller_frame = stack[idx].frame + # You can now use the frame object, for example, to get information about the code + if "__package__" not in caller_frame.f_globals: + return False + package = caller_frame.f_globals["__package__"] + # Most langchain libraries start with langchain. + # So this will suppress warnings from most langchain libraries. + # This does not have to be perfect + return package.startswith("langchain") + except Exception: + return False + + +SURFACE_INTERNAL_WARNINGS = ( + os.environ.get("SURFACE_INTERNAL_WARNINGS", "false").lower() == "true" +) + + +def _get_surface_internal_warnings() -> bool: + """Mocked for testing.""" + return SURFACE_INTERNAL_WARNINGS + + # PUBLIC API @@ -379,8 +419,11 @@ def warn_deprecated( warning_cls = ( LangChainPendingDeprecationWarning if pending else LangChainDeprecationWarning ) - warning = warning_cls(message) - warnings.warn(warning, category=LangChainDeprecationWarning, stacklevel=2) + caller_aware_warn( + message, + category=warning_cls, + surface_internal_warnings=_get_surface_internal_warnings(), + ) def surface_langchain_deprecation_warnings() -> None: @@ -394,3 +437,19 @@ def surface_langchain_deprecation_warnings() -> None: "default", category=LangChainDeprecationWarning, ) + + +def caller_aware_warn( + message: str, + *, + category: Type[Warning] = LangChainDeprecationWarning, + surface_internal_warnings: bool = False, +) -> None: + """Warn deprecated""" + is_warning_internal() + if surface_internal_warnings: + warnings.warn(message, category=category, stacklevel=2) + else: + if is_warning_internal(): + return + warnings.warn(message, category=category, stacklevel=2) diff --git a/libs/core/tests/unit_tests/_api/test_deprecation.py b/libs/core/tests/unit_tests/_api/test_deprecation.py index 8573d64b379..0e789d42138 100644 --- a/libs/core/tests/unit_tests/_api/test_deprecation.py +++ b/libs/core/tests/unit_tests/_api/test_deprecation.py @@ -1,13 +1,24 @@ import inspect import warnings +from contextlib import contextmanager from typing import Any, Dict +from unittest.mock import patch import pytest +from langchain_core._api import deprecation from langchain_core._api.deprecation import deprecated, warn_deprecated from langchain_core.pydantic_v1 import BaseModel +@contextmanager +def surface_internal_warnings() -> None: + """Mock surface_langchain_deprecation_warnings.""" + with patch.object(deprecation, "_get_surface_internal_warnings") as func: + func.return_value = True + yield func + + @pytest.mark.parametrize( "kwargs, expected_message", [ @@ -53,14 +64,15 @@ from langchain_core.pydantic_v1 import BaseModel ) def test_warn_deprecated(kwargs: Dict[str, Any], expected_message: str) -> None: """Test warn deprecated.""" - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") - warn_deprecated(**kwargs) + warn_deprecated(**kwargs) - assert len(warning_list) == 1 - warning = warning_list[0].message - assert str(warning) == expected_message + assert len(warning_list) == 1 + warning = warning_list[0].message + assert str(warning) == expected_message def test_undefined_deprecation_schedule() -> None: @@ -117,143 +129,152 @@ class ClassWithDeprecatedMethods: def test_deprecated_function() -> None: """Test deprecated function.""" - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") - assert deprecated_function() == "This is a deprecated function." - assert len(warning_list) == 1 - warning = warning_list[0].message - assert str(warning) == ( - "The function `deprecated_function` was deprecated in LangChain 2.0.0 " - "and will be removed in 3.0.0" - ) + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") + assert deprecated_function() == "This is a deprecated function." + assert len(warning_list) == 1 + warning = warning_list[0].message + assert str(warning) == ( + "The function `deprecated_function` was deprecated in LangChain 2.0.0 " + "and will be removed in 3.0.0" + ) - doc = deprecated_function.__doc__ - assert isinstance(doc, str) - assert doc.startswith("[*Deprecated*] original doc") + doc = deprecated_function.__doc__ + assert isinstance(doc, str) + assert doc.startswith("[*Deprecated*] original doc") - assert not inspect.iscoroutinefunction(deprecated_function) + assert not inspect.iscoroutinefunction(deprecated_function) @pytest.mark.asyncio async def test_deprecated_async_function() -> None: """Test deprecated async function.""" - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") - assert ( - await deprecated_async_function() == "This is a deprecated async function." - ) - assert len(warning_list) == 1 - warning = warning_list[0].message - assert str(warning) == ( - "The function `deprecated_async_function` was deprecated " - "in LangChain 2.0.0 and will be removed in 3.0.0" - ) + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") + assert ( + await deprecated_async_function() + == "This is a deprecated async function." + ) + assert len(warning_list) == 1 + warning = warning_list[0].message + assert str(warning) == ( + "The function `deprecated_async_function` was deprecated " + "in LangChain 2.0.0 and will be removed in 3.0.0" + ) - doc = deprecated_function.__doc__ - assert isinstance(doc, str) - assert doc.startswith("[*Deprecated*] original doc") + doc = deprecated_function.__doc__ + assert isinstance(doc, str) + assert doc.startswith("[*Deprecated*] original doc") - assert inspect.iscoroutinefunction(deprecated_async_function) + assert inspect.iscoroutinefunction(deprecated_async_function) def test_deprecated_method() -> None: """Test deprecated method.""" - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") - obj = ClassWithDeprecatedMethods() - assert obj.deprecated_method() == "This is a deprecated method." - assert len(warning_list) == 1 - warning = warning_list[0].message - assert str(warning) == ( - "The function `deprecated_method` was deprecated in " - "LangChain 2.0.0 and will be removed in 3.0.0" - ) + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") + obj = ClassWithDeprecatedMethods() + assert obj.deprecated_method() == "This is a deprecated method." + assert len(warning_list) == 1 + warning = warning_list[0].message + assert str(warning) == ( + "The function `deprecated_method` was deprecated in " + "LangChain 2.0.0 and will be removed in 3.0.0" + ) - doc = obj.deprecated_method.__doc__ - assert isinstance(doc, str) - assert doc.startswith("[*Deprecated*] original doc") + doc = obj.deprecated_method.__doc__ + assert isinstance(doc, str) + assert doc.startswith("[*Deprecated*] original doc") - assert not inspect.iscoroutinefunction(obj.deprecated_method) + assert not inspect.iscoroutinefunction(obj.deprecated_method) @pytest.mark.asyncio async def test_deprecated_async_method() -> None: """Test deprecated async method.""" - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") - obj = ClassWithDeprecatedMethods() - assert ( - await obj.deprecated_async_method() == "This is a deprecated async method." - ) - assert len(warning_list) == 1 - warning = warning_list[0].message - assert str(warning) == ( - "The function `deprecated_async_method` was deprecated in " - "LangChain 2.0.0 and will be removed in 3.0.0" - ) + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") + obj = ClassWithDeprecatedMethods() + assert ( + await obj.deprecated_async_method() + == "This is a deprecated async method." + ) + assert len(warning_list) == 1 + warning = warning_list[0].message + assert str(warning) == ( + "The function `deprecated_async_method` was deprecated in " + "LangChain 2.0.0 and will be removed in 3.0.0" + ) - doc = obj.deprecated_method.__doc__ - assert isinstance(doc, str) - assert doc.startswith("[*Deprecated*] original doc") + doc = obj.deprecated_method.__doc__ + assert isinstance(doc, str) + assert doc.startswith("[*Deprecated*] original doc") - assert inspect.iscoroutinefunction(obj.deprecated_async_method) + assert inspect.iscoroutinefunction(obj.deprecated_async_method) def test_deprecated_classmethod() -> None: """Test deprecated classmethod.""" - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") - ClassWithDeprecatedMethods.deprecated_classmethod() - assert len(warning_list) == 1 - warning = warning_list[0].message - assert str(warning) == ( - "The function `deprecated_classmethod` was deprecated in " - "LangChain 2.0.0 and will be removed in 3.0.0" - ) + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") + ClassWithDeprecatedMethods.deprecated_classmethod() + assert len(warning_list) == 1 + warning = warning_list[0].message + assert str(warning) == ( + "The function `deprecated_classmethod` was deprecated in " + "LangChain 2.0.0 and will be removed in 3.0.0" + ) - doc = ClassWithDeprecatedMethods.deprecated_classmethod.__doc__ - assert isinstance(doc, str) - assert doc.startswith("[*Deprecated*] original doc") + doc = ClassWithDeprecatedMethods.deprecated_classmethod.__doc__ + assert isinstance(doc, str) + assert doc.startswith("[*Deprecated*] original doc") def test_deprecated_staticmethod() -> None: """Test deprecated staticmethod.""" - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") - assert ( - ClassWithDeprecatedMethods.deprecated_staticmethod() - == "This is a deprecated staticmethod." - ) - assert len(warning_list) == 1 - warning = warning_list[0].message + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") + assert ( + ClassWithDeprecatedMethods.deprecated_staticmethod() + == "This is a deprecated staticmethod." + ) + assert len(warning_list) == 1 + warning = warning_list[0].message - assert str(warning) == ( - "The function `deprecated_staticmethod` was deprecated in " - "LangChain 2.0.0 and will be removed in 3.0.0" - ) - doc = ClassWithDeprecatedMethods.deprecated_staticmethod.__doc__ - assert isinstance(doc, str) - assert doc.startswith("[*Deprecated*] original doc") + assert str(warning) == ( + "The function `deprecated_staticmethod` was deprecated in " + "LangChain 2.0.0 and will be removed in 3.0.0" + ) + doc = ClassWithDeprecatedMethods.deprecated_staticmethod.__doc__ + assert isinstance(doc, str) + assert doc.startswith("[*Deprecated*] original doc") def test_deprecated_property() -> None: """Test deprecated staticmethod.""" - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") - obj = ClassWithDeprecatedMethods() - assert obj.deprecated_property == "This is a deprecated property." + obj = ClassWithDeprecatedMethods() + assert obj.deprecated_property == "This is a deprecated property." - assert len(warning_list) == 1 - warning = warning_list[0].message + assert len(warning_list) == 1 + warning = warning_list[0].message - assert str(warning) == ( - "The function `deprecated_property` was deprecated in " - "LangChain 2.0.0 and will be removed in 3.0.0" - ) - doc = ClassWithDeprecatedMethods.deprecated_property.__doc__ - assert isinstance(doc, str) - assert doc.startswith("[*Deprecated*] original doc") + assert str(warning) == ( + "The function `deprecated_property` was deprecated in " + "LangChain 2.0.0 and will be removed in 3.0.0" + ) + doc = ClassWithDeprecatedMethods.deprecated_property.__doc__ + assert isinstance(doc, str) + assert doc.startswith("[*Deprecated*] original doc") def test_whole_class_deprecation() -> None: @@ -271,27 +292,28 @@ def test_whole_class_deprecation() -> None: """original doc""" return "This is a deprecated method." - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") - obj = DeprecatedClass() - assert obj.deprecated_method() == "This is a deprecated method." + obj = DeprecatedClass() + assert obj.deprecated_method() == "This is a deprecated method." - assert len(warning_list) == 2 - warning = warning_list[0].message - assert str(warning) == ( - "The class `tests.unit_tests._api.test_deprecation.DeprecatedClass` was " - "deprecated in tests 2.0.0 and will be removed in 3.0.0" - ) + assert len(warning_list) == 2 + warning = warning_list[0].message + assert str(warning) == ( + "The class `tests.unit_tests._api.test_deprecation.DeprecatedClass` was " + "deprecated in tests 2.0.0 and will be removed in 3.0.0" + ) - warning = warning_list[1].message - assert str(warning) == ( - "The function `deprecated_method` was deprecated in " - "LangChain 2.0.0 and will be removed in 3.0.0" - ) - # [*Deprecated*] should be inserted only once: - if obj.__doc__ is not None: - assert obj.__doc__.count("[*Deprecated*]") == 1 + warning = warning_list[1].message + assert str(warning) == ( + "The function `deprecated_method` was deprecated in " + "LangChain 2.0.0 and will be removed in 3.0.0" + ) + # [*Deprecated*] should be inserted only once: + if obj.__doc__ is not None: + assert obj.__doc__.count("[*Deprecated*]") == 1 def test_whole_class_inherited_deprecation() -> None: @@ -326,51 +348,52 @@ def test_whole_class_inherited_deprecation() -> None: """original doc""" return "This is a deprecated method." - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") - obj = DeprecatedClass() - assert obj.deprecated_method() == "This is a deprecated method." + obj = DeprecatedClass() + assert obj.deprecated_method() == "This is a deprecated method." - assert len(warning_list) == 2 - warning = warning_list[0].message - assert str(warning) == ( - "The class `tests.unit_tests._api.test_deprecation.DeprecatedClass` was " - "deprecated in tests 2.0.0 and will be removed in 3.0.0" - ) + assert len(warning_list) == 2 + warning = warning_list[0].message + assert str(warning) == ( + "The class `tests.unit_tests._api.test_deprecation.DeprecatedClass` was " + "deprecated in tests 2.0.0 and will be removed in 3.0.0" + ) - warning = warning_list[1].message - assert str(warning) == ( - "The function `deprecated_method` was deprecated in " - "LangChain 2.0.0 and will be removed in 3.0.0" - ) - # if [*Deprecated*] was inserted only once: - if obj.__doc__ is not None: - assert obj.__doc__.count("[*Deprecated*]") == 1 + warning = warning_list[1].message + assert str(warning) == ( + "The function `deprecated_method` was deprecated in " + "LangChain 2.0.0 and will be removed in 3.0.0" + ) + # if [*Deprecated*] was inserted only once: + if obj.__doc__ is not None: + assert obj.__doc__.count("[*Deprecated*]") == 1 - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") - obj = InheritedDeprecatedClass() - assert obj.deprecated_method() == "This is a deprecated method." + obj = InheritedDeprecatedClass() + assert obj.deprecated_method() == "This is a deprecated method." - assert len(warning_list) == 2 - warning = warning_list[0].message - assert str(warning) == ( - "The class " - "`tests.unit_tests._api.test_deprecation.InheritedDeprecatedClass` " - "was deprecated in tests 2.2.0 and will be removed in 3.2.0" - ) + assert len(warning_list) == 2 + warning = warning_list[0].message + assert str(warning) == ( + "The class " + "`tests.unit_tests._api.test_deprecation.InheritedDeprecatedClass` " + "was deprecated in tests 2.2.0 and will be removed in 3.2.0" + ) - warning = warning_list[1].message - assert str(warning) == ( - "The function `deprecated_method` was deprecated in " - "LangChain 2.2.0 and will be removed in 3.2.0" - ) - # if [*Deprecated*] was inserted only once: - if obj.__doc__ is not None: - assert obj.__doc__.count("[*Deprecated*]") == 1 - assert "[*Deprecated*] Inherited deprecated class." in obj.__doc__ + warning = warning_list[1].message + assert str(warning) == ( + "The function `deprecated_method` was deprecated in " + "LangChain 2.2.0 and will be removed in 3.2.0" + ) + # if [*Deprecated*] was inserted only once: + if obj.__doc__ is not None: + assert obj.__doc__.count("[*Deprecated*]") == 1 + assert "[*Deprecated*] Inherited deprecated class." in obj.__doc__ # Tests with pydantic models @@ -383,17 +406,18 @@ class MyModel(BaseModel): def test_deprecated_method_pydantic() -> None: """Test deprecated method.""" - with warnings.catch_warnings(record=True) as warning_list: - warnings.simplefilter("always") - obj = MyModel() - assert obj.deprecated_method() == "This is a deprecated method." - assert len(warning_list) == 1 - warning = warning_list[0].message - assert str(warning) == ( - "The function `deprecated_method` was deprecated in " - "LangChain 2.0.0 and will be removed in 3.0.0" - ) + with surface_internal_warnings(): + with warnings.catch_warnings(record=True) as warning_list: + warnings.simplefilter("always") + obj = MyModel() + assert obj.deprecated_method() == "This is a deprecated method." + assert len(warning_list) == 1 + warning = warning_list[0].message + assert str(warning) == ( + "The function `deprecated_method` was deprecated in " + "LangChain 2.0.0 and will be removed in 3.0.0" + ) - doc = obj.deprecated_method.__doc__ - assert isinstance(doc, str) - assert doc.startswith("[*Deprecated*] original doc") + doc = obj.deprecated_method.__doc__ + assert isinstance(doc, str) + assert doc.startswith("[*Deprecated*] original doc") diff --git a/libs/core/tests/unit_tests/_api/test_imports.py b/libs/core/tests/unit_tests/_api/test_imports.py index 474e959f79f..2812de8b01f 100644 --- a/libs/core/tests/unit_tests/_api/test_imports.py +++ b/libs/core/tests/unit_tests/_api/test_imports.py @@ -12,6 +12,7 @@ EXPECTED_ALL = [ "warn_deprecated", "as_import_path", "get_relative_path", + "caller_aware_warn", ] diff --git a/libs/core/tests/unit_tests/prompts/test_chat.py b/libs/core/tests/unit_tests/prompts/test_chat.py index 0f14605f409..6571960bd2a 100644 --- a/libs/core/tests/unit_tests/prompts/test_chat.py +++ b/libs/core/tests/unit_tests/prompts/test_chat.py @@ -246,15 +246,14 @@ def test_chat_valid_infer_variables() -> None: def test_chat_from_role_strings() -> None: """Test instantiation of chat template from role strings.""" - with pytest.warns(LangChainPendingDeprecationWarning): - template = ChatPromptTemplate.from_role_strings( - [ - ("system", "You are a bot."), - ("assistant", "hello!"), - ("human", "{question}"), - ("other", "{quack}"), - ] - ) + template = ChatPromptTemplate.from_role_strings( + [ + ("system", "You are a bot."), + ("assistant", "hello!"), + ("human", "{question}"), + ("other", "{quack}"), + ] + ) messages = template.format_messages(question="How are you?", quack="duck") assert messages == [ diff --git a/libs/langchain/langchain/__init__.py b/libs/langchain/langchain/__init__.py index dad447585e4..e09c85f98e8 100644 --- a/libs/langchain/langchain/__init__.py +++ b/libs/langchain/langchain/__init__.py @@ -1,10 +1,12 @@ # ruff: noqa: E402 """Main entrypoint into package.""" -import warnings from importlib import metadata from typing import Any, Optional -from langchain_core._api.deprecation import surface_langchain_deprecation_warnings +from langchain_core._api.deprecation import ( + caller_aware_warn, + surface_langchain_deprecation_warnings, +) try: __version__ = metadata.version(__package__) @@ -26,13 +28,13 @@ def _warn_on_import(name: str, replacement: Optional[str] = None) -> None: return if replacement: - warnings.warn( + caller_aware_warn( f"Importing {name} from langchain root module is no longer supported. " - f"Please use {replacement} instead." + f"Please use {replacement} instead.", ) else: - warnings.warn( - f"Importing {name} from langchain root module is no longer supported." + caller_aware_warn( + f"Importing {name} from langchain root module is no longer supported.", ) diff --git a/libs/langchain/langchain/agents/agent_toolkits/__init__.py b/libs/langchain/langchain/agents/agent_toolkits/__init__.py index e718a66c311..b9bb738f6c2 100644 --- a/libs/langchain/langchain/agents/agent_toolkits/__init__.py +++ b/libs/langchain/langchain/agents/agent_toolkits/__init__.py @@ -17,7 +17,7 @@ import warnings from pathlib import Path from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain_core._api.path import as_import_path from langchain.agents.agent_toolkits.conversational_retrieval.openai_functions import ( @@ -61,13 +61,12 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing this agent toolkit from langchain is deprecated. Importing it " "from langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.agent_toolkits import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(agent_toolkits, name) diff --git a/libs/langchain/langchain/callbacks/__init__.py b/libs/langchain/langchain/callbacks/__init__.py index 80d9671fde3..39a2319da00 100644 --- a/libs/langchain/langchain/callbacks/__init__.py +++ b/libs/langchain/langchain/callbacks/__init__.py @@ -9,7 +9,7 @@ import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain_core.callbacks import ( StdOutCallbackHandler, StreamingStdOutCallbackHandler, @@ -34,15 +34,13 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing this callback from langchain is deprecated. Importing it from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.callbacks import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) - return getattr(callbacks, name) diff --git a/libs/langchain/langchain/chat_models/__init__.py b/libs/langchain/langchain/chat_models/__init__.py index 69639536203..2a40e316ec4 100644 --- a/libs/langchain/langchain/chat_models/__init__.py +++ b/libs/langchain/langchain/chat_models/__init__.py @@ -16,9 +16,8 @@ an interface where "chat messages" are the inputs and outputs. AIMessage, BaseMessage, HumanMessage """ # noqa: E501 -import warnings -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain.utils.interactive_env import is_interactive_env @@ -28,13 +27,12 @@ def __getattr__(name: str) -> None: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing chat models from langchain is deprecated. Importing from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.chat_models import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(chat_models, name) diff --git a/libs/langchain/langchain/docstore/__init__.py b/libs/langchain/langchain/docstore/__init__.py index 6be963a63c0..0501640f644 100644 --- a/libs/langchain/langchain/docstore/__init__.py +++ b/libs/langchain/langchain/docstore/__init__.py @@ -17,7 +17,7 @@ The **Docstore** is a simplified version of the Document Loader. import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain.utils.interactive_env import is_interactive_env @@ -27,13 +27,12 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing docstores from langchain is deprecated. Importing from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.docstore import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(docstore, name) diff --git a/libs/langchain/langchain/document_loaders/__init__.py b/libs/langchain/langchain/document_loaders/__init__.py index 4e816f7d354..efb251060e9 100644 --- a/libs/langchain/langchain/document_loaders/__init__.py +++ b/libs/langchain/langchain/document_loaders/__init__.py @@ -17,7 +17,7 @@ import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain.utils.interactive_env import is_interactive_env @@ -33,17 +33,16 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing document loaders from langchain is deprecated. Importing from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.document_loaders import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) if name in _old_to_new_name: - warnings.warn( + caller_aware_warn( f"Using legacy class name {name}, use {_old_to_new_name[name]} instead." ) name = _old_to_new_name[name] diff --git a/libs/langchain/langchain/document_transformers/__init__.py b/libs/langchain/langchain/document_transformers/__init__.py index 1704bb2c8d5..2c02718658e 100644 --- a/libs/langchain/langchain/document_transformers/__init__.py +++ b/libs/langchain/langchain/document_transformers/__init__.py @@ -14,10 +14,9 @@ Document """ # noqa: E501 -import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain.utils.interactive_env import is_interactive_env @@ -27,13 +26,12 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing document transformers from langchain is deprecated. Importing " "from langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.document_transformers import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(document_transformers, name) diff --git a/libs/langchain/langchain/embeddings/__init__.py b/libs/langchain/langchain/embeddings/__init__.py index 785308e71c4..5dc9c328a5e 100644 --- a/libs/langchain/langchain/embeddings/__init__.py +++ b/libs/langchain/langchain/embeddings/__init__.py @@ -15,7 +15,7 @@ import logging import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain.embeddings.cache import CacheBackedEmbeddings from langchain.utils.interactive_env import is_interactive_env @@ -26,13 +26,12 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing embeddings from langchain is deprecated. Importing from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.embeddings import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(embeddings, name) diff --git a/libs/langchain/langchain/llms/__init__.py b/libs/langchain/langchain/llms/__init__.py index 87268883687..464e47a104d 100644 --- a/libs/langchain/langchain/llms/__init__.py +++ b/libs/langchain/langchain/llms/__init__.py @@ -20,7 +20,7 @@ access to the large language model (**LLM**) APIs and services. import warnings from typing import Any, Callable, Dict, Type -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain_core.language_models.llms import BaseLLM from langchain.utils.interactive_env import is_interactive_env @@ -545,13 +545,12 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing LLMs from langchain is deprecated. Importing from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.llms import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) if name == "type_to_cls_dict": diff --git a/libs/langchain/langchain/memory/chat_message_histories/__init__.py b/libs/langchain/langchain/memory/chat_message_histories/__init__.py index 627d6eadd47..9b259546d88 100644 --- a/libs/langchain/langchain/memory/chat_message_histories/__init__.py +++ b/libs/langchain/langchain/memory/chat_message_histories/__init__.py @@ -1,7 +1,6 @@ -import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain.utils.interactive_env import is_interactive_env @@ -11,15 +10,13 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing chat message histories from langchain is deprecated. Importing " "from langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.chat_message_histories import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) - return getattr(chat_message_histories, name) diff --git a/libs/langchain/langchain/retrievers/__init__.py b/libs/langchain/langchain/retrievers/__init__.py index 43e286cee8a..b8a1d028a42 100644 --- a/libs/langchain/langchain/retrievers/__init__.py +++ b/libs/langchain/langchain/retrievers/__init__.py @@ -20,7 +20,7 @@ the backbone of a retriever, but there are other types of retrievers as well. import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain.retrievers.contextual_compression import ContextualCompressionRetriever from langchain.retrievers.ensemble import EnsembleRetriever @@ -43,13 +43,12 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing this retriever from langchain is deprecated. Importing it from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.retrievers import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(retrievers, name) diff --git a/libs/langchain/langchain/storage/__init__.py b/libs/langchain/langchain/storage/__init__.py index aae71c5e902..7dafac443e7 100644 --- a/libs/langchain/langchain/storage/__init__.py +++ b/libs/langchain/langchain/storage/__init__.py @@ -8,7 +8,7 @@ The primary goal of these storages is to support implementation of caching. import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain.storage._lc_store import create_kv_docstore, create_lc_store from langchain.storage.encoder_backed import EncoderBackedStore @@ -22,13 +22,12 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing stores from langchain is deprecated. Importing from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.storage import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(storage, name) diff --git a/libs/langchain/langchain/tools/__init__.py b/libs/langchain/langchain/tools/__init__.py index c96f8db95a7..407a369b90c 100644 --- a/libs/langchain/langchain/tools/__init__.py +++ b/libs/langchain/langchain/tools/__init__.py @@ -19,7 +19,7 @@ tool for the job. import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain_core.tools import BaseTool, StructuredTool, Tool, tool from langchain.utils.interactive_env import is_interactive_env @@ -60,14 +60,13 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing tools from langchain is deprecated. Importing from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.tools import {name}`.\n\n" "To install langchain-community run " "`pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(tools, name) diff --git a/libs/langchain/langchain/utilities/__init__.py b/libs/langchain/langchain/utilities/__init__.py index fce438aea39..88d73e6b08e 100644 --- a/libs/langchain/langchain/utilities/__init__.py +++ b/libs/langchain/langchain/utilities/__init__.py @@ -11,7 +11,7 @@ from langchain_community.utilities.requests import ( RequestsWrapper, TextRequestsWrapper, ) -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain.utils.interactive_env import is_interactive_env @@ -21,13 +21,12 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing this utility from langchain is deprecated. Importing it from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.utilities import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(utilities, name) diff --git a/libs/langchain/langchain/vectorstores/__init__.py b/libs/langchain/langchain/vectorstores/__init__.py index 359949dac12..b4b530e68b5 100644 --- a/libs/langchain/langchain/vectorstores/__init__.py +++ b/libs/langchain/langchain/vectorstores/__init__.py @@ -21,7 +21,7 @@ and retrieve the data that are 'most similar' to the embedded query. import warnings from typing import Any -from langchain_core._api import LangChainDeprecationWarning +from langchain_core._api import caller_aware_warn from langchain_core.vectorstores import VectorStore from langchain.utils.interactive_env import is_interactive_env @@ -32,13 +32,12 @@ def __getattr__(name: str) -> Any: # If not in interactive env, raise warning. if not is_interactive_env(): - warnings.warn( + caller_aware_warn( "Importing vector stores from langchain is deprecated. Importing from " "langchain will no longer be supported as of langchain==0.2.0. " "Please import from langchain-community instead:\n\n" f"`from langchain_community.vectorstores import {name}`.\n\n" "To install langchain-community run `pip install -U langchain-community`.", - category=LangChainDeprecationWarning, ) return getattr(vectorstores, name)