Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

core: Bump ruff version to 0.9 #29201

Merged
merged 2 commits into from
Jan 22, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion libs/core/langchain_core/_api/beta_decorator.py
Original file line number Diff line number Diff line change
Expand Up @@ -214,7 +214,7 @@ def finalize(wrapper: Callable[..., Any], new_doc: str) -> T:
old_doc = inspect.cleandoc(old_doc or "").strip("\n") or ""
components = [message, addendum]
details = " ".join([component.strip() for component in components if component])
new_doc = f".. beta::\n" f" {details}\n\n" f"{old_doc}\n"
new_doc = f".. beta::\n {details}\n\n{old_doc}\n"

if inspect.iscoroutinefunction(obj):
finalized = finalize(awarning_emitting_wrapper, new_doc)
Expand Down
1 change: 1 addition & 0 deletions libs/core/langchain_core/_api/deprecation.py
Original file line number Diff line number Diff line change
Expand Up @@ -238,6 +238,7 @@ def finalize(wrapper: Callable[..., Any], new_doc: str) -> T:
exclude=obj.exclude,
),
)

elif isinstance(obj, FieldInfoV2):
wrapped = None
if not _obj_type:
Expand Down
3 changes: 1 addition & 2 deletions libs/core/langchain_core/callbacks/manager.py
Original file line number Diff line number Diff line change
Expand Up @@ -385,8 +385,7 @@ async def _ahandle_event_for_handler(
)
except Exception as e:
logger.warning(
f"Error in {handler.__class__.__name__}.{event_name} callback:"
f" {repr(e)}"
f"Error in {handler.__class__.__name__}.{event_name} callback: {repr(e)}"
)
if handler.raise_error:
raise e
Expand Down
3 changes: 2 additions & 1 deletion libs/core/langchain_core/indexing/in_memory.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import operator
import uuid
from collections.abc import Sequence
from typing import Any, Optional, cast
Expand Down Expand Up @@ -80,5 +81,5 @@ def _get_relevant_documents(
count = document.page_content.count(query)
counts_by_doc.append((document, count))

counts_by_doc.sort(key=lambda x: x[1], reverse=True)
counts_by_doc.sort(key=operator.itemgetter(1), reverse=True)
return [doc.model_copy() for doc, count in counts_by_doc[: self.top_k]]
2 changes: 1 addition & 1 deletion libs/core/langchain_core/language_models/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -390,7 +390,7 @@ def get_num_tokens_from_messages(
"Counting tokens in tool schemas is not yet supported. Ignoring tools.",
stacklevel=2,
)
return sum([self.get_num_tokens(get_buffer_string([m])) for m in messages])
return sum(self.get_num_tokens(get_buffer_string([m])) for m in messages)

@classmethod
def _all_required_field_names(cls) -> set:
Expand Down
3 changes: 1 addition & 2 deletions libs/core/langchain_core/language_models/llms.py
Original file line number Diff line number Diff line change
Expand Up @@ -347,8 +347,7 @@ def _get_ls_params(
"""Get standard params for tracing."""
# get default provider from class name
default_provider = self.__class__.__name__
if default_provider.endswith("LLM"):
default_provider = default_provider[:-3]
default_provider = default_provider.removesuffix("LLM")
default_provider = default_provider.lower()

ls_params = LangSmithParams(ls_provider=default_provider, ls_model_type="llm")
Expand Down
10 changes: 8 additions & 2 deletions libs/core/langchain_core/messages/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -1008,7 +1008,10 @@ def convert_to_openai_messages(
)
raise ValueError(err)
content.append(
{"type": "image_url", "image_url": block["image_url"]}
{
"type": "image_url",
"image_url": block["image_url"],
}
)
# Anthropic and Bedrock converse format
elif (block.get("type") == "image") or "image" in block:
Expand Down Expand Up @@ -1127,7 +1130,10 @@ def convert_to_openai_messages(
)
raise ValueError(msg)
content.append(
{"type": "text", "text": json.dumps(block["json"])}
{
"type": "text",
"text": json.dumps(block["json"]),
}
)
elif (
block.get("type") == "guard_content"
Expand Down
2 changes: 1 addition & 1 deletion libs/core/langchain_core/output_parsers/list.py
Original file line number Diff line number Diff line change
Expand Up @@ -227,7 +227,7 @@ class MarkdownListOutputParser(ListOutputParser):

def get_format_instructions(self) -> str:
"""Return the format instructions for the Markdown list output."""
return "Your response should be a markdown list, " "eg: `- foo\n- bar\n- baz`"
return "Your response should be a markdown list, eg: `- foo\n- bar\n- baz`"

def parse(self, text: str) -> list[str]:
"""Parse the output of an LLM call.
Expand Down
4 changes: 1 addition & 3 deletions libs/core/langchain_core/prompts/chat.py
Original file line number Diff line number Diff line change
Expand Up @@ -1398,9 +1398,7 @@ def _create_template_from_message_type(
elif len(template) == 2 and isinstance(template[1], bool):
var_name_wrapped, is_optional = template
if not isinstance(var_name_wrapped, str):
msg = (
"Expected variable name to be a string." f" Got: {var_name_wrapped}"
)
msg = f"Expected variable name to be a string. Got: {var_name_wrapped}"
raise ValueError(msg)
if var_name_wrapped[0] != "{" or var_name_wrapped[-1] != "}":
msg = (
Expand Down
2 changes: 1 addition & 1 deletion libs/core/langchain_core/pydantic_v1/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

from langchain_core._api.deprecation import warn_deprecated

## Create namespaces for pydantic v1 and v2.
# Create namespaces for pydantic v1 and v2.
# This code must stay at the top of the file before other modules may
# attempt to import pydantic since it adds pydantic_v1 and pydantic_v2 to sys.modules.
#
Expand Down
4 changes: 2 additions & 2 deletions libs/core/langchain_core/rate_limiters.py
Original file line number Diff line number Diff line change
Expand Up @@ -248,14 +248,14 @@ async def aacquire(self, *, blocking: bool = True) -> bool:
if not blocking:
return self._consume()

while not self._consume():
while not self._consume(): # noqa: ASYNC110
# This code ignores the ASYNC110 warning which is a false positive in this
# case.
# There is no external actor that can mark that the Event is done
# since the tokens are managed by the rate limiter itself.
# It needs to wake up to re-fill the tokens.
# https://docs.astral.sh/ruff/rules/async-busy-wait/
await asyncio.sleep(self.check_every_n_seconds) # ruff: noqa: ASYNC110
await asyncio.sleep(self.check_every_n_seconds)
return True


Expand Down
30 changes: 15 additions & 15 deletions libs/core/langchain_core/runnables/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -2862,7 +2862,7 @@ def config_specs(self) -> list[ConfigurableFieldSpec]:
# calculate context dependencies
specs_by_pos = groupby(
[tup for tup in all_specs if tup[0].id.startswith(CONTEXT_CONFIG_PREFIX)],
lambda x: x[1],
itemgetter(1),
)
next_deps: set[str] = set()
deps_by_pos: dict[int, set[str]] = {}
Expand Down Expand Up @@ -3006,7 +3006,7 @@ def invoke(
for i, step in enumerate(self.steps):
# mark each step as a child run
config = patch_config(
config, callbacks=run_manager.get_child(f"seq:step:{i+1}")
config, callbacks=run_manager.get_child(f"seq:step:{i + 1}")
)
context = copy_context()
context.run(_set_config_context, config)
Expand Down Expand Up @@ -3046,7 +3046,7 @@ async def ainvoke(
for i, step in enumerate(self.steps):
# mark each step as a child run
config = patch_config(
config, callbacks=run_manager.get_child(f"seq:step:{i+1}")
config, callbacks=run_manager.get_child(f"seq:step:{i + 1}")
)
context = copy_context()
context.run(_set_config_context, config)
Expand Down Expand Up @@ -3131,7 +3131,8 @@ def batch(
[
# each step a child run of the corresponding root run
patch_config(
config, callbacks=rm.get_child(f"seq:step:{stepidx+1}")
config,
callbacks=rm.get_child(f"seq:step:{stepidx + 1}"),
)
for i, (rm, config) in enumerate(zip(run_managers, configs))
if i not in failed_inputs_map
Expand Down Expand Up @@ -3163,7 +3164,7 @@ def batch(
[
# each step a child run of the corresponding root run
patch_config(
config, callbacks=rm.get_child(f"seq:step:{i+1}")
config, callbacks=rm.get_child(f"seq:step:{i + 1}")
)
for rm, config in zip(run_managers, configs)
],
Expand Down Expand Up @@ -3260,7 +3261,8 @@ async def abatch(
[
# each step a child run of the corresponding root run
patch_config(
config, callbacks=rm.get_child(f"seq:step:{stepidx+1}")
config,
callbacks=rm.get_child(f"seq:step:{stepidx + 1}"),
)
for i, (rm, config) in enumerate(zip(run_managers, configs))
if i not in failed_inputs_map
Expand Down Expand Up @@ -3292,7 +3294,7 @@ async def abatch(
[
# each step a child run of the corresponding root run
patch_config(
config, callbacks=rm.get_child(f"seq:step:{i+1}")
config, callbacks=rm.get_child(f"seq:step:{i + 1}")
)
for rm, config in zip(run_managers, configs)
],
Expand Down Expand Up @@ -3339,7 +3341,7 @@ def _transform(
final_pipeline = cast(Iterator[Output], input)
for idx, step in enumerate(steps):
config = patch_config(
config, callbacks=run_manager.get_child(f"seq:step:{idx+1}")
config, callbacks=run_manager.get_child(f"seq:step:{idx + 1}")
)
if idx == 0:
final_pipeline = step.transform(final_pipeline, config, **kwargs)
Expand Down Expand Up @@ -3368,7 +3370,7 @@ async def _atransform(
for idx, step in enumerate(steps):
config = patch_config(
config,
callbacks=run_manager.get_child(f"seq:step:{idx+1}"),
callbacks=run_manager.get_child(f"seq:step:{idx + 1}"),
)
if idx == 0:
final_pipeline = step.atransform(final_pipeline, config, **kwargs)
Expand Down Expand Up @@ -4400,7 +4402,7 @@ def get_input_schema(
if dict_keys := get_function_first_arg_dict_keys(func):
return create_model_v2(
self.get_name("Input"),
field_definitions={key: (Any, ...) for key in dict_keys},
field_definitions=dict.fromkeys(dict_keys, (Any, ...)),
)

return super().get_input_schema(config)
Expand Down Expand Up @@ -4524,7 +4526,7 @@ def __eq__(self, other: Any) -> bool:
def __repr__(self) -> str:
"""A string representation of this Runnable."""
if hasattr(self, "func") and isinstance(self.func, itemgetter):
return f"RunnableLambda({str(self.func)[len('operator.'):]})"
return f"RunnableLambda({str(self.func)[len('operator.') :]})"
elif hasattr(self, "func"):
return f"RunnableLambda({get_lambda_source(self.func) or '...'})"
elif hasattr(self, "afunc"):
Expand Down Expand Up @@ -4785,8 +4787,7 @@ def _transform(
recursion_limit = config["recursion_limit"]
if recursion_limit <= 0:
msg = (
f"Recursion limit reached when invoking "
f"{self} with input {final}."
f"Recursion limit reached when invoking {self} with input {final}."
)
raise RecursionError(msg)
for chunk in output.stream(
Expand Down Expand Up @@ -4909,8 +4910,7 @@ async def f(*args, **kwargs): # type: ignore[no-untyped-def]
recursion_limit = config["recursion_limit"]
if recursion_limit <= 0:
msg = (
f"Recursion limit reached when invoking "
f"{self} with input {final}."
f"Recursion limit reached when invoking {self} with input {final}."
)
raise RecursionError(msg)
async for chunk in output.astream(
Expand Down
4 changes: 2 additions & 2 deletions libs/core/langchain_core/runnables/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -110,8 +110,8 @@ class RunnableConfig(TypedDict, total=False):
DEFAULT_RECURSION_LIMIT = 25


var_child_runnable_config = ContextVar(
"child_runnable_config", default=RunnableConfig()
var_child_runnable_config: ContextVar[RunnableConfig | None] = ContextVar(
"child_runnable_config", default=None
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

)


Expand Down
15 changes: 9 additions & 6 deletions libs/core/langchain_core/runnables/graph_ascii.py
Original file line number Diff line number Diff line change
Expand Up @@ -242,17 +242,20 @@ def draw_ascii(vertices: Mapping[str, str], edges: Sequence[LangEdge]) -> str:
"""
# NOTE: coordinates might me negative, so we need to shift
# everything to the positive plane before we actually draw it.
xlist = []
ylist = []
xlist: list[float] = []
ylist: list[float] = []

sug = _build_sugiyama_layout(vertices, edges)

for vertex in sug.g.sV:
# NOTE: moving boxes w/2 to the left
xlist.append(vertex.view.xy[0] - vertex.view.w / 2.0)
xlist.append(vertex.view.xy[0] + vertex.view.w / 2.0)
ylist.append(vertex.view.xy[1])
ylist.append(vertex.view.xy[1] + vertex.view.h)
xlist.extend(
(
vertex.view.xy[0] - vertex.view.w / 2.0,
vertex.view.xy[0] + vertex.view.w / 2.0,
)
)
ylist.extend((vertex.view.xy[1], vertex.view.xy[1] + vertex.view.h))

for edge in sug.g.sE:
for x, y in edge.view._pts:
Expand Down
4 changes: 1 addition & 3 deletions libs/core/langchain_core/runnables/history.py
Original file line number Diff line number Diff line change
Expand Up @@ -590,9 +590,7 @@ def _merge_configs(self, *configs: Optional[RunnableConfig]) -> RunnableConfig:

if missing_keys and parameter_names:
example_input = {self.input_messages_key: "foo"}
example_configurable = {
missing_key: "[your-value-here]" for missing_key in missing_keys
}
example_configurable = dict.fromkeys(missing_keys, "[your-value-here]")
example_config = {"configurable": example_configurable}
msg = (
f"Missing keys {sorted(missing_keys)} in config['configurable'] "
Expand Down
4 changes: 2 additions & 2 deletions libs/core/langchain_core/runnables/retry.py
Original file line number Diff line number Diff line change
Expand Up @@ -248,7 +248,7 @@ def pending(iterable: list[U]) -> list[U]:
result = cast(list[Output], [e] * len(inputs))

outputs: list[Union[Output, Exception]] = []
for idx, _ in enumerate(inputs):
for idx in range(len(inputs)):
if idx in results_map:
outputs.append(results_map[idx])
else:
Expand Down Expand Up @@ -314,7 +314,7 @@ def pending(iterable: list[U]) -> list[U]:
result = cast(list[Output], [e] * len(inputs))

outputs: list[Union[Output, Exception]] = []
for idx, _ in enumerate(inputs):
for idx in range(len(inputs)):
if idx in results_map:
outputs.append(results_map[idx])
else:
Expand Down
6 changes: 2 additions & 4 deletions libs/core/langchain_core/runnables/router.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
from __future__ import annotations

from collections.abc import AsyncIterator, Iterator, Mapping
from itertools import starmap
from typing import (
Any,
Callable,
Expand Down Expand Up @@ -189,10 +190,7 @@ async def ainvoke(
configs = get_config_list(config, len(inputs))
return await gather_with_concurrency(
configs[0].get("max_concurrency"),
*(
ainvoke(runnable, input, config)
for runnable, input, config in zip(runnables, actual_inputs, configs)
),
*starmap(ainvoke, zip(runnables, actual_inputs, configs)),
)

def stream(
Expand Down
2 changes: 1 addition & 1 deletion libs/core/langchain_core/tracers/event_stream.py
Original file line number Diff line number Diff line change
Expand Up @@ -863,7 +863,7 @@ async def _astream_events_implementation_v1(
tags=log_entry["tags"],
metadata=log_entry["metadata"],
data=data,
parent_ids=[], # Not supported in v1
parent_ids=[], # Not supported in v1
)

# Finally, we take care of the streaming output from the root chain
Expand Down
4 changes: 2 additions & 2 deletions libs/core/langchain_core/tracers/stdout.py
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,7 @@ def _on_llm_error(self, run: Run) -> None:
def _on_tool_start(self, run: Run) -> None:
crumbs = self.get_breadcrumbs(run)
self.function_callback(
f'{get_colored_text("[tool/start]", color="green")} '
f"{get_colored_text('[tool/start]', color='green')} "
+ get_bolded_text(f"[{crumbs}] Entering Tool run with input:\n")
+ f'"{run.inputs["input"].strip()}"'
)
Expand All @@ -169,7 +169,7 @@ def _on_tool_end(self, run: Run) -> None:
crumbs = self.get_breadcrumbs(run)
if run.outputs:
self.function_callback(
f'{get_colored_text("[tool/end]", color="blue")} '
f"{get_colored_text('[tool/end]', color='blue')} "
+ get_bolded_text(
f"[{crumbs}] [{elapsed(run)}] Exiting Tool run with output:\n"
)
Expand Down
2 changes: 1 addition & 1 deletion libs/core/langchain_core/utils/formatting.py
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ def validate_input_variables(
Raises:
ValueError: If any input variables are not used in the format string.
"""
dummy_inputs = {input_variable: "foo" for input_variable in input_variables}
dummy_inputs = dict.fromkeys(input_variables, "foo")
super().format(format_string, **dummy_inputs)


Expand Down
7 changes: 3 additions & 4 deletions libs/core/langchain_core/utils/mustache.py
Original file line number Diff line number Diff line change
Expand Up @@ -122,8 +122,7 @@ def parse_tag(template: str, l_del: str, r_del: str) -> tuple[tuple[str, str], s
ChevronError: If the tag is unclosed.
ChevronError: If the set delimiter tag is unclosed.
"""
global _CURRENT_LINE
global _LAST_TAG_LINE
global _CURRENT_LINE, _LAST_TAG_LINE

tag_types = {
"!": "comment",
Expand All @@ -140,7 +139,7 @@ def parse_tag(template: str, l_del: str, r_del: str) -> tuple[tuple[str, str], s
try:
tag, template = template.split(r_del, 1)
except ValueError as e:
msg = "unclosed tag " f"at line {_CURRENT_LINE}"
msg = f"unclosed tag at line {_CURRENT_LINE}"
raise ChevronError(msg) from e

# Find the type meaning of the first character
Expand All @@ -161,7 +160,7 @@ def parse_tag(template: str, l_del: str, r_del: str) -> tuple[tuple[str, str], s

# Otherwise we should complain
else:
msg = "unclosed set delimiter tag\n" f"at line {_CURRENT_LINE}"
msg = f"unclosed set delimiter tag\nat line {_CURRENT_LINE}"
raise ChevronError(msg)

elif (
Expand Down
Loading
Loading