feat: private built_object added, implement get_function
This commit is contained in:
parent
b67c7d6442
commit
c6ebbe3517
2 changed files with 34 additions and 7 deletions
|
|
@ -1,8 +1,9 @@
|
||||||
|
from langflow.utils import util
|
||||||
from pydantic import BaseModel, validator
|
from pydantic import BaseModel, validator
|
||||||
from langchain.agents import tool
|
from langchain.agents import tool
|
||||||
|
|
||||||
|
|
||||||
class PythonFunction(BaseModel):
|
class Function(BaseModel):
|
||||||
code: str
|
code: str
|
||||||
|
|
||||||
# Validate the function
|
# Validate the function
|
||||||
|
|
@ -11,3 +12,13 @@ class PythonFunction(BaseModel):
|
||||||
# Validate with LangChain's tool decorator
|
# Validate with LangChain's tool decorator
|
||||||
tool(v)
|
tool(v)
|
||||||
return v
|
return v
|
||||||
|
|
||||||
|
def get_function(self):
|
||||||
|
"""Get the function"""
|
||||||
|
return util.eval_function(self.code)
|
||||||
|
|
||||||
|
|
||||||
|
class PythonFunction(Function):
|
||||||
|
"""Python function"""
|
||||||
|
|
||||||
|
code: str
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,6 @@
|
||||||
|
from copy import deepcopy
|
||||||
import types
|
import types
|
||||||
from typing import Dict, List, Union
|
from typing import Any, Dict, List, Union
|
||||||
from langflow.interface import loading
|
from langflow.interface import loading
|
||||||
from langflow.utils import payload, util
|
from langflow.utils import payload, util
|
||||||
from langflow.interface.listing import ALL_TYPES_DICT
|
from langflow.interface.listing import ALL_TYPES_DICT
|
||||||
|
|
@ -11,6 +12,8 @@ class Node:
|
||||||
self._data = data
|
self._data = data
|
||||||
self.edges: List[Edge] = []
|
self.edges: List[Edge] = []
|
||||||
self._parse_data()
|
self._parse_data()
|
||||||
|
self._built_object = None
|
||||||
|
self._built = False
|
||||||
|
|
||||||
def _parse_data(self) -> None:
|
def _parse_data(self) -> None:
|
||||||
self.data = self._data["data"]
|
self.data = self._data["data"]
|
||||||
|
|
@ -94,7 +97,7 @@ class Node:
|
||||||
# Add _type to params
|
# Add _type to params
|
||||||
self.params = params
|
self.params = params
|
||||||
|
|
||||||
def build(self):
|
def _build(self):
|
||||||
# The params dict is used to build the module
|
# The params dict is used to build the module
|
||||||
# it contains values and keys that point to nodes which
|
# it contains values and keys that point to nodes which
|
||||||
# have their own params dict
|
# have their own params dict
|
||||||
|
|
@ -113,7 +116,12 @@ class Node:
|
||||||
result = value.build()
|
result = value.build()
|
||||||
# If the key is "func", then we need to use the run method
|
# If the key is "func", then we need to use the run method
|
||||||
if key == "func" and not isinstance(result, types.FunctionType):
|
if key == "func" and not isinstance(result, types.FunctionType):
|
||||||
result = result.run
|
# func can be PythonFunction(code='\ndef upper_case(text: str) -> str:\n return text.upper()\n')
|
||||||
|
# so we need to check if there is an attribute called run
|
||||||
|
if hasattr(result, "run"):
|
||||||
|
result = result.run # type: ignore
|
||||||
|
elif hasattr(result, "get_function"):
|
||||||
|
result = result.get_function() # type: ignore
|
||||||
self.params[key] = result
|
self.params[key] = result
|
||||||
elif isinstance(value, list) and all(
|
elif isinstance(value, list) and all(
|
||||||
isinstance(node, Node) for node in value
|
isinstance(node, Node) for node in value
|
||||||
|
|
@ -123,19 +131,27 @@ class Node:
|
||||||
# Get the class from LANGCHAIN_TYPES_DICT
|
# Get the class from LANGCHAIN_TYPES_DICT
|
||||||
# and instantiate it with the params
|
# and instantiate it with the params
|
||||||
# and return the instance
|
# and return the instance
|
||||||
instance = None
|
|
||||||
for base_type, value in ALL_TYPES_DICT.items():
|
for base_type, value in ALL_TYPES_DICT.items():
|
||||||
if base_type == "tools":
|
if base_type == "tools":
|
||||||
value = util.get_tools_dict()
|
value = util.get_tools_dict()
|
||||||
|
|
||||||
if self.node_type in value:
|
if self.node_type in value:
|
||||||
instance = loading.instantiate_class(
|
self._built_object = loading.instantiate_class(
|
||||||
node_type=self.node_type,
|
node_type=self.node_type,
|
||||||
base_type=base_type,
|
base_type=base_type,
|
||||||
params=self.params,
|
params=self.params,
|
||||||
)
|
)
|
||||||
break
|
break
|
||||||
return instance
|
|
||||||
|
if self._built_object is None:
|
||||||
|
raise ValueError(f"Node type {self.node_type} not found")
|
||||||
|
|
||||||
|
self._built = True
|
||||||
|
|
||||||
|
def build(self, force: bool = False) -> Any:
|
||||||
|
if not self._built or force:
|
||||||
|
self._build()
|
||||||
|
return deepcopy(self._built_object)
|
||||||
|
|
||||||
def add_edge(self, edge: "Edge") -> None:
|
def add_edge(self, edge: "Edge") -> None:
|
||||||
self.edges.append(edge)
|
self.edges.append(edge)
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue