feat: ability to run flow without langflow server (#7507)

* flow-runner

* flow-runner

* flow-runner - fix lint

* Update flow_runner.py

* [autofix.ci] apply automated fixes

* Update flow_runner.py

* [autofix.ci] apply automated fixes

* Update flow_runner.py

* [autofix.ci] apply automated fixes

* Update flow_runner.py

* [autofix.ci] apply automated fixes

* CR

* Add docs and require sessionid

* fix lint

* [autofix.ci] apply automated fixes

* refactor: simplify flow ID handling and update class docstring

* refactor: update flow runner import to experimental version

* removed obsolete test

* remove test that use io

* remove another io test

---------

Co-authored-by: autofix-ci[bot] <114827586+autofix-ci[bot]@users.noreply.github.com>
Co-authored-by: Edwin Jose <edwin.jose@datastax.com>
Co-authored-by: Jordan Frazier <jordan.frazier@datastax.com>
Co-authored-by: Jordan Frazier <122494242+jordanrfrazier@users.noreply.github.com>
Co-authored-by: Gabriel Luiz Freitas Almeida <gabriel@langflow.org>
This commit is contained in:
Bar Nuri 2025-04-29 08:59:00 +03:00 • committed by GitHub
commit e50476b30a
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
4 changed files with 256 additions and 0 deletions

View file

@ -0,0 +1,84 @@
from uuid import uuid4
import pytest
from langflow.services.flow.flow_runner import LangflowRunnerExperimental
@pytest.fixture
def sample_flow_dict():
return {
"data": {
"nodes": [],
"edges": [],
}
}
@pytest.fixture
def flow_runner():
return LangflowRunnerExperimental()
@pytest.mark.asyncio
async def test_database_exists_check(flow_runner):
"""Test database exists check functionality."""
result = await flow_runner.database_exists_check()
assert isinstance(result, bool)
@pytest.mark.asyncio
async def test_get_flow_dict_from_dict(flow_runner, sample_flow_dict):
"""Test loading flow from a dictionary."""
result = await flow_runner.get_flow_dict(sample_flow_dict)
assert result == sample_flow_dict
@pytest.mark.asyncio
async def test_get_flow_dict_invalid_input(flow_runner):
"""Test loading flow with invalid input type."""
pattern = r"Input must be a file path .* or a JSON object .*"
with pytest.raises(TypeError, match=pattern):
await flow_runner.get_flow_dict(123)
@pytest.mark.asyncio
async def test_run_with_dict_input(flow_runner, sample_flow_dict):
"""Test running flow with dictionary input."""
session_id = str(uuid4())
input_value = "test input"
result = await flow_runner.run(
flow=sample_flow_dict,
input_value=input_value,
session_id=session_id,
)
assert result is not None
@pytest.mark.asyncio
async def test_run_with_different_input_types(flow_runner, sample_flow_dict):
"""Test running flow with different input and output types."""
session_id = str(uuid4())
test_cases = [
("text input", "text", "text"),
("chat input", "chat", "chat"),
("test input", "chat", "text"),
]
for input_value, input_type, output_type in test_cases:
result = await flow_runner.run(
flow=sample_flow_dict,
input_value=input_value,
input_type=input_type,
output_type=output_type,
session_id=session_id,
)
assert result is not None
@pytest.mark.asyncio
async def test_initialize_database(flow_runner):
"""Test database initialization."""
flow_runner.should_initialize_db = True
await flow_runner.init_db_if_needed()
assert not flow_runner.should_initialize_db