UPDATE
This commit is contained in:
@@ -0,0 +1,52 @@
|
||||
from unittest.mock import patch
|
||||
|
||||
from django.test import SimpleTestCase
|
||||
|
||||
from rag.chat import build_chat_context
|
||||
|
||||
|
||||
class ChatContextTests(SimpleTestCase):
|
||||
@patch("rag.chat.search_with_query")
|
||||
@patch("rag.chat._rank_text_chunks_by_query")
|
||||
@patch("rag.chat.chunk_text")
|
||||
def test_build_chat_context_combines_farm_and_kb_context(
|
||||
self,
|
||||
mock_chunk_text,
|
||||
mock_rank_text_chunks_by_query,
|
||||
mock_search_with_query,
|
||||
):
|
||||
mock_chunk_text.return_value = ["chunk-a", "chunk-b"]
|
||||
mock_rank_text_chunks_by_query.return_value = ["chunk-b"]
|
||||
mock_search_with_query.return_value = [
|
||||
{"text": "kb text 1"},
|
||||
{"text": "kb text 2"},
|
||||
]
|
||||
|
||||
context = build_chat_context(
|
||||
query="وضعیت مزرعه چطور است؟",
|
||||
farm_uuid="farm-123",
|
||||
farm_details={"sensor_payload": {"sensor-7-1": {"soil_moisture": 30}}},
|
||||
)
|
||||
|
||||
self.assertIn("[بخشهای مرتبط بازیابیشده از اطلاعات مزرعه]", context)
|
||||
self.assertIn("chunk-b", context)
|
||||
self.assertIn("[اطلاعات بازیابیشده از پایگاه دانش]", context)
|
||||
self.assertIn("kb text 1", context)
|
||||
self.assertIn("kb text 2", context)
|
||||
|
||||
@patch("rag.chat.search_with_query", return_value=[])
|
||||
@patch("rag.chat._rank_text_chunks_by_query", return_value=[])
|
||||
@patch("rag.chat.chunk_text", return_value=["farm chunk"])
|
||||
def test_build_chat_context_falls_back_to_full_farm_context(
|
||||
self,
|
||||
_mock_chunk_text,
|
||||
_mock_rank_text_chunks_by_query,
|
||||
_mock_search_with_query,
|
||||
):
|
||||
context = build_chat_context(
|
||||
query="رطوبت چقدر است؟",
|
||||
farm_uuid="farm-123",
|
||||
farm_details={"sensor_payload": {"sensor-7-1": {"soil_moisture": 30}}},
|
||||
)
|
||||
|
||||
self.assertEqual(context, "")
|
||||
@@ -0,0 +1,91 @@
|
||||
import uuid
|
||||
from datetime import date
|
||||
from unittest.mock import Mock, patch
|
||||
|
||||
from django.test import TestCase
|
||||
|
||||
from farm_data.models import SensorData
|
||||
from irrigation.models import IrrigationMethod
|
||||
from location_data.models import SoilLocation
|
||||
from plant.models import Plant
|
||||
from rag.services.fertilization import get_fertilization_recommendation
|
||||
from rag.services.irrigation import get_irrigation_recommendation
|
||||
from weather.models import WeatherForecast
|
||||
|
||||
|
||||
class RecommendationServiceDefaultsTests(TestCase):
|
||||
def setUp(self):
|
||||
self.location = SoilLocation.objects.create(
|
||||
latitude="35.700000",
|
||||
longitude="51.400000",
|
||||
farm_boundary={"type": "Polygon", "coordinates": []},
|
||||
)
|
||||
WeatherForecast.objects.create(
|
||||
location=self.location,
|
||||
forecast_date=date(2026, 4, 10),
|
||||
temperature_min=12.0,
|
||||
temperature_max=23.0,
|
||||
temperature_mean=18.0,
|
||||
)
|
||||
self.plant = Plant.objects.create(name="گوجهفرنگی")
|
||||
self.irrigation_method = IrrigationMethod.objects.create(name="آبیاری قطرهای")
|
||||
self.farm_uuid = uuid.uuid4()
|
||||
self.farm = SensorData.objects.create(
|
||||
farm_uuid=self.farm_uuid,
|
||||
center_location=self.location,
|
||||
irrigation_method=self.irrigation_method,
|
||||
sensor_payload={"sensor-7-1": {"soil_moisture": 30.0}},
|
||||
)
|
||||
self.farm.plants.set([self.plant])
|
||||
|
||||
@patch("rag.services.irrigation.calculate_forecast_water_needs", return_value=[])
|
||||
@patch("rag.services.irrigation.resolve_kc", return_value=0.9)
|
||||
@patch("rag.services.irrigation.resolve_crop_profile", return_value={})
|
||||
@patch("rag.services.irrigation.build_irrigation_method_text", return_value="method text")
|
||||
@patch("rag.services.irrigation.build_plant_text", return_value="plant text")
|
||||
@patch("rag.services.irrigation.build_rag_context", return_value="")
|
||||
@patch("rag.services.irrigation.get_chat_client")
|
||||
def test_irrigation_recommendation_uses_farm_relations_when_request_omits_names(
|
||||
self,
|
||||
mock_get_chat_client,
|
||||
mock_build_rag_context,
|
||||
mock_build_plant_text,
|
||||
mock_build_irrigation_method_text,
|
||||
_mock_resolve_crop_profile,
|
||||
_mock_resolve_kc,
|
||||
_mock_calculate_forecast_water_needs,
|
||||
):
|
||||
mock_response = Mock()
|
||||
mock_response.choices = [Mock(message=Mock(content='{"plan": {"frequencyPerWeek": 2}}'))]
|
||||
mock_get_chat_client.return_value.chat.completions.create.return_value = mock_response
|
||||
|
||||
result = get_irrigation_recommendation(
|
||||
sensor_uuid=str(self.farm_uuid),
|
||||
growth_stage="میوهدهی",
|
||||
)
|
||||
|
||||
self.assertEqual(result["plan"]["frequencyPerWeek"], 2)
|
||||
mock_build_rag_context.assert_called_once()
|
||||
mock_build_plant_text.assert_called_once_with("گوجهفرنگی", "میوهدهی")
|
||||
mock_build_irrigation_method_text.assert_called_once_with("آبیاری قطرهای")
|
||||
|
||||
@patch("rag.services.fertilization.build_plant_text", return_value="plant text")
|
||||
@patch("rag.services.fertilization.build_rag_context", return_value="")
|
||||
@patch("rag.services.fertilization.get_chat_client")
|
||||
def test_fertilization_recommendation_uses_farm_plant_when_request_omits_name(
|
||||
self,
|
||||
mock_get_chat_client,
|
||||
_mock_build_rag_context,
|
||||
mock_build_plant_text,
|
||||
):
|
||||
mock_response = Mock()
|
||||
mock_response.choices = [Mock(message=Mock(content='{"plan": {"npkRatio": "20-20-20"}}'))]
|
||||
mock_get_chat_client.return_value.chat.completions.create.return_value = mock_response
|
||||
|
||||
result = get_fertilization_recommendation(
|
||||
sensor_uuid=str(self.farm_uuid),
|
||||
growth_stage="رویشی",
|
||||
)
|
||||
|
||||
self.assertEqual(result["plan"]["npkRatio"], "20-20-20")
|
||||
mock_build_plant_text.assert_called_once_with("گوجهفرنگی", "رویشی")
|
||||
Reference in New Issue
Block a user