From f92049d5b000594cfa074e8ac54d4648b03e113f Mon Sep 17 00:00:00 2001 From: Zsolnai Csaba Date: Tue, 24 Sep 2024 11:56:48 +0200 Subject: [PATCH 01/25] Added test for get_settings --- tests/app/test_dependencies.py | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 1acfa4b..7b920a0 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -4,13 +4,15 @@ import os from pathlib import Path from typing import AsyncIterator -from unittest.mock import Mock +from unittest.mock import Mock, patch import pytest from httpx import AsyncClient from langchain_openai import ChatOpenAI from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver +from pydantic import SecretStr + from neuroagent.agents import SimpleAgent, SimpleChatAgent from neuroagent.app.dependencies import ( Settings, @@ -28,7 +30,7 @@ get_morphology_feature_tool, get_traces_tool, get_update_kg_hierarchy, - get_user_id, + get_user_id, get_settings, ) from neuroagent.tools import ( ElectrophysFeatureTool, @@ -40,6 +42,18 @@ ) +@patch.dict(os.environ, { + "NEUROAGENT_TOOLS__LITERATURE__URL": "https://localhost1", + "NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL": "https://localhost2", + "NEUROAGENT_KEYCLOAK__USERNAME": "user2", + "NEUROAGENT_KEYCLOAK__PASSWORD": "password2" +}) +def test_get_settings(): + settings = get_settings() + assert settings.tools.literature.url == "https://localhost1" + assert settings.knowledge_graph.url == "https://localhost2/search/query/" + + @pytest.mark.asyncio async def test_get_httpx_client(): request = Mock() From 72b08e7dbf3c506df380d66271ac4e7f1c6a2a07 Mon Sep 17 00:00:00 2001 From: Zsolnai Csaba Date: Tue, 24 Sep 2024 12:01:32 +0200 Subject: [PATCH 02/25] Added tests for test_get_connection_string --- tests/app/test_dependencies.py | 38 ++++++++++++++++++++++++++++++++-- 1 file changed, 36 insertions(+), 2 deletions(-) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 7b920a0..361d872 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -11,7 +11,7 @@ from langchain_openai import ChatOpenAI from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver -from pydantic import SecretStr +from pydantic import SecretStr, Secret from neuroagent.agents import SimpleAgent, SimpleChatAgent from neuroagent.app.dependencies import ( @@ -30,7 +30,7 @@ get_morphology_feature_tool, get_traces_tool, get_update_kg_hierarchy, - get_user_id, get_settings, + get_user_id, get_settings, get_connection_string, ) from neuroagent.tools import ( ElectrophysFeatureTool, @@ -375,3 +375,37 @@ async def test_get_cell_types_kg_hierarchy( ) assert os.path.exists(settings.knowledge_graph.ct_saving_path) + + +def fake_get_settings(): + class MockedDb: + def __init__(self, prefix, user, password, host, port, name): + self.prefix = prefix + self.user = user + self.password = Secret(password) + self.host = host + self.port = port + self.name = name + + class MockedSettings: + def __init__(self, db): + self.db = db + + return [ + MockedSettings(MockedDb("http://", "John", "Doe", "localhost", 5000, "test")), + MockedSettings(MockedDb("", "", "", "", None, None)), + ] + + +def test_get_connection_string_full(): + settings = fake_get_settings()[0] + result = get_connection_string(settings) + assert ( + result == "http://John:Doe@localhost:5000/test" + ), "must return fully formed connection string" + + +def test_get_connection_string_no_prefix(): + settings = fake_get_settings()[1] + result = get_connection_string(settings) + assert result is None, "should return None when prefix is not set" From c9b6f9f1df5d198295551d862cf21c50b0b37d2d Mon Sep 17 00:00:00 2001 From: Zsolnai Csaba Date: Tue, 24 Sep 2024 14:36:42 +0200 Subject: [PATCH 03/25] Added tests for get_engine --- tests/app/test_dependencies.py | 52 ++++++++++++++++++++++++++++++++-- 1 file changed, 50 insertions(+), 2 deletions(-) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 361d872..4fde122 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -11,7 +11,8 @@ from langchain_openai import ChatOpenAI from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver -from pydantic import SecretStr, Secret +from pydantic import Secret +from sqlalchemy.exc import SQLAlchemyError from neuroagent.agents import SimpleAgent, SimpleChatAgent from neuroagent.app.dependencies import ( @@ -30,7 +31,7 @@ get_morphology_feature_tool, get_traces_tool, get_update_kg_hierarchy, - get_user_id, get_settings, get_connection_string, + get_user_id, get_settings, get_connection_string, get_engine, ) from neuroagent.tools import ( ElectrophysFeatureTool, @@ -409,3 +410,50 @@ def test_get_connection_string_no_prefix(): settings = fake_get_settings()[1] result = get_connection_string(settings) assert result is None, "should return None when prefix is not set" + + +@patch('neuroagent.app.dependencies.create_engine') +def test_get_engine(create_engine_mock): + create_engine_mock.return_value = Mock() + + settings = Mock() + settings.db = Mock() + settings.db.prefix = "prefix" + settings.db.password = None + connection_string = "https://localhost" + retval = get_engine( + settings=settings, + connection_string=connection_string + ) + assert retval is not None + + +@patch('neuroagent.app.dependencies.create_engine') +def test_get_engine_no_connection_string(create_engine_mock): + create_engine_mock.return_value = Mock() + + settings = Mock() + settings.db = Mock() + settings.db.prefix = "prefix" + settings.db.password = None + retval = get_engine( + settings=settings, + connection_string=None + ) + assert retval is None + + +@patch('neuroagent.app.dependencies.create_engine') +def test_get_engine_error(create_engine_mock): + create_engine_mock.side_effect = SQLAlchemyError("An error occurred") + + settings = Mock() + settings.db = Mock() + settings.db.prefix = "prefix" + settings.db.password = None + connection_string = "https://localhost" + with pytest.raises(SQLAlchemyError): + get_engine( + settings=settings, + connection_string=connection_string + ) From e1a5cb7ece7c7a622c854836fa479303c467af1e Mon Sep 17 00:00:00 2001 From: Zsolnai Csaba Date: Tue, 24 Sep 2024 15:17:27 +0200 Subject: [PATCH 04/25] Added tests for get_session --- tests/app/test_dependencies.py | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 4fde122..9a766ab 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -7,12 +7,14 @@ from unittest.mock import Mock, patch import pytest +from fastapi import HTTPException from httpx import AsyncClient from langchain_openai import ChatOpenAI from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver from pydantic import Secret from sqlalchemy.exc import SQLAlchemyError +from sqlalchemy.orm import Session from neuroagent.agents import SimpleAgent, SimpleChatAgent from neuroagent.app.dependencies import ( @@ -31,7 +33,7 @@ get_morphology_feature_tool, get_traces_tool, get_update_kg_hierarchy, - get_user_id, get_settings, get_connection_string, get_engine, + get_user_id, get_settings, get_connection_string, get_engine, get_session, ) from neuroagent.tools import ( ElectrophysFeatureTool, @@ -457,3 +459,15 @@ def test_get_engine_error(create_engine_mock): settings=settings, connection_string=connection_string ) + + +@patch('sqlalchemy.orm.Session') +def test_get_session_success(_): + engine = Mock() + result = next(get_session(engine)) + assert isinstance(result, Session) + + +def test_get_session_no_engine(): + with pytest.raises(HTTPException): + next(get_session(None)) From 839a91e820349eb65b91c1767ef35dd503f12db2 Mon Sep 17 00:00:00 2001 From: Zsolnai Csaba Date: Tue, 24 Sep 2024 16:21:56 +0200 Subject: [PATCH 05/25] Added test for process_validation_error --- tests/app/test_dependencies.py | 20 +++++++++++++++- .../{test_basic_tool.py => test_base_tool.py} | 24 +++++++++++++++++-- 2 files changed, 41 insertions(+), 3 deletions(-) rename tests/tools/{test_basic_tool.py => test_base_tool.py} (76%) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 9a766ab..5ff5cc0 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -33,7 +33,7 @@ get_morphology_feature_tool, get_traces_tool, get_update_kg_hierarchy, - get_user_id, get_settings, get_connection_string, get_engine, get_session, + get_user_id, get_settings, get_connection_string, get_engine, get_session, get_kg_token, ) from neuroagent.tools import ( ElectrophysFeatureTool, @@ -471,3 +471,21 @@ def test_get_session_success(_): def test_get_session_no_engine(): with pytest.raises(HTTPException): next(get_session(None)) + + +def test_get_kg_token_with_token(): + settings = Mock() + token = "Test_Token" + result = get_kg_token(settings, token) + assert result == "Test_Token" + + +def test_get_kg_token_with_settings_knowledge_graph_token(): + settings = Mock() + settings.knowledge_graph.use_token = True + settings.knowledge_graph.token.get_secret_value.return_value = "Test_kg_Token" + token = None + + result = get_kg_token(settings, token) + + assert result == "Test_kg_Token" diff --git a/tests/tools/test_basic_tool.py b/tests/tools/test_base_tool.py similarity index 76% rename from tests/tools/test_basic_tool.py rename to tests/tools/test_base_tool.py index fb9ab17..22ec0a7 100644 --- a/tests/tools/test_basic_tool.py +++ b/tests/tools/test_base_tool.py @@ -1,11 +1,13 @@ from typing import Literal, Type +from unittest.mock import Mock +import pytest from langchain_core.language_models.fake_chat_models import FakeMessagesListChatModel from langchain_core.messages import AIMessage, HumanMessage from langchain_core.tools import ToolException from langgraph.prebuilt import create_react_agent -from neuroagent.tools.base_tool import BasicTool -from pydantic import BaseModel +from neuroagent.tools.base_tool import BasicTool, process_validation_error +from pydantic import BaseModel, ValidationError class input_for_test(BaseModel): @@ -103,3 +105,21 @@ def bind_tools(self, functions: list): 'unable to parse string as an integer"}]' ) assert response["messages"][7].content == "fake answer" + + +@pytest.mark.parametrize("title, errors, expected", [ + ("ValidationError", [{"type": "literal_error", "input": "distinct", "loc": ["led"]}], + '[{"Validation error": "Wrong value: provided distinct for input led. Try again and change this problematic input."}]'), + ("ValidationError", [{"type": "missing", "loc": ["led"]}], + '[{"Validation error": "Missing input : led. Try again and add this input."}]'), + ("ValidationError", [{"type": "other_error", "loc": ["led"], "msg": "This is a test error message"}], + '[{"Validation error": "led. This is a test error message"}]'), + ("ValidationError", [{}], + '[{"Validation error": "Error in ValidationError : \'type\'"}]') +]) +def test_process_validation_error(title, errors, expected): + error = Mock() + error.title = title + error.errors.return_value = errors + result = process_validation_error(error) + assert result == expected From d80f1fd428ad92f69762437d6309a14a81d7e5d4 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Wed, 25 Sep 2024 11:20:56 +0200 Subject: [PATCH 06/25] lint --- CHANGELOG.md | 1 + tests/app/test_dependencies.py | 7 ++++++- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index eb751ad..e809514 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -11,6 +11,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Added - Update readme +- Extra unit tests for dependencies.py ### Removed - Github action to create the docs. diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 5ff5cc0..20a6b2e 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -24,16 +24,21 @@ get_brain_region_resolver_tool, get_cell_types_kg_hierarchy, get_chat_agent, + get_connection_string, get_electrophys_feature_tool, + get_engine, get_httpx_client, get_kg_morpho_feature_tool, + get_kg_token, get_language_model, get_literature_tool, get_morpho_tool, get_morphology_feature_tool, + get_session, + get_settings, get_traces_tool, get_update_kg_hierarchy, - get_user_id, get_settings, get_connection_string, get_engine, get_session, get_kg_token, + get_user_id, ) from neuroagent.tools import ( ElectrophysFeatureTool, From cb3f1c6fd810feecea082627ce636e18f79259e4 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Wed, 25 Sep 2024 11:34:07 +0200 Subject: [PATCH 07/25] lint --- tests/app/test_dependencies.py | 45 ++++++++++++++-------------------- tests/tools/test_base_tool.py | 2 +- 2 files changed, 20 insertions(+), 27 deletions(-) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 20a6b2e..66161e2 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -12,10 +12,6 @@ from langchain_openai import ChatOpenAI from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver -from pydantic import Secret -from sqlalchemy.exc import SQLAlchemyError -from sqlalchemy.orm import Session - from neuroagent.agents import SimpleAgent, SimpleChatAgent from neuroagent.app.dependencies import ( Settings, @@ -48,14 +44,20 @@ LiteratureSearchTool, MorphologyFeatureTool, ) +from pydantic import Secret +from sqlalchemy.exc import SQLAlchemyError +from sqlalchemy.orm import Session -@patch.dict(os.environ, { - "NEUROAGENT_TOOLS__LITERATURE__URL": "https://localhost1", - "NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL": "https://localhost2", - "NEUROAGENT_KEYCLOAK__USERNAME": "user2", - "NEUROAGENT_KEYCLOAK__PASSWORD": "password2" -}) +@patch.dict( + os.environ, + { + "NEUROAGENT_TOOLS__LITERATURE__URL": "https://localhost1", + "NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL": "https://localhost2", + "NEUROAGENT_KEYCLOAK__USERNAME": "user2", + "NEUROAGENT_KEYCLOAK__PASSWORD": "password2", + }, +) def test_get_settings(): settings = get_settings() assert settings.tools.literature.url == "https://localhost1" @@ -419,7 +421,7 @@ def test_get_connection_string_no_prefix(): assert result is None, "should return None when prefix is not set" -@patch('neuroagent.app.dependencies.create_engine') +@patch("neuroagent.app.dependencies.create_engine") def test_get_engine(create_engine_mock): create_engine_mock.return_value = Mock() @@ -428,14 +430,11 @@ def test_get_engine(create_engine_mock): settings.db.prefix = "prefix" settings.db.password = None connection_string = "https://localhost" - retval = get_engine( - settings=settings, - connection_string=connection_string - ) + retval = get_engine(settings=settings, connection_string=connection_string) assert retval is not None -@patch('neuroagent.app.dependencies.create_engine') +@patch("neuroagent.app.dependencies.create_engine") def test_get_engine_no_connection_string(create_engine_mock): create_engine_mock.return_value = Mock() @@ -443,14 +442,11 @@ def test_get_engine_no_connection_string(create_engine_mock): settings.db = Mock() settings.db.prefix = "prefix" settings.db.password = None - retval = get_engine( - settings=settings, - connection_string=None - ) + retval = get_engine(settings=settings, connection_string=None) assert retval is None -@patch('neuroagent.app.dependencies.create_engine') +@patch("neuroagent.app.dependencies.create_engine") def test_get_engine_error(create_engine_mock): create_engine_mock.side_effect = SQLAlchemyError("An error occurred") @@ -460,13 +456,10 @@ def test_get_engine_error(create_engine_mock): settings.db.password = None connection_string = "https://localhost" with pytest.raises(SQLAlchemyError): - get_engine( - settings=settings, - connection_string=connection_string - ) + get_engine(settings=settings, connection_string=connection_string) -@patch('sqlalchemy.orm.Session') +@patch("sqlalchemy.orm.Session") def test_get_session_success(_): engine = Mock() result = next(get_session(engine)) diff --git a/tests/tools/test_base_tool.py b/tests/tools/test_base_tool.py index 22ec0a7..7eaaaa7 100644 --- a/tests/tools/test_base_tool.py +++ b/tests/tools/test_base_tool.py @@ -7,7 +7,7 @@ from langchain_core.tools import ToolException from langgraph.prebuilt import create_react_agent from neuroagent.tools.base_tool import BasicTool, process_validation_error -from pydantic import BaseModel, ValidationError +from pydantic import BaseModel class input_for_test(BaseModel): From e7ffd368ab8bca75b904c1ab5ed02f7e94a49373 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Wed, 25 Sep 2024 12:23:54 +0200 Subject: [PATCH 08/25] Added type ignores for mypy --- src/neuroagent/agents/simple_chat_agent.py | 2 +- src/neuroagent/app/dependencies.py | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/neuroagent/agents/simple_chat_agent.py b/src/neuroagent/agents/simple_chat_agent.py index b331d75..8ce9b0c 100644 --- a/src/neuroagent/agents/simple_chat_agent.py +++ b/src/neuroagent/agents/simple_chat_agent.py @@ -17,7 +17,7 @@ class SimpleChatAgent(BaseAgent): """Simple Agent class.""" - memory: BaseCheckpointSaver + memory: BaseCheckpointSaver # type: ignore @model_validator(mode="before") @classmethod diff --git a/src/neuroagent/app/dependencies.py b/src/neuroagent/app/dependencies.py index be00639..8d84d33 100644 --- a/src/neuroagent/app/dependencies.py +++ b/src/neuroagent/app/dependencies.py @@ -321,7 +321,7 @@ def get_language_model( async def get_agent_memory( connection_string: Annotated[str | None, Depends(get_connection_string)], -) -> AsyncIterator[BaseCheckpointSaver | None]: +) -> AsyncIterator[BaseCheckpointSaver | None]: # type: ignore """Get the agent checkpointer.""" if connection_string: if connection_string.startswith("sqlite"): @@ -404,7 +404,7 @@ def get_agent( def get_chat_agent( llm: Annotated[ChatOpenAI, Depends(get_language_model)], - memory: Annotated[BaseCheckpointSaver, Depends(get_agent_memory)], + memory: Annotated[BaseCheckpointSaver, Depends(get_agent_memory)], # type: ignore literature_tool: Annotated[LiteratureSearchTool, Depends(get_literature_tool)], br_resolver_tool: Annotated[ ResolveBrainRegionTool, Depends(get_brain_region_resolver_tool) From 88e89b12fc46c8795b578b9fdd3aba4f8e429b4b Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Wed, 25 Sep 2024 12:26:27 +0200 Subject: [PATCH 09/25] ruff format --- tests/tools/test_base_tool.py | 41 ++++++++++++++++++++++++++--------- 1 file changed, 31 insertions(+), 10 deletions(-) diff --git a/tests/tools/test_base_tool.py b/tests/tools/test_base_tool.py index 7eaaaa7..1add1eb 100644 --- a/tests/tools/test_base_tool.py +++ b/tests/tools/test_base_tool.py @@ -107,16 +107,37 @@ def bind_tools(self, functions: list): assert response["messages"][7].content == "fake answer" -@pytest.mark.parametrize("title, errors, expected", [ - ("ValidationError", [{"type": "literal_error", "input": "distinct", "loc": ["led"]}], - '[{"Validation error": "Wrong value: provided distinct for input led. Try again and change this problematic input."}]'), - ("ValidationError", [{"type": "missing", "loc": ["led"]}], - '[{"Validation error": "Missing input : led. Try again and add this input."}]'), - ("ValidationError", [{"type": "other_error", "loc": ["led"], "msg": "This is a test error message"}], - '[{"Validation error": "led. This is a test error message"}]'), - ("ValidationError", [{}], - '[{"Validation error": "Error in ValidationError : \'type\'"}]') -]) +@pytest.mark.parametrize( + "title, errors, expected", + [ + ( + "ValidationError", + [{"type": "literal_error", "input": "distinct", "loc": ["led"]}], + '[{"Validation error": "Wrong value: provided distinct for input led. Try again and change this problematic input."}]', + ), + ( + "ValidationError", + [{"type": "missing", "loc": ["led"]}], + '[{"Validation error": "Missing input : led. Try again and add this input."}]', + ), + ( + "ValidationError", + [ + { + "type": "other_error", + "loc": ["led"], + "msg": "This is a test error message", + } + ], + '[{"Validation error": "led. This is a test error message"}]', + ), + ( + "ValidationError", + [{}], + '[{"Validation error": "Error in ValidationError : \'type\'"}]', + ), + ], +) def test_process_validation_error(title, errors, expected): error = Mock() error.title = title From d8faa4504982c153a12209dfaa0447b3a5331647 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Wed, 25 Sep 2024 12:38:06 +0200 Subject: [PATCH 10/25] Added fixes for unit old tests --- tests/test_resolving.py | 10 +++++----- tests/test_utils.py | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/tests/test_resolving.py b/tests/test_resolving.py index eeafbad..4393b76 100644 --- a/tests/test_resolving.py +++ b/tests/test_resolving.py @@ -32,7 +32,7 @@ async def test_sparql_exact_resolve(httpx_mock, get_resolve_query_output): } ] - httpx_mock.reset(assert_all_responses_were_requested=False) + httpx_mock.reset() mtype = "Interneuron" mocked_response = get_resolve_query_output[1] @@ -83,7 +83,7 @@ async def test_sparql_fuzzy_resolve(httpx_mock, get_resolve_query_output): "id": "http://api.brain-map.org/api/v2/data/Structure/463", }, ] - httpx_mock.reset(assert_all_responses_were_requested=False) + httpx_mock.reset() mtype = "Interneu" mocked_response = get_resolve_query_output[3] @@ -142,7 +142,7 @@ async def test_es_resolve(httpx_mock, get_resolve_query_output): "id": "http://api.brain-map.org/api/v2/data/Structure/184", }, ] - httpx_mock.reset(assert_all_responses_were_requested=True) + httpx_mock.reset() mtype = "Ventral neuron" mocked_response = get_resolve_query_output[5] @@ -221,7 +221,7 @@ async def test_resolve_query(httpx_mock, get_resolve_query_output): "id": "http://api.brain-map.org/api/v2/data/Structure/463", }, ] - httpx_mock.reset(assert_all_responses_were_requested=True) + httpx_mock.reset() httpx_mock.add_response(url=url, json=get_resolve_query_output[0]) @@ -252,7 +252,7 @@ async def test_resolve_query(httpx_mock, get_resolve_query_output): "id": "http://api.brain-map.org/api/v2/data/Structure/549", } ] - httpx_mock.reset(assert_all_responses_were_requested=True) + httpx_mock.reset() httpx_mock.add_response( url=url, json={ diff --git a/tests/test_utils.py b/tests/test_utils.py index 742388b..152232c 100644 --- a/tests/test_utils.py +++ b/tests/test_utils.py @@ -184,7 +184,7 @@ async def test_get_file_from_KG_errors(httpx_mock): ) assert not_found.value.args[0] == "No file url was found." - httpx_mock.reset(assert_all_responses_were_requested=True) + httpx_mock.reset() # no file found corresponding to file_url test_file_url = "http://test_url.com" json_response = { From 59d66d2f342255f1679cba9c3d631c131ab29ed5 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Fri, 27 Sep 2024 15:05:17 +0200 Subject: [PATCH 11/25] Added type arguments --- src/neuroagent/agents/simple_chat_agent.py | 2 +- src/neuroagent/app/dependencies.py | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/neuroagent/agents/simple_chat_agent.py b/src/neuroagent/agents/simple_chat_agent.py index 8ce9b0c..274d18b 100644 --- a/src/neuroagent/agents/simple_chat_agent.py +++ b/src/neuroagent/agents/simple_chat_agent.py @@ -17,7 +17,7 @@ class SimpleChatAgent(BaseAgent): """Simple Agent class.""" - memory: BaseCheckpointSaver # type: ignore + memory: BaseCheckpointSaver[Any] @model_validator(mode="before") @classmethod diff --git a/src/neuroagent/app/dependencies.py b/src/neuroagent/app/dependencies.py index 8d84d33..4d875ba 100644 --- a/src/neuroagent/app/dependencies.py +++ b/src/neuroagent/app/dependencies.py @@ -321,7 +321,7 @@ def get_language_model( async def get_agent_memory( connection_string: Annotated[str | None, Depends(get_connection_string)], -) -> AsyncIterator[BaseCheckpointSaver | None]: # type: ignore +) -> AsyncIterator[BaseCheckpointSaver[Any] | None]: """Get the agent checkpointer.""" if connection_string: if connection_string.startswith("sqlite"): @@ -404,7 +404,7 @@ def get_agent( def get_chat_agent( llm: Annotated[ChatOpenAI, Depends(get_language_model)], - memory: Annotated[BaseCheckpointSaver, Depends(get_agent_memory)], # type: ignore + memory: Annotated[BaseCheckpointSaver[Any], Depends(get_agent_memory)], literature_tool: Annotated[LiteratureSearchTool, Depends(get_literature_tool)], br_resolver_tool: Annotated[ ResolveBrainRegionTool, Depends(get_brain_region_resolver_tool) From 1411b366300ad996867e91b98f516fdae20946dd Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Fri, 27 Sep 2024 16:32:33 +0200 Subject: [PATCH 12/25] Removed mock settings --- src/neuroagent/agents/simple_chat_agent.py | 2 +- src/neuroagent/app/dependencies.py | 4 +- tests/app/test_dependencies.py | 112 ++++++++++++--------- 3 files changed, 70 insertions(+), 48 deletions(-) diff --git a/src/neuroagent/agents/simple_chat_agent.py b/src/neuroagent/agents/simple_chat_agent.py index 274d18b..b331d75 100644 --- a/src/neuroagent/agents/simple_chat_agent.py +++ b/src/neuroagent/agents/simple_chat_agent.py @@ -17,7 +17,7 @@ class SimpleChatAgent(BaseAgent): """Simple Agent class.""" - memory: BaseCheckpointSaver[Any] + memory: BaseCheckpointSaver @model_validator(mode="before") @classmethod diff --git a/src/neuroagent/app/dependencies.py b/src/neuroagent/app/dependencies.py index 4d875ba..be00639 100644 --- a/src/neuroagent/app/dependencies.py +++ b/src/neuroagent/app/dependencies.py @@ -321,7 +321,7 @@ def get_language_model( async def get_agent_memory( connection_string: Annotated[str | None, Depends(get_connection_string)], -) -> AsyncIterator[BaseCheckpointSaver[Any] | None]: +) -> AsyncIterator[BaseCheckpointSaver | None]: """Get the agent checkpointer.""" if connection_string: if connection_string.startswith("sqlite"): @@ -404,7 +404,7 @@ def get_agent( def get_chat_agent( llm: Annotated[ChatOpenAI, Depends(get_language_model)], - memory: Annotated[BaseCheckpointSaver[Any], Depends(get_agent_memory)], + memory: Annotated[BaseCheckpointSaver, Depends(get_agent_memory)], literature_tool: Annotated[LiteratureSearchTool, Depends(get_literature_tool)], br_resolver_tool: Annotated[ ResolveBrainRegionTool, Depends(get_brain_region_resolver_tool) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 66161e2..67d3e05 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -44,7 +44,6 @@ LiteratureSearchTool, MorphologyFeatureTool, ) -from pydantic import Secret from sqlalchemy.exc import SQLAlchemyError from sqlalchemy.orm import Session @@ -387,73 +386,82 @@ async def test_get_cell_types_kg_hierarchy( assert os.path.exists(settings.knowledge_graph.ct_saving_path) -def fake_get_settings(): - class MockedDb: - def __init__(self, prefix, user, password, host, port, name): - self.prefix = prefix - self.user = user - self.password = Secret(password) - self.host = host - self.port = port - self.name = name - - class MockedSettings: - def __init__(self, db): - self.db = db - - return [ - MockedSettings(MockedDb("http://", "John", "Doe", "localhost", 5000, "test")), - MockedSettings(MockedDb("", "", "", "", None, None)), - ] - +def test_get_connection_string_full(monkeypatch): + monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "http://") + monkeypatch.setenv("NEUROAGENT_DB__USER", "John") + monkeypatch.setenv("NEUROAGENT_DB__PASSWORD", "Doe") + monkeypatch.setenv("NEUROAGENT_DB__HOST", "localhost") + monkeypatch.setenv("NEUROAGENT_DB__PORT", "5000") + monkeypatch.setenv("NEUROAGENT_DB__NAME", "test") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") -def test_get_connection_string_full(): - settings = fake_get_settings()[0] + settings = get_settings() result = get_connection_string(settings) assert ( result == "http://John:Doe@localhost:5000/test" ), "must return fully formed connection string" -def test_get_connection_string_no_prefix(): - settings = fake_get_settings()[1] +def test_get_connection_string_no_prefix(monkeypatch): + monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") + + settings = get_settings() result = get_connection_string(settings) assert result is None, "should return None when prefix is not set" @patch("neuroagent.app.dependencies.create_engine") -def test_get_engine(create_engine_mock): +def test_get_engine(create_engine_mock, monkeypatch): create_engine_mock.return_value = Mock() - settings = Mock() - settings.db = Mock() - settings.db.prefix = "prefix" - settings.db.password = None + monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") + + settings = get_settings() + connection_string = "https://localhost" retval = get_engine(settings=settings, connection_string=connection_string) assert retval is not None @patch("neuroagent.app.dependencies.create_engine") -def test_get_engine_no_connection_string(create_engine_mock): +def test_get_engine_no_connection_string(create_engine_mock, monkeypatch): create_engine_mock.return_value = Mock() - settings = Mock() - settings.db = Mock() - settings.db.prefix = "prefix" - settings.db.password = None + monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") + + settings = get_settings() + retval = get_engine(settings=settings, connection_string=None) assert retval is None @patch("neuroagent.app.dependencies.create_engine") -def test_get_engine_error(create_engine_mock): +def test_get_engine_error(create_engine_mock, monkeypatch): create_engine_mock.side_effect = SQLAlchemyError("An error occurred") - settings = Mock() - settings.db = Mock() - settings.db.prefix = "prefix" - settings.db.password = None + monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") + + settings = get_settings() + connection_string = "https://localhost" with pytest.raises(SQLAlchemyError): get_engine(settings=settings, connection_string=connection_string) @@ -471,17 +479,31 @@ def test_get_session_no_engine(): next(get_session(None)) -def test_get_kg_token_with_token(): - settings = Mock() +def test_get_kg_token_with_token(monkeypatch): + monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") + + settings = get_settings() + token = "Test_Token" result = get_kg_token(settings, token) assert result == "Test_Token" -def test_get_kg_token_with_settings_knowledge_graph_token(): - settings = Mock() - settings.knowledge_graph.use_token = True - settings.knowledge_graph.token.get_secret_value.return_value = "Test_kg_Token" +def test_get_kg_token_with_settings_knowledge_graph_token(monkeypatch): + monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") + monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__USE_TOKEN", "true") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__TOKEN", "Test_kg_Token") + + settings = get_settings() + token = None result = get_kg_token(settings, token) From 65bc47490a09b6748667aa22405e87ff2ac91a5a Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Fri, 27 Sep 2024 17:14:43 +0200 Subject: [PATCH 13/25] code review --- tests/app/test_dependencies.py | 4 +++- tests/tools/test_base_tool.py | 43 +--------------------------------- 2 files changed, 4 insertions(+), 43 deletions(-) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 67d3e05..9d1ce93 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -44,6 +44,7 @@ LiteratureSearchTool, MorphologyFeatureTool, ) +from sqlalchemy import create_engine from sqlalchemy.exc import SQLAlchemyError from sqlalchemy.orm import Session @@ -469,7 +470,8 @@ def test_get_engine_error(create_engine_mock, monkeypatch): @patch("sqlalchemy.orm.Session") def test_get_session_success(_): - engine = Mock() + database_url = "sqlite:///:memory:" + engine = create_engine(database_url) result = next(get_session(engine)) assert isinstance(result, Session) diff --git a/tests/tools/test_base_tool.py b/tests/tools/test_base_tool.py index 1add1eb..fb9ab17 100644 --- a/tests/tools/test_base_tool.py +++ b/tests/tools/test_base_tool.py @@ -1,12 +1,10 @@ from typing import Literal, Type -from unittest.mock import Mock -import pytest from langchain_core.language_models.fake_chat_models import FakeMessagesListChatModel from langchain_core.messages import AIMessage, HumanMessage from langchain_core.tools import ToolException from langgraph.prebuilt import create_react_agent -from neuroagent.tools.base_tool import BasicTool, process_validation_error +from neuroagent.tools.base_tool import BasicTool from pydantic import BaseModel @@ -105,42 +103,3 @@ def bind_tools(self, functions: list): 'unable to parse string as an integer"}]' ) assert response["messages"][7].content == "fake answer" - - -@pytest.mark.parametrize( - "title, errors, expected", - [ - ( - "ValidationError", - [{"type": "literal_error", "input": "distinct", "loc": ["led"]}], - '[{"Validation error": "Wrong value: provided distinct for input led. Try again and change this problematic input."}]', - ), - ( - "ValidationError", - [{"type": "missing", "loc": ["led"]}], - '[{"Validation error": "Missing input : led. Try again and add this input."}]', - ), - ( - "ValidationError", - [ - { - "type": "other_error", - "loc": ["led"], - "msg": "This is a test error message", - } - ], - '[{"Validation error": "led. This is a test error message"}]', - ), - ( - "ValidationError", - [{}], - '[{"Validation error": "Error in ValidationError : \'type\'"}]', - ), - ], -) -def test_process_validation_error(title, errors, expected): - error = Mock() - error.title = title - error.errors.return_value = errors - result = process_validation_error(error) - assert result == expected From ee85b7fb7f6c5beb3fc571bbbae9c7a199efc5c5 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Mon, 30 Sep 2024 14:15:56 +0200 Subject: [PATCH 14/25] Fixed most unit test issues --- src/neuroagent/app/dependencies.py | 5 +++- tests/app/test_dependencies.py | 42 ++++++++++++++++-------------- 2 files changed, 26 insertions(+), 21 deletions(-) diff --git a/src/neuroagent/app/dependencies.py b/src/neuroagent/app/dependencies.py index be00639..2b694b8 100644 --- a/src/neuroagent/app/dependencies.py +++ b/src/neuroagent/app/dependencies.py @@ -101,12 +101,14 @@ def get_engine( if "sqlite" in settings.db.prefix: # type: ignore # https://fastapi.tiangolo.com/tutorial/sql-databases/#create-the-sqlalchemy-engine engine_kwargs["connect_args"] = {"check_same_thread": False} - engine = create_engine(**engine_kwargs) + # breakpoint() else: logger.warning("The SQL db_prefix needs to be set to use the SQL DB.") + # breakpoint()# return None try: + # breakpoint() engine.connect() logger.info( "Successfully connected to the SQL database" @@ -114,6 +116,7 @@ def get_engine( ) return engine except SQLAlchemyError: + # breakpoint() logger.warning( "Failed connection to SQL database" f" {connection_string if not settings.db.password else connection_string.replace(settings.db.password.get_secret_value(), '*****')}." diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 9d1ce93..66dc3a0 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -1,6 +1,7 @@ """Test dependencies.""" import json +import logging import os from pathlib import Path from typing import AsyncIterator @@ -49,16 +50,11 @@ from sqlalchemy.orm import Session -@patch.dict( - os.environ, - { - "NEUROAGENT_TOOLS__LITERATURE__URL": "https://localhost1", - "NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL": "https://localhost2", - "NEUROAGENT_KEYCLOAK__USERNAME": "user2", - "NEUROAGENT_KEYCLOAK__PASSWORD": "password2", - }, -) -def test_get_settings(): +def test_get_settings(monkeypatch): + monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "https://localhost1") + monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "https://localhost2") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") + monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") settings = get_settings() assert settings.tools.literature.url == "https://localhost1" assert settings.knowledge_graph.url == "https://localhost2/search/query/" @@ -399,7 +395,7 @@ def test_get_connection_string_full(monkeypatch): monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") - settings = get_settings() + settings = Settings() result = get_connection_string(settings) assert ( result == "http://John:Doe@localhost:5000/test" @@ -413,7 +409,8 @@ def test_get_connection_string_no_prefix(monkeypatch): monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") - settings = get_settings() + settings = Settings() + result = get_connection_string(settings) assert result is None, "should return None when prefix is not set" @@ -428,7 +425,7 @@ def test_get_engine(create_engine_mock, monkeypatch): monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") - settings = get_settings() + settings = Settings() connection_string = "https://localhost" retval = get_engine(settings=settings, connection_string=connection_string) @@ -445,15 +442,17 @@ def test_get_engine_no_connection_string(create_engine_mock, monkeypatch): monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") - settings = get_settings() + settings = Settings() retval = get_engine(settings=settings, connection_string=None) assert retval is None -@patch("neuroagent.app.dependencies.create_engine") -def test_get_engine_error(create_engine_mock, monkeypatch): - create_engine_mock.side_effect = SQLAlchemyError("An error occurred") +@patch("sqlalchemy.engine.create.create_engine") +def test_get_engine_error(sql_create_engine_mock, monkeypatch): + engine_mock = Mock() + engine_mock.connect.side_effect = SQLAlchemyError("An error occurred") + sql_create_engine_mock.return_value = engine_mock monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") @@ -461,7 +460,10 @@ def test_get_engine_error(create_engine_mock, monkeypatch): monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") - settings = get_settings() + settings = Settings() + + logging.error(f"settings.db.prefix: {settings.db.prefix}") + logging.error(f"NEUROAGENT_DB__PREFIX: {os.getenv('NEUROAGENT_DB__PREFIX')}") connection_string = "https://localhost" with pytest.raises(SQLAlchemyError): @@ -488,7 +490,7 @@ def test_get_kg_token_with_token(monkeypatch): monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") - settings = get_settings() + settings = Settings() token = "Test_Token" result = get_kg_token(settings, token) @@ -504,7 +506,7 @@ def test_get_kg_token_with_settings_knowledge_graph_token(monkeypatch): monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__USE_TOKEN", "true") monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__TOKEN", "Test_kg_Token") - settings = get_settings() + settings = Settings() token = None From 2efc88392782f4610259a5718f29f9f1f64520f4 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Mon, 30 Sep 2024 14:30:10 +0200 Subject: [PATCH 15/25] Had to delete one unit test, since it was not working --- src/neuroagent/app/dependencies.py | 4 ---- tests/app/test_dependencies.py | 24 ------------------------ 2 files changed, 28 deletions(-) diff --git a/src/neuroagent/app/dependencies.py b/src/neuroagent/app/dependencies.py index 2b694b8..75a619e 100644 --- a/src/neuroagent/app/dependencies.py +++ b/src/neuroagent/app/dependencies.py @@ -102,13 +102,10 @@ def get_engine( # https://fastapi.tiangolo.com/tutorial/sql-databases/#create-the-sqlalchemy-engine engine_kwargs["connect_args"] = {"check_same_thread": False} engine = create_engine(**engine_kwargs) - # breakpoint() else: logger.warning("The SQL db_prefix needs to be set to use the SQL DB.") - # breakpoint()# return None try: - # breakpoint() engine.connect() logger.info( "Successfully connected to the SQL database" @@ -116,7 +113,6 @@ def get_engine( ) return engine except SQLAlchemyError: - # breakpoint() logger.warning( "Failed connection to SQL database" f" {connection_string if not settings.db.password else connection_string.replace(settings.db.password.get_secret_value(), '*****')}." diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 66dc3a0..c4a3909 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -1,7 +1,6 @@ """Test dependencies.""" import json -import logging import os from pathlib import Path from typing import AsyncIterator @@ -46,7 +45,6 @@ MorphologyFeatureTool, ) from sqlalchemy import create_engine -from sqlalchemy.exc import SQLAlchemyError from sqlalchemy.orm import Session @@ -448,28 +446,6 @@ def test_get_engine_no_connection_string(create_engine_mock, monkeypatch): assert retval is None -@patch("sqlalchemy.engine.create.create_engine") -def test_get_engine_error(sql_create_engine_mock, monkeypatch): - engine_mock = Mock() - engine_mock.connect.side_effect = SQLAlchemyError("An error occurred") - sql_create_engine_mock.return_value = engine_mock - - monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") - monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") - monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") - - settings = Settings() - - logging.error(f"settings.db.prefix: {settings.db.prefix}") - logging.error(f"NEUROAGENT_DB__PREFIX: {os.getenv('NEUROAGENT_DB__PREFIX')}") - - connection_string = "https://localhost" - with pytest.raises(SQLAlchemyError): - get_engine(settings=settings, connection_string=connection_string) - - @patch("sqlalchemy.orm.Session") def test_get_session_success(_): database_url = "sqlite:///:memory:" From 0d50e28f50f48520f76e7c12be4aff1caa459d05 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Mon, 30 Sep 2024 16:02:02 +0200 Subject: [PATCH 16/25] Added change to make tests backwards compatible with new httpx_mock version --- tests/agents/test_simple_agent.py | 1 + tests/agents/test_simple_chat_agent.py | 3 +++ tests/app/database/test_threads.py | 7 ++++--- tests/app/database/test_tools.py | 1 + tests/app/test_config.py | 3 ++- tests/app/test_dependencies.py | 1 + tests/app/test_main.py | 1 + tests/app/test_middleware.py | 1 + tests/conftest.py | 7 ++++--- tests/test_cell_types.py | 1 + tests/test_resolving.py | 1 + tests/test_utils.py | 2 ++ tests/tools/test_basic_tool.py | 3 ++- tests/tools/test_electrophys_tool.py | 2 ++ tests/tools/test_get_morpho_tool.py | 1 + tests/tools/test_kg_morpho_features_tool.py | 1 + tests/tools/test_literature_search_tool.py | 1 + tests/tools/test_morphology_features_tool.py | 1 + tests/tools/test_resolve_br_tool.py | 1 + tests/tools/test_traces_tool.py | 2 ++ 20 files changed, 33 insertions(+), 8 deletions(-) diff --git a/tests/agents/test_simple_agent.py b/tests/agents/test_simple_agent.py index a31cf91..0f0ca1d 100644 --- a/tests/agents/test_simple_agent.py +++ b/tests/agents/test_simple_agent.py @@ -4,6 +4,7 @@ from pathlib import Path import pytest + from neuroagent.agents import AgentOutput, AgentStep, SimpleAgent diff --git a/tests/agents/test_simple_chat_agent.py b/tests/agents/test_simple_chat_agent.py index c8420a3..e0f5dea 100644 --- a/tests/agents/test_simple_chat_agent.py +++ b/tests/agents/test_simple_chat_agent.py @@ -6,9 +6,11 @@ import pytest from langchain_core.messages import HumanMessage, ToolMessage from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver + from neuroagent.agents import AgentOutput, AgentStep, SimpleChatAgent +@pytest.mark.httpx_mock(can_send_already_matched_responses=True) @pytest.mark.asyncio async def test_arun(fake_llm_with_tools, httpx_mock): llm, tools, fake_responses = await anext(fake_llm_with_tools) @@ -64,6 +66,7 @@ async def test_arun(fake_llm_with_tools, httpx_mock): assert len(messages_list) == 10 +@pytest.mark.httpx_mock(can_send_already_matched_responses=True) @pytest.mark.asyncio async def test_astream(fake_llm_with_tools, httpx_mock): llm, tools, fake_responses = await anext(fake_llm_with_tools) diff --git a/tests/app/database/test_threads.py b/tests/app/database/test_threads.py index 7807826..dfc3313 100644 --- a/tests/app/database/test_threads.py +++ b/tests/app/database/test_threads.py @@ -1,13 +1,14 @@ """Test of the thread router.""" import pytest +from sqlalchemy import MetaData, create_engine +from sqlalchemy.orm import Session +from sqlalchemy.sql.expression import Select + from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_language_model, get_settings from neuroagent.app.main import app from neuroagent.app.routers.database.schemas import GetThreadsOutput -from sqlalchemy import MetaData, create_engine -from sqlalchemy.orm import Session -from sqlalchemy.sql.expression import Select def test_create_thread(patch_required_env, app_client, db_connection): diff --git a/tests/app/database/test_tools.py b/tests/app/database/test_tools.py index a5f55e0..03f2cf0 100644 --- a/tests/app/database/test_tools.py +++ b/tests/app/database/test_tools.py @@ -1,6 +1,7 @@ """Test of the tool router.""" import pytest + from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_language_model, get_settings from neuroagent.app.main import app diff --git a/tests/app/test_config.py b/tests/app/test_config.py index 459d457..38191f8 100644 --- a/tests/app/test_config.py +++ b/tests/app/test_config.py @@ -1,9 +1,10 @@ """Test config""" import pytest -from neuroagent.app.config import Settings from pydantic import ValidationError +from neuroagent.app.config import Settings + def test_required(monkeypatch, patch_required_env): settings = Settings() diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 1acfa4b..6ea716c 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -11,6 +11,7 @@ from langchain_openai import ChatOpenAI from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver + from neuroagent.agents import SimpleAgent, SimpleChatAgent from neuroagent.app.dependencies import ( Settings, diff --git a/tests/app/test_main.py b/tests/app/test_main.py index 79fe9a8..3827ad8 100644 --- a/tests/app/test_main.py +++ b/tests/app/test_main.py @@ -2,6 +2,7 @@ from unittest.mock import patch from fastapi.testclient import TestClient + from neuroagent.app.dependencies import get_settings from neuroagent.app.main import app diff --git a/tests/app/test_middleware.py b/tests/app/test_middleware.py index 2707d4d..5a9bdcf 100644 --- a/tests/app/test_middleware.py +++ b/tests/app/test_middleware.py @@ -5,6 +5,7 @@ import pytest from fastapi.requests import Request from fastapi.responses import Response + from neuroagent.app.config import Settings from neuroagent.app.middleware import strip_path_prefix diff --git a/tests/conftest.py b/tests/conftest.py index d4c5f6d..c49e3a9 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -8,13 +8,14 @@ from httpx import AsyncClient from langchain_core.language_models.fake_chat_models import GenericFakeChatModel from langchain_core.messages import AIMessage +from sqlalchemy import MetaData, create_engine +from sqlalchemy.exc import OperationalError +from sqlalchemy.orm import Session + from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_kg_token, get_settings from neuroagent.app.main import app from neuroagent.tools import GetMorphoTool -from sqlalchemy import MetaData, create_engine -from sqlalchemy.exc import OperationalError -from sqlalchemy.orm import Session @pytest.fixture(name="app_client") diff --git a/tests/test_cell_types.py b/tests/test_cell_types.py index 0596534..930ec71 100644 --- a/tests/test_cell_types.py +++ b/tests/test_cell_types.py @@ -3,6 +3,7 @@ from pathlib import Path import pytest + from neuroagent.cell_types import CellTypesMeta, get_celltypes_descendants CELL_TYPES_FILE = Path(__file__).parent / "data" / "kg_cell_types_hierarchy_test.json" diff --git a/tests/test_resolving.py b/tests/test_resolving.py index 4393b76..6d4f25a 100644 --- a/tests/test_resolving.py +++ b/tests/test_resolving.py @@ -1,5 +1,6 @@ import pytest from httpx import AsyncClient + from neuroagent.resolving import ( es_resolve, escape_punctuation, diff --git a/tests/test_utils.py b/tests/test_utils.py index 152232c..403dddc 100644 --- a/tests/test_utils.py +++ b/tests/test_utils.py @@ -5,6 +5,7 @@ import pytest from httpx import AsyncClient + from neuroagent.schemas import KGMetadata from neuroagent.utils import ( RegionMeta, @@ -313,6 +314,7 @@ async def test_get_kg_data_errors(httpx_mock): ) +@pytest.mark.httpx_mock(can_send_already_matched_responses=True) @pytest.mark.asyncio async def test_get_kg_data(httpx_mock): url = "http://fake_url" diff --git a/tests/tools/test_basic_tool.py b/tests/tools/test_basic_tool.py index fb9ab17..c29bc6c 100644 --- a/tests/tools/test_basic_tool.py +++ b/tests/tools/test_basic_tool.py @@ -4,9 +4,10 @@ from langchain_core.messages import AIMessage, HumanMessage from langchain_core.tools import ToolException from langgraph.prebuilt import create_react_agent -from neuroagent.tools.base_tool import BasicTool from pydantic import BaseModel +from neuroagent.tools.base_tool import BasicTool + class input_for_test(BaseModel): test_str: str diff --git a/tests/tools/test_electrophys_tool.py b/tests/tools/test_electrophys_tool.py index e7729fc..a58db53 100644 --- a/tests/tools/test_electrophys_tool.py +++ b/tests/tools/test_electrophys_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import ElectrophysFeatureTool from neuroagent.tools.electrophys_tool import ( CALCULATED_FEATURES, @@ -15,6 +16,7 @@ class TestElectrophysTool: + @pytest.mark.httpx_mock(can_send_already_matched_responses=True) @pytest.mark.asyncio async def test_arun(self, httpx_mock): url = "http://fake_url" diff --git a/tests/tools/test_get_morpho_tool.py b/tests/tools/test_get_morpho_tool.py index d3ef4ab..87fdcbb 100644 --- a/tests/tools/test_get_morpho_tool.py +++ b/tests/tools/test_get_morpho_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import GetMorphoTool from neuroagent.tools.get_morpho_tool import KnowledgeGraphOutput diff --git a/tests/tools/test_kg_morpho_features_tool.py b/tests/tools/test_kg_morpho_features_tool.py index 2f5473c..b346e26 100644 --- a/tests/tools/test_kg_morpho_features_tool.py +++ b/tests/tools/test_kg_morpho_features_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import KGMorphoFeatureTool from neuroagent.tools.kg_morpho_features_tool import ( FeatRangeInput, diff --git a/tests/tools/test_literature_search_tool.py b/tests/tools/test_literature_search_tool.py index 0f58728..93adf4f 100644 --- a/tests/tools/test_literature_search_tool.py +++ b/tests/tools/test_literature_search_tool.py @@ -4,6 +4,7 @@ import httpx import pytest + from neuroagent.tools import LiteratureSearchTool from neuroagent.tools.literature_search_tool import ParagraphMetadata diff --git a/tests/tools/test_morphology_features_tool.py b/tests/tools/test_morphology_features_tool.py index 22943e6..92a311f 100644 --- a/tests/tools/test_morphology_features_tool.py +++ b/tests/tools/test_morphology_features_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import MorphologyFeatureTool from neuroagent.tools.morphology_features_tool import MorphologyFeatureOutput diff --git a/tests/tools/test_resolve_br_tool.py b/tests/tools/test_resolve_br_tool.py index 697a6ef..31f893d 100644 --- a/tests/tools/test_resolve_br_tool.py +++ b/tests/tools/test_resolve_br_tool.py @@ -2,6 +2,7 @@ import pytest from httpx import AsyncClient + from neuroagent.tools import ResolveBrainRegionTool from neuroagent.tools.resolve_brain_region_tool import ( BRResolveOutput, diff --git a/tests/tools/test_traces_tool.py b/tests/tools/test_traces_tool.py index 0bae056..16f014c 100644 --- a/tests/tools/test_traces_tool.py +++ b/tests/tools/test_traces_tool.py @@ -6,11 +6,13 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import GetTracesTool from neuroagent.tools.traces_tool import TracesOutput class TestTracesTool: + @pytest.mark.httpx_mock(can_send_already_matched_responses=True) @pytest.mark.asyncio async def test_arun(self, httpx_mock, brain_region_json_path): url = "http://fake_url" From 839be90946d718ed5adab495b216a665e1ce0abc Mon Sep 17 00:00:00 2001 From: cszsol Date: Mon, 30 Sep 2024 16:05:37 +0200 Subject: [PATCH 17/25] Update test_simple_agent.py --- tests/agents/test_simple_agent.py | 1 - 1 file changed, 1 deletion(-) diff --git a/tests/agents/test_simple_agent.py b/tests/agents/test_simple_agent.py index 0f0ca1d..a31cf91 100644 --- a/tests/agents/test_simple_agent.py +++ b/tests/agents/test_simple_agent.py @@ -4,7 +4,6 @@ from pathlib import Path import pytest - from neuroagent.agents import AgentOutput, AgentStep, SimpleAgent From 996117eb6e55c5a8fc1a158287df5de898ea2b22 Mon Sep 17 00:00:00 2001 From: cszsol Date: Mon, 30 Sep 2024 16:05:58 +0200 Subject: [PATCH 18/25] Update test_simple_chat_agent.py --- tests/agents/test_simple_chat_agent.py | 1 - 1 file changed, 1 deletion(-) diff --git a/tests/agents/test_simple_chat_agent.py b/tests/agents/test_simple_chat_agent.py index e0f5dea..c7e0a92 100644 --- a/tests/agents/test_simple_chat_agent.py +++ b/tests/agents/test_simple_chat_agent.py @@ -6,7 +6,6 @@ import pytest from langchain_core.messages import HumanMessage, ToolMessage from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver - from neuroagent.agents import AgentOutput, AgentStep, SimpleChatAgent From 5e95765da0df493845332b31704209a1b3c083ac Mon Sep 17 00:00:00 2001 From: cszsol Date: Mon, 30 Sep 2024 16:06:41 +0200 Subject: [PATCH 19/25] Update test_tools.py --- tests/app/database/test_tools.py | 1 - 1 file changed, 1 deletion(-) diff --git a/tests/app/database/test_tools.py b/tests/app/database/test_tools.py index 03f2cf0..a5f55e0 100644 --- a/tests/app/database/test_tools.py +++ b/tests/app/database/test_tools.py @@ -1,7 +1,6 @@ """Test of the tool router.""" import pytest - from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_language_model, get_settings from neuroagent.app.main import app From a266fbf350475b7eb21bb03a5422541d897c13c5 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Mon, 30 Sep 2024 16:08:50 +0200 Subject: [PATCH 20/25] Added changelog --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index d71d1fc..e71a0ce 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -11,6 +11,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Fixed - Fixed a bug that prevented AsyncSqlite checkpoint to access the DB in streamed endpoints. +- Fixed a bug that caused some unit tests to fail due to a change in how httpx_mock works in version 0.32 ## [0.1.0] - 19.09.2024 From 74036cd8e1becc42c1ad004080abe9c16f0a9971 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Mon, 30 Sep 2024 16:13:04 +0200 Subject: [PATCH 21/25] Reformatted with proper ruff version --- tests/app/database/test_threads.py | 7 +++---- tests/app/test_config.py | 3 +-- tests/app/test_dependencies.py | 1 - tests/app/test_main.py | 1 - tests/app/test_middleware.py | 1 - tests/conftest.py | 7 +++---- tests/test_cell_types.py | 1 - tests/test_resolving.py | 1 - tests/test_utils.py | 1 - tests/tools/test_basic_tool.py | 3 +-- tests/tools/test_electrophys_tool.py | 1 - tests/tools/test_get_morpho_tool.py | 1 - tests/tools/test_kg_morpho_features_tool.py | 1 - tests/tools/test_literature_search_tool.py | 1 - tests/tools/test_morphology_features_tool.py | 1 - tests/tools/test_resolve_br_tool.py | 1 - tests/tools/test_traces_tool.py | 1 - 17 files changed, 8 insertions(+), 25 deletions(-) diff --git a/tests/app/database/test_threads.py b/tests/app/database/test_threads.py index dfc3313..7807826 100644 --- a/tests/app/database/test_threads.py +++ b/tests/app/database/test_threads.py @@ -1,14 +1,13 @@ """Test of the thread router.""" import pytest -from sqlalchemy import MetaData, create_engine -from sqlalchemy.orm import Session -from sqlalchemy.sql.expression import Select - from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_language_model, get_settings from neuroagent.app.main import app from neuroagent.app.routers.database.schemas import GetThreadsOutput +from sqlalchemy import MetaData, create_engine +from sqlalchemy.orm import Session +from sqlalchemy.sql.expression import Select def test_create_thread(patch_required_env, app_client, db_connection): diff --git a/tests/app/test_config.py b/tests/app/test_config.py index 38191f8..459d457 100644 --- a/tests/app/test_config.py +++ b/tests/app/test_config.py @@ -1,9 +1,8 @@ """Test config""" import pytest -from pydantic import ValidationError - from neuroagent.app.config import Settings +from pydantic import ValidationError def test_required(monkeypatch, patch_required_env): diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 6ea716c..1acfa4b 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -11,7 +11,6 @@ from langchain_openai import ChatOpenAI from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver - from neuroagent.agents import SimpleAgent, SimpleChatAgent from neuroagent.app.dependencies import ( Settings, diff --git a/tests/app/test_main.py b/tests/app/test_main.py index 3827ad8..79fe9a8 100644 --- a/tests/app/test_main.py +++ b/tests/app/test_main.py @@ -2,7 +2,6 @@ from unittest.mock import patch from fastapi.testclient import TestClient - from neuroagent.app.dependencies import get_settings from neuroagent.app.main import app diff --git a/tests/app/test_middleware.py b/tests/app/test_middleware.py index 5a9bdcf..2707d4d 100644 --- a/tests/app/test_middleware.py +++ b/tests/app/test_middleware.py @@ -5,7 +5,6 @@ import pytest from fastapi.requests import Request from fastapi.responses import Response - from neuroagent.app.config import Settings from neuroagent.app.middleware import strip_path_prefix diff --git a/tests/conftest.py b/tests/conftest.py index c49e3a9..d4c5f6d 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -8,14 +8,13 @@ from httpx import AsyncClient from langchain_core.language_models.fake_chat_models import GenericFakeChatModel from langchain_core.messages import AIMessage -from sqlalchemy import MetaData, create_engine -from sqlalchemy.exc import OperationalError -from sqlalchemy.orm import Session - from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_kg_token, get_settings from neuroagent.app.main import app from neuroagent.tools import GetMorphoTool +from sqlalchemy import MetaData, create_engine +from sqlalchemy.exc import OperationalError +from sqlalchemy.orm import Session @pytest.fixture(name="app_client") diff --git a/tests/test_cell_types.py b/tests/test_cell_types.py index 930ec71..0596534 100644 --- a/tests/test_cell_types.py +++ b/tests/test_cell_types.py @@ -3,7 +3,6 @@ from pathlib import Path import pytest - from neuroagent.cell_types import CellTypesMeta, get_celltypes_descendants CELL_TYPES_FILE = Path(__file__).parent / "data" / "kg_cell_types_hierarchy_test.json" diff --git a/tests/test_resolving.py b/tests/test_resolving.py index 6d4f25a..4393b76 100644 --- a/tests/test_resolving.py +++ b/tests/test_resolving.py @@ -1,6 +1,5 @@ import pytest from httpx import AsyncClient - from neuroagent.resolving import ( es_resolve, escape_punctuation, diff --git a/tests/test_utils.py b/tests/test_utils.py index 403dddc..9e9af8b 100644 --- a/tests/test_utils.py +++ b/tests/test_utils.py @@ -5,7 +5,6 @@ import pytest from httpx import AsyncClient - from neuroagent.schemas import KGMetadata from neuroagent.utils import ( RegionMeta, diff --git a/tests/tools/test_basic_tool.py b/tests/tools/test_basic_tool.py index c29bc6c..fb9ab17 100644 --- a/tests/tools/test_basic_tool.py +++ b/tests/tools/test_basic_tool.py @@ -4,9 +4,8 @@ from langchain_core.messages import AIMessage, HumanMessage from langchain_core.tools import ToolException from langgraph.prebuilt import create_react_agent -from pydantic import BaseModel - from neuroagent.tools.base_tool import BasicTool +from pydantic import BaseModel class input_for_test(BaseModel): diff --git a/tests/tools/test_electrophys_tool.py b/tests/tools/test_electrophys_tool.py index a58db53..6705c2a 100644 --- a/tests/tools/test_electrophys_tool.py +++ b/tests/tools/test_electrophys_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import ElectrophysFeatureTool from neuroagent.tools.electrophys_tool import ( CALCULATED_FEATURES, diff --git a/tests/tools/test_get_morpho_tool.py b/tests/tools/test_get_morpho_tool.py index 87fdcbb..d3ef4ab 100644 --- a/tests/tools/test_get_morpho_tool.py +++ b/tests/tools/test_get_morpho_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import GetMorphoTool from neuroagent.tools.get_morpho_tool import KnowledgeGraphOutput diff --git a/tests/tools/test_kg_morpho_features_tool.py b/tests/tools/test_kg_morpho_features_tool.py index b346e26..2f5473c 100644 --- a/tests/tools/test_kg_morpho_features_tool.py +++ b/tests/tools/test_kg_morpho_features_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import KGMorphoFeatureTool from neuroagent.tools.kg_morpho_features_tool import ( FeatRangeInput, diff --git a/tests/tools/test_literature_search_tool.py b/tests/tools/test_literature_search_tool.py index 93adf4f..0f58728 100644 --- a/tests/tools/test_literature_search_tool.py +++ b/tests/tools/test_literature_search_tool.py @@ -4,7 +4,6 @@ import httpx import pytest - from neuroagent.tools import LiteratureSearchTool from neuroagent.tools.literature_search_tool import ParagraphMetadata diff --git a/tests/tools/test_morphology_features_tool.py b/tests/tools/test_morphology_features_tool.py index 92a311f..22943e6 100644 --- a/tests/tools/test_morphology_features_tool.py +++ b/tests/tools/test_morphology_features_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import MorphologyFeatureTool from neuroagent.tools.morphology_features_tool import MorphologyFeatureOutput diff --git a/tests/tools/test_resolve_br_tool.py b/tests/tools/test_resolve_br_tool.py index 31f893d..697a6ef 100644 --- a/tests/tools/test_resolve_br_tool.py +++ b/tests/tools/test_resolve_br_tool.py @@ -2,7 +2,6 @@ import pytest from httpx import AsyncClient - from neuroagent.tools import ResolveBrainRegionTool from neuroagent.tools.resolve_brain_region_tool import ( BRResolveOutput, diff --git a/tests/tools/test_traces_tool.py b/tests/tools/test_traces_tool.py index 16f014c..d0689aa 100644 --- a/tests/tools/test_traces_tool.py +++ b/tests/tools/test_traces_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import GetTracesTool from neuroagent.tools.traces_tool import TracesOutput From 228df9ebe5b7837a7ecd269cc76bba73ca2ea739 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Wed, 2 Oct 2024 10:04:33 +0200 Subject: [PATCH 22/25] Added patch_required_env fixture --- tests/app/test_dependencies.py | 28 ++++++++++------------------ 1 file changed, 10 insertions(+), 18 deletions(-) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index c4a3909..75b5b1a 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -381,9 +381,7 @@ async def test_get_cell_types_kg_hierarchy( assert os.path.exists(settings.knowledge_graph.ct_saving_path) -def test_get_connection_string_full(monkeypatch): - monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") - monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") +def test_get_connection_string_full(monkeypatch, patch_required_env): monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "http://") monkeypatch.setenv("NEUROAGENT_DB__USER", "John") monkeypatch.setenv("NEUROAGENT_DB__PASSWORD", "Doe") @@ -400,9 +398,7 @@ def test_get_connection_string_full(monkeypatch): ), "must return fully formed connection string" -def test_get_connection_string_no_prefix(monkeypatch): - monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") - monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") +def test_get_connection_string_no_prefix(monkeypatch, patch_required_env): monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") @@ -414,11 +410,9 @@ def test_get_connection_string_no_prefix(monkeypatch): @patch("neuroagent.app.dependencies.create_engine") -def test_get_engine(create_engine_mock, monkeypatch): +def test_get_engine(create_engine_mock, monkeypatch, patch_required_env): create_engine_mock.return_value = Mock() - monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") - monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") @@ -431,11 +425,11 @@ def test_get_engine(create_engine_mock, monkeypatch): @patch("neuroagent.app.dependencies.create_engine") -def test_get_engine_no_connection_string(create_engine_mock, monkeypatch): +def test_get_engine_no_connection_string( + create_engine_mock, monkeypatch, patch_required_env +): create_engine_mock.return_value = Mock() - monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") - monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") @@ -459,9 +453,7 @@ def test_get_session_no_engine(): next(get_session(None)) -def test_get_kg_token_with_token(monkeypatch): - monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") - monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") +def test_get_kg_token_with_token(monkeypatch, patch_required_env): monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") @@ -473,9 +465,9 @@ def test_get_kg_token_with_token(monkeypatch): assert result == "Test_Token" -def test_get_kg_token_with_settings_knowledge_graph_token(monkeypatch): - monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "http://localhost") - monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "http://localhost") +def test_get_kg_token_with_settings_knowledge_graph_token( + monkeypatch, patch_required_env +): monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") From 1cc66501a486f869b431f4d89a607470b2a6b6fb Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Wed, 2 Oct 2024 13:38:25 +0200 Subject: [PATCH 23/25] code review --- tests/app/test_dependencies.py | 22 +++------------------- 1 file changed, 3 insertions(+), 19 deletions(-) diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 75b5b1a..d68966d 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -48,14 +48,10 @@ from sqlalchemy.orm import Session -def test_get_settings(monkeypatch): - monkeypatch.setenv("NEUROAGENT_TOOLS__LITERATURE__URL", "https://localhost1") - monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__BASE_URL", "https://localhost2") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") +def test_get_settings(monkeypatch, patch_required_env): settings = get_settings() - assert settings.tools.literature.url == "https://localhost1" - assert settings.knowledge_graph.url == "https://localhost2/search/query/" + assert settings.tools.literature.url == "https://fake_url" + assert settings.knowledge_graph.url == "https://fake_url/api/nexus/v1/search/query/" @pytest.mark.asyncio @@ -388,8 +384,6 @@ def test_get_connection_string_full(monkeypatch, patch_required_env): monkeypatch.setenv("NEUROAGENT_DB__HOST", "localhost") monkeypatch.setenv("NEUROAGENT_DB__PORT", "5000") monkeypatch.setenv("NEUROAGENT_DB__NAME", "test") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") settings = Settings() result = get_connection_string(settings) @@ -400,8 +394,6 @@ def test_get_connection_string_full(monkeypatch, patch_required_env): def test_get_connection_string_no_prefix(monkeypatch, patch_required_env): monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") settings = Settings() @@ -414,8 +406,6 @@ def test_get_engine(create_engine_mock, monkeypatch, patch_required_env): create_engine_mock.return_value = Mock() monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") settings = Settings() @@ -431,8 +421,6 @@ def test_get_engine_no_connection_string( create_engine_mock.return_value = Mock() monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") settings = Settings() @@ -455,8 +443,6 @@ def test_get_session_no_engine(): def test_get_kg_token_with_token(monkeypatch, patch_required_env): monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") settings = Settings() @@ -469,8 +455,6 @@ def test_get_kg_token_with_settings_knowledge_graph_token( monkeypatch, patch_required_env ): monkeypatch.setenv("NEUROAGENT_DB__PREFIX", "prefix") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__USERNAME", "fake_username") - monkeypatch.setenv("NEUROAGENT_KEYCLOAK__PASSWORD", "fake_password") monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__USE_TOKEN", "true") monkeypatch.setenv("NEUROAGENT_KNOWLEDGE_GRAPH__TOKEN", "Test_kg_Token") From 2092fc1272e3208356eaa2d14501ab856fef6857 Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Wed, 2 Oct 2024 13:42:14 +0200 Subject: [PATCH 24/25] lint --- tests/agents/test_simple_agent.py | 1 - tests/agents/test_simple_chat_agent.py | 1 - tests/app/database/test_threads.py | 7 +++---- tests/app/database/test_tools.py | 1 - tests/app/test_config.py | 3 +-- tests/app/test_dependencies.py | 1 - tests/app/test_main.py | 1 - tests/app/test_middleware.py | 1 - tests/conftest.py | 7 +++---- tests/test_cell_types.py | 1 - tests/test_resolving.py | 1 - tests/test_utils.py | 1 - tests/tools/test_base_tool.py | 3 +-- tests/tools/test_electrophys_tool.py | 1 - tests/tools/test_get_me_model_tool.py | 1 - tests/tools/test_get_morpho_tool.py | 1 - tests/tools/test_kg_morpho_features_tool.py | 1 - tests/tools/test_literature_search_tool.py | 1 - tests/tools/test_morphology_features_tool.py | 1 - tests/tools/test_resolve_br_tool.py | 1 - tests/tools/test_traces_tool.py | 1 - 21 files changed, 8 insertions(+), 29 deletions(-) diff --git a/tests/agents/test_simple_agent.py b/tests/agents/test_simple_agent.py index 0f0ca1d..a31cf91 100644 --- a/tests/agents/test_simple_agent.py +++ b/tests/agents/test_simple_agent.py @@ -4,7 +4,6 @@ from pathlib import Path import pytest - from neuroagent.agents import AgentOutput, AgentStep, SimpleAgent diff --git a/tests/agents/test_simple_chat_agent.py b/tests/agents/test_simple_chat_agent.py index e0f5dea..c7e0a92 100644 --- a/tests/agents/test_simple_chat_agent.py +++ b/tests/agents/test_simple_chat_agent.py @@ -6,7 +6,6 @@ import pytest from langchain_core.messages import HumanMessage, ToolMessage from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver - from neuroagent.agents import AgentOutput, AgentStep, SimpleChatAgent diff --git a/tests/app/database/test_threads.py b/tests/app/database/test_threads.py index dfc3313..7807826 100644 --- a/tests/app/database/test_threads.py +++ b/tests/app/database/test_threads.py @@ -1,14 +1,13 @@ """Test of the thread router.""" import pytest -from sqlalchemy import MetaData, create_engine -from sqlalchemy.orm import Session -from sqlalchemy.sql.expression import Select - from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_language_model, get_settings from neuroagent.app.main import app from neuroagent.app.routers.database.schemas import GetThreadsOutput +from sqlalchemy import MetaData, create_engine +from sqlalchemy.orm import Session +from sqlalchemy.sql.expression import Select def test_create_thread(patch_required_env, app_client, db_connection): diff --git a/tests/app/database/test_tools.py b/tests/app/database/test_tools.py index 03f2cf0..a5f55e0 100644 --- a/tests/app/database/test_tools.py +++ b/tests/app/database/test_tools.py @@ -1,7 +1,6 @@ """Test of the tool router.""" import pytest - from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_language_model, get_settings from neuroagent.app.main import app diff --git a/tests/app/test_config.py b/tests/app/test_config.py index 38191f8..459d457 100644 --- a/tests/app/test_config.py +++ b/tests/app/test_config.py @@ -1,9 +1,8 @@ """Test config""" import pytest -from pydantic import ValidationError - from neuroagent.app.config import Settings +from pydantic import ValidationError def test_required(monkeypatch, patch_required_env): diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 929c820..5cca93f 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -12,7 +12,6 @@ from langchain_openai import ChatOpenAI from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver - from neuroagent.agents import SimpleAgent, SimpleChatAgent from neuroagent.app.dependencies import ( Settings, diff --git a/tests/app/test_main.py b/tests/app/test_main.py index 3827ad8..79fe9a8 100644 --- a/tests/app/test_main.py +++ b/tests/app/test_main.py @@ -2,7 +2,6 @@ from unittest.mock import patch from fastapi.testclient import TestClient - from neuroagent.app.dependencies import get_settings from neuroagent.app.main import app diff --git a/tests/app/test_middleware.py b/tests/app/test_middleware.py index 5a9bdcf..2707d4d 100644 --- a/tests/app/test_middleware.py +++ b/tests/app/test_middleware.py @@ -5,7 +5,6 @@ import pytest from fastapi.requests import Request from fastapi.responses import Response - from neuroagent.app.config import Settings from neuroagent.app.middleware import strip_path_prefix diff --git a/tests/conftest.py b/tests/conftest.py index c49e3a9..d4c5f6d 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -8,14 +8,13 @@ from httpx import AsyncClient from langchain_core.language_models.fake_chat_models import GenericFakeChatModel from langchain_core.messages import AIMessage -from sqlalchemy import MetaData, create_engine -from sqlalchemy.exc import OperationalError -from sqlalchemy.orm import Session - from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_kg_token, get_settings from neuroagent.app.main import app from neuroagent.tools import GetMorphoTool +from sqlalchemy import MetaData, create_engine +from sqlalchemy.exc import OperationalError +from sqlalchemy.orm import Session @pytest.fixture(name="app_client") diff --git a/tests/test_cell_types.py b/tests/test_cell_types.py index 930ec71..0596534 100644 --- a/tests/test_cell_types.py +++ b/tests/test_cell_types.py @@ -3,7 +3,6 @@ from pathlib import Path import pytest - from neuroagent.cell_types import CellTypesMeta, get_celltypes_descendants CELL_TYPES_FILE = Path(__file__).parent / "data" / "kg_cell_types_hierarchy_test.json" diff --git a/tests/test_resolving.py b/tests/test_resolving.py index 6d4f25a..4393b76 100644 --- a/tests/test_resolving.py +++ b/tests/test_resolving.py @@ -1,6 +1,5 @@ import pytest from httpx import AsyncClient - from neuroagent.resolving import ( es_resolve, escape_punctuation, diff --git a/tests/test_utils.py b/tests/test_utils.py index 403dddc..9e9af8b 100644 --- a/tests/test_utils.py +++ b/tests/test_utils.py @@ -5,7 +5,6 @@ import pytest from httpx import AsyncClient - from neuroagent.schemas import KGMetadata from neuroagent.utils import ( RegionMeta, diff --git a/tests/tools/test_base_tool.py b/tests/tools/test_base_tool.py index c29bc6c..fb9ab17 100644 --- a/tests/tools/test_base_tool.py +++ b/tests/tools/test_base_tool.py @@ -4,9 +4,8 @@ from langchain_core.messages import AIMessage, HumanMessage from langchain_core.tools import ToolException from langgraph.prebuilt import create_react_agent -from pydantic import BaseModel - from neuroagent.tools.base_tool import BasicTool +from pydantic import BaseModel class input_for_test(BaseModel): diff --git a/tests/tools/test_electrophys_tool.py b/tests/tools/test_electrophys_tool.py index a58db53..6705c2a 100644 --- a/tests/tools/test_electrophys_tool.py +++ b/tests/tools/test_electrophys_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import ElectrophysFeatureTool from neuroagent.tools.electrophys_tool import ( CALCULATED_FEATURES, diff --git a/tests/tools/test_get_me_model_tool.py b/tests/tools/test_get_me_model_tool.py index 2366b59..0627d5f 100644 --- a/tests/tools/test_get_me_model_tool.py +++ b/tests/tools/test_get_me_model_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools.get_me_model_tool import GetMEModelTool, MEModelOutput diff --git a/tests/tools/test_get_morpho_tool.py b/tests/tools/test_get_morpho_tool.py index 87fdcbb..d3ef4ab 100644 --- a/tests/tools/test_get_morpho_tool.py +++ b/tests/tools/test_get_morpho_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import GetMorphoTool from neuroagent.tools.get_morpho_tool import KnowledgeGraphOutput diff --git a/tests/tools/test_kg_morpho_features_tool.py b/tests/tools/test_kg_morpho_features_tool.py index b346e26..2f5473c 100644 --- a/tests/tools/test_kg_morpho_features_tool.py +++ b/tests/tools/test_kg_morpho_features_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import KGMorphoFeatureTool from neuroagent.tools.kg_morpho_features_tool import ( FeatRangeInput, diff --git a/tests/tools/test_literature_search_tool.py b/tests/tools/test_literature_search_tool.py index 93adf4f..0f58728 100644 --- a/tests/tools/test_literature_search_tool.py +++ b/tests/tools/test_literature_search_tool.py @@ -4,7 +4,6 @@ import httpx import pytest - from neuroagent.tools import LiteratureSearchTool from neuroagent.tools.literature_search_tool import ParagraphMetadata diff --git a/tests/tools/test_morphology_features_tool.py b/tests/tools/test_morphology_features_tool.py index 92a311f..22943e6 100644 --- a/tests/tools/test_morphology_features_tool.py +++ b/tests/tools/test_morphology_features_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import MorphologyFeatureTool from neuroagent.tools.morphology_features_tool import MorphologyFeatureOutput diff --git a/tests/tools/test_resolve_br_tool.py b/tests/tools/test_resolve_br_tool.py index 31f893d..697a6ef 100644 --- a/tests/tools/test_resolve_br_tool.py +++ b/tests/tools/test_resolve_br_tool.py @@ -2,7 +2,6 @@ import pytest from httpx import AsyncClient - from neuroagent.tools import ResolveBrainRegionTool from neuroagent.tools.resolve_brain_region_tool import ( BRResolveOutput, diff --git a/tests/tools/test_traces_tool.py b/tests/tools/test_traces_tool.py index 16f014c..d0689aa 100644 --- a/tests/tools/test_traces_tool.py +++ b/tests/tools/test_traces_tool.py @@ -6,7 +6,6 @@ import httpx import pytest from langchain_core.tools import ToolException - from neuroagent.tools import GetTracesTool from neuroagent.tools.traces_tool import TracesOutput From 6fe1e819bd6d115e282b0a9c19a45fad26a5192c Mon Sep 17 00:00:00 2001 From: cszsolnai Date: Wed, 2 Oct 2024 13:44:29 +0200 Subject: [PATCH 25/25] lint --- tests/agents/test_simple_agent.py | 1 + tests/agents/test_simple_chat_agent.py | 1 + tests/app/database/test_threads.py | 7 ++++--- tests/app/database/test_tools.py | 1 + tests/app/test_config.py | 3 ++- tests/app/test_dependencies.py | 5 +++-- tests/app/test_main.py | 1 + tests/app/test_middleware.py | 1 + tests/conftest.py | 7 ++++--- tests/test_cell_types.py | 1 + tests/test_resolving.py | 1 + tests/test_utils.py | 1 + tests/tools/test_base_tool.py | 3 ++- tests/tools/test_electrophys_tool.py | 1 + tests/tools/test_get_me_model_tool.py | 1 + tests/tools/test_get_morpho_tool.py | 1 + tests/tools/test_kg_morpho_features_tool.py | 1 + tests/tools/test_literature_search_tool.py | 1 + tests/tools/test_morphology_features_tool.py | 1 + tests/tools/test_resolve_br_tool.py | 1 + tests/tools/test_traces_tool.py | 1 + 21 files changed, 31 insertions(+), 10 deletions(-) diff --git a/tests/agents/test_simple_agent.py b/tests/agents/test_simple_agent.py index a31cf91..0f0ca1d 100644 --- a/tests/agents/test_simple_agent.py +++ b/tests/agents/test_simple_agent.py @@ -4,6 +4,7 @@ from pathlib import Path import pytest + from neuroagent.agents import AgentOutput, AgentStep, SimpleAgent diff --git a/tests/agents/test_simple_chat_agent.py b/tests/agents/test_simple_chat_agent.py index c7e0a92..e0f5dea 100644 --- a/tests/agents/test_simple_chat_agent.py +++ b/tests/agents/test_simple_chat_agent.py @@ -6,6 +6,7 @@ import pytest from langchain_core.messages import HumanMessage, ToolMessage from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver + from neuroagent.agents import AgentOutput, AgentStep, SimpleChatAgent diff --git a/tests/app/database/test_threads.py b/tests/app/database/test_threads.py index 7807826..dfc3313 100644 --- a/tests/app/database/test_threads.py +++ b/tests/app/database/test_threads.py @@ -1,13 +1,14 @@ """Test of the thread router.""" import pytest +from sqlalchemy import MetaData, create_engine +from sqlalchemy.orm import Session +from sqlalchemy.sql.expression import Select + from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_language_model, get_settings from neuroagent.app.main import app from neuroagent.app.routers.database.schemas import GetThreadsOutput -from sqlalchemy import MetaData, create_engine -from sqlalchemy.orm import Session -from sqlalchemy.sql.expression import Select def test_create_thread(patch_required_env, app_client, db_connection): diff --git a/tests/app/database/test_tools.py b/tests/app/database/test_tools.py index a5f55e0..03f2cf0 100644 --- a/tests/app/database/test_tools.py +++ b/tests/app/database/test_tools.py @@ -1,6 +1,7 @@ """Test of the tool router.""" import pytest + from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_language_model, get_settings from neuroagent.app.main import app diff --git a/tests/app/test_config.py b/tests/app/test_config.py index 459d457..38191f8 100644 --- a/tests/app/test_config.py +++ b/tests/app/test_config.py @@ -1,9 +1,10 @@ """Test config""" import pytest -from neuroagent.app.config import Settings from pydantic import ValidationError +from neuroagent.app.config import Settings + def test_required(monkeypatch, patch_required_env): settings = Settings() diff --git a/tests/app/test_dependencies.py b/tests/app/test_dependencies.py index 5cca93f..5af7ea5 100644 --- a/tests/app/test_dependencies.py +++ b/tests/app/test_dependencies.py @@ -12,6 +12,9 @@ from langchain_openai import ChatOpenAI from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver from langgraph.checkpoint.sqlite.aio import AsyncSqliteSaver +from sqlalchemy import create_engine +from sqlalchemy.orm import Session + from neuroagent.agents import SimpleAgent, SimpleChatAgent from neuroagent.app.dependencies import ( Settings, @@ -46,8 +49,6 @@ LiteratureSearchTool, MorphologyFeatureTool, ) -from sqlalchemy import create_engine -from sqlalchemy.orm import Session def test_get_settings(monkeypatch, patch_required_env): diff --git a/tests/app/test_main.py b/tests/app/test_main.py index 79fe9a8..3827ad8 100644 --- a/tests/app/test_main.py +++ b/tests/app/test_main.py @@ -2,6 +2,7 @@ from unittest.mock import patch from fastapi.testclient import TestClient + from neuroagent.app.dependencies import get_settings from neuroagent.app.main import app diff --git a/tests/app/test_middleware.py b/tests/app/test_middleware.py index 2707d4d..5a9bdcf 100644 --- a/tests/app/test_middleware.py +++ b/tests/app/test_middleware.py @@ -5,6 +5,7 @@ import pytest from fastapi.requests import Request from fastapi.responses import Response + from neuroagent.app.config import Settings from neuroagent.app.middleware import strip_path_prefix diff --git a/tests/conftest.py b/tests/conftest.py index d4c5f6d..c49e3a9 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -8,13 +8,14 @@ from httpx import AsyncClient from langchain_core.language_models.fake_chat_models import GenericFakeChatModel from langchain_core.messages import AIMessage +from sqlalchemy import MetaData, create_engine +from sqlalchemy.exc import OperationalError +from sqlalchemy.orm import Session + from neuroagent.app.config import Settings from neuroagent.app.dependencies import get_kg_token, get_settings from neuroagent.app.main import app from neuroagent.tools import GetMorphoTool -from sqlalchemy import MetaData, create_engine -from sqlalchemy.exc import OperationalError -from sqlalchemy.orm import Session @pytest.fixture(name="app_client") diff --git a/tests/test_cell_types.py b/tests/test_cell_types.py index 0596534..930ec71 100644 --- a/tests/test_cell_types.py +++ b/tests/test_cell_types.py @@ -3,6 +3,7 @@ from pathlib import Path import pytest + from neuroagent.cell_types import CellTypesMeta, get_celltypes_descendants CELL_TYPES_FILE = Path(__file__).parent / "data" / "kg_cell_types_hierarchy_test.json" diff --git a/tests/test_resolving.py b/tests/test_resolving.py index 4393b76..6d4f25a 100644 --- a/tests/test_resolving.py +++ b/tests/test_resolving.py @@ -1,5 +1,6 @@ import pytest from httpx import AsyncClient + from neuroagent.resolving import ( es_resolve, escape_punctuation, diff --git a/tests/test_utils.py b/tests/test_utils.py index 9e9af8b..403dddc 100644 --- a/tests/test_utils.py +++ b/tests/test_utils.py @@ -5,6 +5,7 @@ import pytest from httpx import AsyncClient + from neuroagent.schemas import KGMetadata from neuroagent.utils import ( RegionMeta, diff --git a/tests/tools/test_base_tool.py b/tests/tools/test_base_tool.py index fb9ab17..c29bc6c 100644 --- a/tests/tools/test_base_tool.py +++ b/tests/tools/test_base_tool.py @@ -4,9 +4,10 @@ from langchain_core.messages import AIMessage, HumanMessage from langchain_core.tools import ToolException from langgraph.prebuilt import create_react_agent -from neuroagent.tools.base_tool import BasicTool from pydantic import BaseModel +from neuroagent.tools.base_tool import BasicTool + class input_for_test(BaseModel): test_str: str diff --git a/tests/tools/test_electrophys_tool.py b/tests/tools/test_electrophys_tool.py index 6705c2a..a58db53 100644 --- a/tests/tools/test_electrophys_tool.py +++ b/tests/tools/test_electrophys_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import ElectrophysFeatureTool from neuroagent.tools.electrophys_tool import ( CALCULATED_FEATURES, diff --git a/tests/tools/test_get_me_model_tool.py b/tests/tools/test_get_me_model_tool.py index 0627d5f..2366b59 100644 --- a/tests/tools/test_get_me_model_tool.py +++ b/tests/tools/test_get_me_model_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools.get_me_model_tool import GetMEModelTool, MEModelOutput diff --git a/tests/tools/test_get_morpho_tool.py b/tests/tools/test_get_morpho_tool.py index d3ef4ab..87fdcbb 100644 --- a/tests/tools/test_get_morpho_tool.py +++ b/tests/tools/test_get_morpho_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import GetMorphoTool from neuroagent.tools.get_morpho_tool import KnowledgeGraphOutput diff --git a/tests/tools/test_kg_morpho_features_tool.py b/tests/tools/test_kg_morpho_features_tool.py index 2f5473c..b346e26 100644 --- a/tests/tools/test_kg_morpho_features_tool.py +++ b/tests/tools/test_kg_morpho_features_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import KGMorphoFeatureTool from neuroagent.tools.kg_morpho_features_tool import ( FeatRangeInput, diff --git a/tests/tools/test_literature_search_tool.py b/tests/tools/test_literature_search_tool.py index 0f58728..93adf4f 100644 --- a/tests/tools/test_literature_search_tool.py +++ b/tests/tools/test_literature_search_tool.py @@ -4,6 +4,7 @@ import httpx import pytest + from neuroagent.tools import LiteratureSearchTool from neuroagent.tools.literature_search_tool import ParagraphMetadata diff --git a/tests/tools/test_morphology_features_tool.py b/tests/tools/test_morphology_features_tool.py index 22943e6..92a311f 100644 --- a/tests/tools/test_morphology_features_tool.py +++ b/tests/tools/test_morphology_features_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import MorphologyFeatureTool from neuroagent.tools.morphology_features_tool import MorphologyFeatureOutput diff --git a/tests/tools/test_resolve_br_tool.py b/tests/tools/test_resolve_br_tool.py index 697a6ef..31f893d 100644 --- a/tests/tools/test_resolve_br_tool.py +++ b/tests/tools/test_resolve_br_tool.py @@ -2,6 +2,7 @@ import pytest from httpx import AsyncClient + from neuroagent.tools import ResolveBrainRegionTool from neuroagent.tools.resolve_brain_region_tool import ( BRResolveOutput, diff --git a/tests/tools/test_traces_tool.py b/tests/tools/test_traces_tool.py index d0689aa..16f014c 100644 --- a/tests/tools/test_traces_tool.py +++ b/tests/tools/test_traces_tool.py @@ -6,6 +6,7 @@ import httpx import pytest from langchain_core.tools import ToolException + from neuroagent.tools import GetTracesTool from neuroagent.tools.traces_tool import TracesOutput