Merge branch 'dev' into zustand/io/migration

This commit is contained in:
cristhianzl 2024-02-15 18:19:33 -03:00
commit 7e42b52d8c
18 changed files with 137 additions and 54 deletions

11
.github/dependabot.yml vendored Normal file
View file

@ -0,0 +1,11 @@
# Set update schedule for GitHub Actions
version: 2
updates:
- package-ecosystem: "github-actions"
directory: "/"
schedule:
# Check for updates to GitHub Actions every week
interval: "monthly"

View file

@ -16,10 +16,10 @@ jobs:
OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }} OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }}
steps: steps:
- name: Checkout code - name: Checkout code
uses: actions/checkout@v2 uses: actions/checkout@v4
- name: Cache Docker layers - name: Cache Docker layers
uses: actions/cache@v2 uses: actions/cache@v4
with: with:
path: /tmp/.buildx-cache path: /tmp/.buildx-cache
key: ${{ runner.os }}-buildx-${{ github.sha }} key: ${{ runner.os }}-buildx-${{ github.sha }}

View file

@ -30,11 +30,11 @@ jobs:
steps: steps:
- name: Checkout repository - name: Checkout repository
uses: actions/checkout@v3 uses: actions/checkout@v4
# Initializes the CodeQL tools for scanning. # Initializes the CodeQL tools for scanning.
- name: Initialize CodeQL - name: Initialize CodeQL
uses: github/codeql-action/init@v2 uses: github/codeql-action/init@v3
with: with:
languages: ${{ matrix.language }} languages: ${{ matrix.language }}
# If you wish to specify custom queries, you can do so here or in a config file. # If you wish to specify custom queries, you can do so here or in a config file.
@ -48,7 +48,7 @@ jobs:
# Autobuild attempts to build any compiled languages (C/C++, C#, Go, Java, or Swift). # Autobuild attempts to build any compiled languages (C/C++, C#, Go, Java, or Swift).
# If this step fails, then you should remove it and run the build manually (see below) # If this step fails, then you should remove it and run the build manually (see below)
- name: Autobuild - name: Autobuild
uses: github/codeql-action/autobuild@v2 uses: github/codeql-action/autobuild@v3
# ℹ️ Command-line programs to run using the OS shell. # ℹ️ Command-line programs to run using the OS shell.
# 📚 See https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idstepsrun # 📚 See https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idstepsrun
@ -61,6 +61,6 @@ jobs:
# ./location_of_script_within_repo/buildscript.sh # ./location_of_script_within_repo/buildscript.sh
- name: Perform CodeQL Analysis - name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@v2 uses: github/codeql-action/analyze@v3
with: with:
category: "/language:${{matrix.language}}" category: "/language:${{matrix.language}}"

View file

@ -12,8 +12,8 @@ jobs:
name: Deploy to GitHub Pages name: Deploy to GitHub Pages
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@v3 - uses: actions/checkout@v4
- uses: actions/setup-node@v3 - uses: actions/setup-node@v4
with: with:
node-version: 18 node-version: 18
cache: npm cache: npm

View file

@ -17,12 +17,12 @@ jobs:
- "3.9" - "3.9"
- "3.10" - "3.10"
steps: steps:
- uses: actions/checkout@v3 - uses: actions/checkout@v4
- name: Install poetry - name: Install poetry
run: | run: |
pipx install poetry==$POETRY_VERSION pipx install poetry==$POETRY_VERSION
- name: Set up Python ${{ matrix.python-version }} - name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v4 uses: actions/setup-python@v5
with: with:
python-version: ${{ matrix.python-version }} python-version: ${{ matrix.python-version }}
cache: poetry cache: poetry

View file

@ -18,11 +18,11 @@ jobs:
if: ${{ (github.event.pull_request.merged == true) && contains(github.event.pull_request.labels.*.name, 'pre-release') }} if: ${{ (github.event.pull_request.merged == true) && contains(github.event.pull_request.labels.*.name, 'pre-release') }}
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@v3 - uses: actions/checkout@v4
- name: Install poetry - name: Install poetry
run: pipx install poetry==$POETRY_VERSION run: pipx install poetry==$POETRY_VERSION
- name: Set up Python 3.10 - name: Set up Python 3.10
uses: actions/setup-python@v4 uses: actions/setup-python@v5
with: with:
python-version: "3.10" python-version: "3.10"
cache: "poetry" cache: "poetry"

View file

@ -17,11 +17,11 @@ jobs:
if: ${{ (github.event.pull_request.merged == true) && contains(github.event.pull_request.labels.*.name, 'Release') }} if: ${{ (github.event.pull_request.merged == true) && contains(github.event.pull_request.labels.*.name, 'Release') }}
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@v3 - uses: actions/checkout@v4
- name: Install poetry - name: Install poetry
run: pipx install poetry==$POETRY_VERSION run: pipx install poetry==$POETRY_VERSION
- name: Set up Python 3.10 - name: Set up Python 3.10
uses: actions/setup-python@v4 uses: actions/setup-python@v5
with: with:
python-version: "3.10" python-version: "3.10"
cache: "poetry" cache: "poetry"

View file

@ -19,11 +19,11 @@ jobs:
env: env:
OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }} OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }}
steps: steps:
- uses: actions/checkout@v3 - uses: actions/checkout@v4
- name: Install poetry - name: Install poetry
run: pipx install poetry==$POETRY_VERSION run: pipx install poetry==$POETRY_VERSION
- name: Set up Python ${{ matrix.python-version }} - name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v4 uses: actions/setup-python@v5
with: with:
python-version: ${{ matrix.python-version }} python-version: ${{ matrix.python-version }}
cache: "poetry" cache: "poetry"

View file

@ -22,6 +22,8 @@ services:
dockerfile: ./cdk.Dockerfile dockerfile: ./cdk.Dockerfile
args: args:
- BACKEND_URL=http://backend:7860 - BACKEND_URL=http://backend:7860
depends_on:
- backend
environment: environment:
- VITE_PROXY_TARGET=http://backend:7860 - VITE_PROXY_TARGET=http://backend:7860
ports: ports:

View file

@ -1,6 +1,6 @@
[tool.poetry] [tool.poetry]
name = "langflow" name = "langflow"
version = "0.6.7a1" version = "0.6.7a2"
description = "A Python package with a built-in web application" description = "A Python package with a built-in web application"
authors = ["Logspace <contact@logspace.ai>"] authors = ["Logspace <contact@logspace.ai>"]
maintainers = [ maintainers = [

View file

@ -0,0 +1,42 @@
from langflow import CustomComponent
from typing import Optional, Dict
from langchain_community.embeddings.huggingface import HuggingFaceInferenceAPIEmbeddings
class HuggingFaceInferenceAPIEmbeddingsComponent(CustomComponent):
display_name = "HuggingFaceInferenceAPIEmbeddings"
description = "HuggingFace sentence_transformers embedding models, API version."
documentation = (
"https://github.com/huggingface/text-embeddings-inference"
)
def build_config(self):
return {
"api_key": {"display_name": "API Key", "password": True, "advanced": True},
"api_url": {"display_name": "API URL", "advanced": True},
"model_name": {"display_name": "Model Name"},
"cache_folder": {"display_name": "Cache Folder", "advanced": True},
"encode_kwargs": {"display_name": "Encode Kwargs", "advanced": True, "field_type": "dict"},
"model_kwargs": {"display_name": "Model Kwargs", "field_type": "dict", "advanced": True},
"multi_process": {"display_name": "Multi Process", "advanced": True},
}
def build(
self,
api_key: Optional[str] = "",
api_url: str = "http://localhost:8080",
model_name: str = "BAAI/bge-large-en-v1.5",
cache_folder: Optional[str] = None,
encode_kwargs: Optional[Dict] = {},
model_kwargs: Optional[Dict] = {},
multi_process: bool = False,
) -> HuggingFaceInferenceAPIEmbeddings:
return HuggingFaceInferenceAPIEmbeddings(
api_key=api_key,
api_url=api_url,
model_name=model_name,
cache_folder=cache_folder,
encode_kwargs=encode_kwargs,
model_kwargs=model_kwargs,
multi_process=multi_process,
)

View file

@ -15,7 +15,7 @@ class QdrantComponent(CustomComponent):
return { return {
"documents": {"display_name": "Documents"}, "documents": {"display_name": "Documents"},
"embedding": {"display_name": "Embedding"}, "embedding": {"display_name": "Embedding"},
"api_key": {"display_name": "API Key", "password": True}, "api_key": {"display_name": "API Key", "password": True, "advanced": True},
"collection_name": {"display_name": "Collection Name"}, "collection_name": {"display_name": "Collection Name"},
"content_payload_key": {"display_name": "Content Payload Key", "advanced": True}, "content_payload_key": {"display_name": "Content Payload Key", "advanced": True},
"distance_func": {"display_name": "Distance Function", "advanced": True}, "distance_func": {"display_name": "Distance Function", "advanced": True},
@ -36,7 +36,7 @@ class QdrantComponent(CustomComponent):
def build( def build(
self, self,
embedding: Embeddings, embedding: Embeddings,
documents: List[Document], documents: Optional[Document] = None,
api_key: Optional[str] = None, api_key: Optional[str] = None,
collection_name: Optional[str] = None, collection_name: Optional[str] = None,
content_payload_key: str = "page_content", content_payload_key: str = "page_content",
@ -44,7 +44,7 @@ class QdrantComponent(CustomComponent):
grpc_port: Optional[int] = 6334, grpc_port: Optional[int] = 6334,
host: Optional[str] = None, host: Optional[str] = None,
https: bool = False, https: bool = False,
location: str = ":memory:", location: Optional[str] = None,
metadata_payload_key: str = "metadata", metadata_payload_key: str = "metadata",
path: Optional[str] = None, path: Optional[str] = None,
port: Optional[int] = 6333, port: Optional[int] = 6333,
@ -54,23 +54,50 @@ class QdrantComponent(CustomComponent):
timeout: Optional[float] = None, timeout: Optional[float] = None,
url: Optional[str] = None, url: Optional[str] = None,
) -> Union[VectorStore, Qdrant, BaseRetriever]: ) -> Union[VectorStore, Qdrant, BaseRetriever]:
return Qdrant.from_documents( if documents is None:
documents=documents, from qdrant_client import QdrantClient
embedding=embedding, client = QdrantClient(
api_key=api_key, location=location,
collection_name=collection_name, url=host,
content_payload_key=content_payload_key, port=port,
distance_func=distance_func, grpc_port=grpc_port,
grpc_port=grpc_port, https=https,
host=host, prefix=prefix,
https=https, timeout=timeout,
location=location, prefer_grpc=prefer_grpc,
metadata_payload_key=metadata_payload_key, metadata_payload_key=metadata_payload_key,
path=path, content_payload_key=content_payload_key,
port=port, api_key=api_key,
prefer_grpc=prefer_grpc, collection_name=collection_name,
prefix=prefix, host=host,
search_kwargs=search_kwargs, path=path,
timeout=timeout, )
url=url, vs = Qdrant(client=client,
) collection_name=collection_name,
embeddings=embedding,
search_kwargs=search_kwargs,
distance_func=distance_func,
)
return vs
else:
vs = Qdrant.from_documents(
documents=documents,
embedding=embedding,
api_key=api_key,
collection_name=collection_name,
content_payload_key=content_payload_key,
distance_func=distance_func,
grpc_port=grpc_port,
host=host,
https=https,
location=location,
metadata_payload_key=metadata_payload_key,
path=path,
port=port,
prefer_grpc=prefer_grpc,
prefix=prefix,
search_kwargs=search_kwargs,
timeout=timeout,
url=url,
)
return vs

View file

@ -7,8 +7,6 @@ from typing import Any, Dict, List, Optional, Union
from uuid import UUID from uuid import UUID
from fastapi import HTTPException from fastapi import HTTPException
from loguru import logger
from langflow.field_typing.range_spec import RangeSpec from langflow.field_typing.range_spec import RangeSpec
from langflow.interface.custom.code_parser.utils import extract_inner_type from langflow.interface.custom.code_parser.utils import extract_inner_type
from langflow.interface.custom.custom_component import CustomComponent from langflow.interface.custom.custom_component import CustomComponent
@ -22,6 +20,7 @@ from langflow.template.field.base import TemplateField
from langflow.template.frontend_node.custom_components import CustomComponentFrontendNode from langflow.template.frontend_node.custom_components import CustomComponentFrontendNode
from langflow.utils import validate from langflow.utils import validate
from langflow.utils.util import get_base_classes from langflow.utils.util import get_base_classes
from loguru import logger
def add_output_types(frontend_node: CustomComponentFrontendNode, return_types: List[str]): def add_output_types(frontend_node: CustomComponentFrontendNode, return_types: List[str]):
@ -151,9 +150,6 @@ def add_extra_fields(frontend_node, field_config, function_args):
if not function_args: if not function_args:
return return
# sort function_args which is a list of dicts
function_args.sort(key=lambda x: x["name"])
for extra_field in function_args: for extra_field in function_args:
if "name" not in extra_field or extra_field["name"] == "self": if "name" not in extra_field or extra_field["name"] == "self":
continue continue

View file

@ -2,10 +2,13 @@ from typing import TYPE_CHECKING, List, Union
from langchain.agents.agent import AgentExecutor from langchain.agents.agent import AgentExecutor
from langchain.callbacks.base import BaseCallbackHandler from langchain.callbacks.base import BaseCallbackHandler
from loguru import logger
from langflow.api.v1.callback import AsyncStreamingLLMCallbackHandler, StreamingLLMCallbackHandler from langflow.api.v1.callback import AsyncStreamingLLMCallbackHandler, StreamingLLMCallbackHandler
from langflow.processing.process import fix_memory_inputs, format_actions from langflow.processing.process import fix_memory_inputs, format_actions
from langflow.services.deps import get_plugins_service from langflow.services.deps import get_plugins_service
from loguru import logger from langflow.processing.process import fix_memory_inputs, format_actions
from langflow.services.deps import get_plugins_service
if TYPE_CHECKING: if TYPE_CHECKING:
from langfuse.callback import CallbackHandler # type: ignore from langfuse.callback import CallbackHandler # type: ignore
@ -28,13 +31,12 @@ def setup_callbacks(sync, trace_id, **kwargs):
def get_langfuse_callback(trace_id): def get_langfuse_callback(trace_id):
from langflow.services.deps import get_plugins_service from langflow.services.deps import get_plugins_service
from langfuse.callback import CreateTrace
logger.debug("Initializing langfuse callback") logger.debug("Initializing langfuse callback")
if langfuse := get_plugins_service().get("langfuse"): if langfuse := get_plugins_service().get("langfuse"):
logger.debug("Langfuse credentials found") logger.debug("Langfuse credentials found")
try: try:
trace = langfuse.trace(CreateTrace(name="langflow-" + trace_id, id=trace_id)) trace = langfuse.trace(name="langflow-" + trace_id, id=trace_id)
return trace.getNewHandler() return trace.getNewHandler()
except Exception as exc: except Exception as exc:
logger.error(f"Error initializing langfuse callback: {exc}") logger.error(f"Error initializing langfuse callback: {exc}")

View file

@ -64,14 +64,13 @@ class LangfusePlugin(CallbackPlugin):
def get_callback(self, _id: Optional[str] = None): def get_callback(self, _id: Optional[str] = None):
if _id is None: if _id is None:
_id = "default" _id = "default"
from langfuse.callback import CreateTrace # type: ignore
logger.debug("Initializing langfuse callback") logger.debug("Initializing langfuse callback")
try: try:
langfuse_instance = self.get() langfuse_instance = self.get()
if langfuse_instance is not None and hasattr(langfuse_instance, "trace"): if langfuse_instance is not None and hasattr(langfuse_instance, "trace"):
trace = langfuse_instance.trace(CreateTrace(name="langflow-" + _id, id=_id)) trace = langfuse_instance.trace(name="langflow-" + _id, id=_id)
if trace: if trace:
return trace.getNewHandler() return trace.getNewHandler()

View file

@ -99,7 +99,7 @@
"pretty-quick": "^3.1.3", "pretty-quick": "^3.1.3",
"tailwindcss": "^3.3.3", "tailwindcss": "^3.3.3",
"typescript": "^5.2.2", "typescript": "^5.2.2",
"vite": "^4.5.1" "vite": "^4.5.2"
} }
}, },
"node_modules/@adobe/css-tools": { "node_modules/@adobe/css-tools": {

View file

@ -121,6 +121,6 @@
"pretty-quick": "^3.1.3", "pretty-quick": "^3.1.3",
"tailwindcss": "^3.3.3", "tailwindcss": "^3.3.3",
"typescript": "^5.2.2", "typescript": "^5.2.2",
"vite": "^4.5.1" "vite": "^4.5.2"
} }
} }

View file

@ -139,12 +139,16 @@ export function groupByFamily(
}))) })))
); );
}; };
console.log(flow);
if (flow) { if (flow) {
// se existir o flow
for (const node of flow) { for (const node of flow) {
// para cada node do flow
if (node!.data!.node!.flow) break; // não faz nada se o node for um group
const nodeData = node.data; const nodeData = node.data;
const foundNode = checkedNodes.get(nodeData.type); const foundNode = checkedNodes.get(nodeData.type); // verifica se o tipo do node já foi checado
checkedNodes.set(nodeData.type, { checkedNodes.set(nodeData.type, {
hasBaseClassInTemplate: hasBaseClassInTemplate:
foundNode?.hasBaseClassInTemplate || foundNode?.hasBaseClassInTemplate ||
@ -153,7 +157,7 @@ export function groupByFamily(
foundNode?.hasBaseClassInBaseClasses || foundNode?.hasBaseClassInBaseClasses ||
nodeData.node!.base_classes.some((baseClass) => nodeData.node!.base_classes.some((baseClass) =>
baseClassesSet.has(baseClass) baseClassesSet.has(baseClass)
), ), //seta como anterior ou verifica se o node tem base class
displayName: nodeData.node?.display_name, displayName: nodeData.node?.display_name,
}); });
} }