lfx-nightly 0.2.0.dev26__py3-none-any.whl → 0.2.1.dev7__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (85) hide show
  1. lfx/_assets/component_index.json +1 -1
  2. lfx/base/agents/agent.py +9 -4
  3. lfx/base/agents/altk_base_agent.py +16 -3
  4. lfx/base/agents/altk_tool_wrappers.py +1 -1
  5. lfx/base/agents/utils.py +4 -0
  6. lfx/base/composio/composio_base.py +78 -41
  7. lfx/base/data/base_file.py +14 -4
  8. lfx/base/data/cloud_storage_utils.py +156 -0
  9. lfx/base/data/docling_utils.py +191 -65
  10. lfx/base/data/storage_utils.py +109 -0
  11. lfx/base/datastax/astradb_base.py +75 -64
  12. lfx/base/mcp/util.py +2 -2
  13. lfx/base/models/__init__.py +11 -1
  14. lfx/base/models/anthropic_constants.py +21 -12
  15. lfx/base/models/google_generative_ai_constants.py +33 -9
  16. lfx/base/models/model_metadata.py +6 -0
  17. lfx/base/models/ollama_constants.py +196 -30
  18. lfx/base/models/openai_constants.py +37 -10
  19. lfx/base/models/unified_models.py +1123 -0
  20. lfx/base/models/watsonx_constants.py +36 -0
  21. lfx/base/tools/component_tool.py +2 -9
  22. lfx/cli/commands.py +6 -1
  23. lfx/cli/run.py +65 -409
  24. lfx/cli/script_loader.py +13 -3
  25. lfx/components/__init__.py +0 -3
  26. lfx/components/composio/github_composio.py +1 -1
  27. lfx/components/cuga/cuga_agent.py +39 -27
  28. lfx/components/data_source/api_request.py +4 -2
  29. lfx/components/docling/__init__.py +45 -11
  30. lfx/components/docling/chunk_docling_document.py +3 -1
  31. lfx/components/docling/docling_inline.py +39 -49
  32. lfx/components/docling/export_docling_document.py +3 -1
  33. lfx/components/elastic/opensearch_multimodal.py +215 -57
  34. lfx/components/files_and_knowledge/file.py +439 -39
  35. lfx/components/files_and_knowledge/ingestion.py +8 -0
  36. lfx/components/files_and_knowledge/retrieval.py +10 -0
  37. lfx/components/files_and_knowledge/save_file.py +123 -53
  38. lfx/components/ibm/watsonx.py +7 -1
  39. lfx/components/input_output/chat_output.py +7 -1
  40. lfx/components/langchain_utilities/tool_calling.py +14 -6
  41. lfx/components/llm_operations/batch_run.py +80 -25
  42. lfx/components/llm_operations/lambda_filter.py +33 -6
  43. lfx/components/llm_operations/llm_conditional_router.py +39 -7
  44. lfx/components/llm_operations/structured_output.py +38 -12
  45. lfx/components/models/__init__.py +16 -74
  46. lfx/components/models_and_agents/agent.py +51 -201
  47. lfx/components/models_and_agents/embedding_model.py +185 -339
  48. lfx/components/models_and_agents/language_model.py +54 -318
  49. lfx/components/models_and_agents/mcp_component.py +58 -9
  50. lfx/components/ollama/ollama.py +9 -4
  51. lfx/components/ollama/ollama_embeddings.py +2 -1
  52. lfx/components/openai/openai_chat_model.py +1 -1
  53. lfx/components/processing/__init__.py +0 -3
  54. lfx/components/vllm/__init__.py +37 -0
  55. lfx/components/vllm/vllm.py +141 -0
  56. lfx/components/vllm/vllm_embeddings.py +110 -0
  57. lfx/custom/custom_component/custom_component.py +8 -6
  58. lfx/custom/directory_reader/directory_reader.py +5 -2
  59. lfx/graph/utils.py +64 -18
  60. lfx/inputs/__init__.py +2 -0
  61. lfx/inputs/input_mixin.py +54 -0
  62. lfx/inputs/inputs.py +115 -0
  63. lfx/interface/initialize/loading.py +42 -12
  64. lfx/io/__init__.py +2 -0
  65. lfx/run/__init__.py +5 -0
  66. lfx/run/base.py +494 -0
  67. lfx/schema/data.py +1 -1
  68. lfx/schema/image.py +28 -19
  69. lfx/schema/message.py +19 -3
  70. lfx/services/interfaces.py +5 -0
  71. lfx/services/manager.py +5 -4
  72. lfx/services/mcp_composer/service.py +45 -13
  73. lfx/services/settings/auth.py +18 -11
  74. lfx/services/settings/base.py +12 -24
  75. lfx/services/settings/constants.py +2 -0
  76. lfx/services/storage/local.py +37 -0
  77. lfx/services/storage/service.py +19 -0
  78. lfx/utils/constants.py +1 -0
  79. lfx/utils/image.py +29 -11
  80. lfx/utils/validate_cloud.py +14 -3
  81. {lfx_nightly-0.2.0.dev26.dist-info → lfx_nightly-0.2.1.dev7.dist-info}/METADATA +5 -2
  82. {lfx_nightly-0.2.0.dev26.dist-info → lfx_nightly-0.2.1.dev7.dist-info}/RECORD +84 -78
  83. lfx/components/processing/dataframe_to_toolset.py +0 -259
  84. {lfx_nightly-0.2.0.dev26.dist-info → lfx_nightly-0.2.1.dev7.dist-info}/WHEEL +0 -0
  85. {lfx_nightly-0.2.0.dev26.dist-info → lfx_nightly-0.2.1.dev7.dist-info}/entry_points.txt +0 -0
@@ -1,259 +0,0 @@
1
- """DataFrame to Toolset Component.
2
-
3
- This component converts each row of a DataFrame into a callable tool/action within a toolset.
4
- Each row becomes a tool where the action name comes from one column and the content/response
5
- comes from another column.
6
- """
7
-
8
- from __future__ import annotations
9
-
10
- import re
11
- from typing import TYPE_CHECKING
12
-
13
- from langchain.tools import StructuredTool
14
- from pydantic import BaseModel, create_model
15
-
16
- from lfx.base.langchain_utilities.model import LCToolComponent
17
- from lfx.field_typing.constants import Tool
18
- from lfx.io import HandleInput, Output, StrInput
19
- from lfx.schema.data import Data
20
- from lfx.schema.dataframe import DataFrame
21
- from lfx.schema.message import Message
22
-
23
- if TYPE_CHECKING:
24
- from lfx.field_typing.constants import Tool
25
-
26
-
27
- class DataFrameToToolsetComponent(LCToolComponent):
28
- """Component that converts DataFrame rows into a toolset with multiple callable actions."""
29
-
30
- display_name = "DataFrame to Toolset"
31
- description = "Convert each row of a DataFrame into a callable tool/action in a toolset."
32
- icon = "wrench"
33
- name = "DataFrameToToolset"
34
-
35
- inputs = [
36
- HandleInput(
37
- name="dataframe",
38
- display_name="DataFrame",
39
- input_types=["DataFrame"],
40
- info="DataFrame where each row will become a tool/action",
41
- required=True,
42
- ),
43
- StrInput(
44
- name="tool_name_column",
45
- display_name="Tool Name Column",
46
- info="Column with tool names",
47
- required=True,
48
- ),
49
- StrInput(
50
- name="tool_output_column",
51
- display_name="Tool Output Column",
52
- info="Column with tool outputs/responses",
53
- required=True,
54
- ),
55
- ]
56
-
57
- outputs = [
58
- Output(display_name="Tools", name="tools", method="build_tools"),
59
- Output(display_name="Message", name="message", method="get_message"),
60
- ]
61
-
62
- def __init__(self, **kwargs):
63
- super().__init__(**kwargs)
64
- self._tools_cache: list[Tool] = []
65
- self._action_data: dict[str, dict[str, str]] = {}
66
-
67
- def _sanitize_tool_name(self, name: str) -> str:
68
- """Sanitize tool name to match required format '^[a-zA-Z0-9_-]+$'."""
69
- # Replace any non-alphanumeric characters (except _ and -) with underscores
70
- sanitized = re.sub(r"[^a-zA-Z0-9_-]", "_", str(name))
71
- # Ensure it starts with a letter or underscore
72
- if sanitized and not sanitized[0].isalpha() and sanitized[0] != "_":
73
- sanitized = f"tool_{sanitized}"
74
- return sanitized or "unnamed_tool"
75
-
76
- def _prepare_action_data(self) -> None:
77
- """Prepare action data from DataFrame."""
78
- # Check if dataframe exists and is valid
79
- if not hasattr(self, "dataframe") or self.dataframe is None:
80
- self._action_data = {}
81
- return
82
-
83
- if not isinstance(self.dataframe, DataFrame):
84
- self._action_data = {}
85
- return
86
-
87
- if not hasattr(self.dataframe, "columns"):
88
- self._action_data = {}
89
- return
90
-
91
- # Check if column names are provided
92
- if not self.tool_name_column or not self.tool_output_column:
93
- self._action_data = {}
94
- return
95
-
96
- if self.tool_name_column not in self.dataframe.columns:
97
- msg = (
98
- f"Tool name column '{self.tool_name_column}' not found in DataFrame columns: "
99
- f"{list(self.dataframe.columns)}"
100
- )
101
- raise ValueError(msg)
102
-
103
- if self.tool_output_column not in self.dataframe.columns:
104
- msg = (
105
- f"Tool output column '{self.tool_output_column}' not found in DataFrame columns: "
106
- f"{list(self.dataframe.columns)}"
107
- )
108
- raise ValueError(msg)
109
-
110
- # Clear previous data
111
- self._action_data = {}
112
-
113
- # Process each row to create action mappings
114
- for _, row in self.dataframe.iterrows():
115
- action_name = str(row[self.tool_name_column]).strip()
116
- content = str(row[self.tool_output_column]).strip()
117
-
118
- if action_name and content:
119
- sanitized_name = self._sanitize_tool_name(action_name)
120
- self._action_data[sanitized_name] = {
121
- "original_name": action_name,
122
- "content": content,
123
- "sanitized_name": sanitized_name,
124
- }
125
-
126
- def _create_action_function(self, action_name: str, content: str):
127
- """Create a function for a specific action that returns the content."""
128
-
129
- def action_function(**kwargs) -> str:
130
- # You could extend this to use kwargs to modify the content
131
- # For now, just return the stored content
132
- self.log(kwargs) # TODO: Coming soon: implement arguments to modify content
133
- return content
134
-
135
- action_function.__name__ = f"execute_{action_name}"
136
- action_function.__doc__ = f"Execute {action_name} action and return the associated content."
137
- return action_function
138
-
139
- def build_tools(self) -> list[Tool]:
140
- """Build the toolset from DataFrame data."""
141
- # Handle case where inputs are not ready
142
- if not hasattr(self, "dataframe") or self.dataframe is None:
143
- return []
144
-
145
- self._prepare_action_data()
146
-
147
- if not self._action_data:
148
- return []
149
-
150
- tools_description_preview_length = 100
151
- tools_description_content_length = 200
152
-
153
- tools = []
154
-
155
- for sanitized_name, action_info in self._action_data.items():
156
- original_name = action_info["original_name"]
157
- content = action_info["content"]
158
-
159
- # Create a simple schema for this tool (no parameters needed)
160
- # But we could extend this to accept parameters if needed
161
- tool_schema = create_model(
162
- f"{sanitized_name}Schema",
163
- __base__=BaseModel,
164
- # Add parameters here if you want the tools to accept inputs
165
- # For now, keeping it simple with no parameters
166
- )
167
-
168
- # Create the tool function
169
- tool_function = self._create_action_function(sanitized_name, content)
170
-
171
- # Create the StructuredTool
172
- tool = StructuredTool(
173
- name=sanitized_name,
174
- description=(
175
- f"Execute {original_name} action. Returns: "
176
- f"{content[:tools_description_preview_length]}"
177
- f"{'...' if len(content) > tools_description_preview_length else ''}"
178
- ),
179
- func=tool_function,
180
- args_schema=tool_schema,
181
- handle_tool_error=True,
182
- tags=[sanitized_name],
183
- metadata={
184
- "display_name": original_name,
185
- "display_description": f"Action: {original_name}",
186
- "original_name": original_name,
187
- "content_preview": content[:tools_description_content_length],
188
- },
189
- )
190
-
191
- tools.append(tool)
192
-
193
- self._tools_cache = tools
194
- return tools
195
-
196
- def build_tool(self) -> Tool:
197
- """Build a single tool (for compatibility with LCToolComponent)."""
198
- tools = self.build_tools()
199
- if not tools:
200
- # Return a placeholder tool when no data is available
201
- def placeholder_function(**kwargs) -> str:
202
- self.log(kwargs) # TODO: Coming soon: implement arguments to modify content
203
- return "No tools available. Please connect a DataFrame with appropriate columns."
204
-
205
- return StructuredTool(
206
- name="placeholder_tool",
207
- description="Placeholder tool - waiting for DataFrame input",
208
- func=placeholder_function,
209
- args_schema=create_model("PlaceholderSchema", __base__=BaseModel),
210
- )
211
-
212
- # Return the first tool, or create a composite tool
213
- return tools[0]
214
-
215
- def get_message(self) -> Message:
216
- """Get a message describing the created toolset."""
217
- # Handle case where inputs are not ready
218
- if not hasattr(self, "dataframe") or self.dataframe is None:
219
- return Message(text="Waiting for DataFrame input...")
220
-
221
- self._prepare_action_data()
222
-
223
- if not self._action_data:
224
- return Message(text="No tools were created. Please check your DataFrame and column selections.")
225
-
226
- tool_count = len(self._action_data)
227
- tool_names = [info["original_name"] for info in self._action_data.values()]
228
-
229
- message_text = f"Created toolset with {tool_count} tools:\n"
230
- for i, name in enumerate(tool_names, 1):
231
- message_text += f"{i}. {name}\n"
232
-
233
- return Message(text=message_text)
234
-
235
- def run_model(self) -> list[Data]:
236
- """Run the model and return tool information as Data objects."""
237
- # Handle case where inputs are not ready
238
- if not hasattr(self, "dataframe") or self.dataframe is None:
239
- return [Data(data={"status": "Waiting for DataFrame input"})]
240
-
241
- tools = self.build_tools()
242
-
243
- if not tools:
244
- return [Data(data={"status": "No tools created. Check DataFrame and column selections."})]
245
-
246
- results = []
247
- for tool in tools:
248
- tool_data = {
249
- "tool_name": tool.name,
250
- "display_name": tool.metadata.get("display_name", tool.name)
251
- if hasattr(tool, "metadata")
252
- else tool.name,
253
- "description": tool.description,
254
- "original_name": tool.metadata.get("original_name", "") if hasattr(tool, "metadata") else "",
255
- "content_preview": tool.metadata.get("content_preview", "") if hasattr(tool, "metadata") else "",
256
- }
257
- results.append(Data(data=tool_data))
258
-
259
- return results