CoolFace
Apppublic

findEthics/Atlas

sourceHugging Faceupdated 1y agoView on Hugging Face
0likes
test_chat_api.py596 linesDownload Raw Back to integration
1"""2Integration tests for chat API with user authentication3 4Consolidated from:5- test_chat_integration_user_auth.py6- test_chat_analytics.py (integration portions)7- Parts of test_user_authentication_comprehensive.py (integration portions)8"""9 10import asyncio11import time12 13import pytest14 15from tests.utilities import HTTPHelpers, MockHelpers, TestHelpers, ValidationHelpers, authenticated_chat_request, empty_user_ids, invalid_user_ids, sample_chat_request, skip_if_no_server, valid_user_ids16 17    HTTPHelpers, TestHelpers, MockHelpers, ValidationHelpers,18    skip_if_no_server, authenticated_chat_request, sample_chat_request,19    valid_user_ids, invalid_user_ids, empty_user_ids20)21 22 23class TestChatRequestValidation:24    """Test chat request validation with user_id"""25    26    @pytest.mark.asyncio27    @skip_if_no_server()28    async def test_valid_user_id_formats(self, valid_user_ids):29        """Test chat requests with various valid user_id formats"""30        for user_id in valid_user_ids[:5]:  # Test first 5 to avoid too many requests31            chat_data = {32                "prompt": f"Test message for user {user_id}",33                "max_new_tokens": 50,34                "use_search": False,35                "temperature": 0.7,36                "user_id": user_id37            }38            39            response = await HTTPHelpers.make_chat_request(chat_data)40            if response is None:41                pytest.skip("Server not available")42            43            session_id = HTTPHelpers.assert_successful_chat_response(response)44            assert session_id is not None45    46    @pytest.mark.asyncio47    @skip_if_no_server()48    async def test_invalid_user_id_formats(self, invalid_user_ids):49        """Test chat requests with invalid user_id formats"""50        for user_id in invalid_user_ids[:10]:  # Test first 10 to avoid too many requests51            chat_data = {52                "prompt": f"Test message for invalid user {user_id}",53                "max_new_tokens": 50,54                "use_search": False,55                "temperature": 0.7,56                "user_id": user_id57            }58            59            response = await HTTPHelpers.make_chat_request(chat_data)60            if response is None:61                pytest.skip("Server not available")62            63            HTTPHelpers.assert_failed_chat_response(response, expected_status=400)64    65    @pytest.mark.asyncio66    @skip_if_no_server()67    async def test_empty_user_id_handling(self, empty_user_ids):68        """Test that empty user_id is treated as anonymous"""69        for empty_user_id in empty_user_ids:70            chat_data = {71                "prompt": "Test message with empty user_id",72                "max_new_tokens": 50,73                "use_search": False,74                "temperature": 0.7,75                "user_id": empty_user_id76            }77            78            response = await HTTPHelpers.make_chat_request(chat_data)79            if response is None:80                pytest.skip("Server not available")81            82            session_id = HTTPHelpers.assert_successful_chat_response(response)83            assert session_id is not None84    85    @pytest.mark.asyncio86    @skip_if_no_server()87    async def test_missing_user_id_field(self, sample_chat_request):88        """Test that missing user_id field works (backward compatibility)"""89        response = await HTTPHelpers.make_chat_request(sample_chat_request)90        if response is None:91            pytest.skip("Server not available")92        93        session_id = HTTPHelpers.assert_successful_chat_response(response)94        assert session_id is not None95 96 97class TestChatRequestFlow:98    """Test complete chat request flow with user authentication"""99    100    @pytest.mark.asyncio101    @skip_if_no_server()102    async def test_authenticated_user_session_flow(self):103        """Test complete flow for authenticated user"""104        user_id = "test_flow_user"105        106        # First request - creates new session107        chat_data1 = {108            "prompt": "First message from authenticated user",109            "max_new_tokens": 50,110            "use_search": False,111            "temperature": 0.7,112            "user_id": user_id113        }114        115        response1 = await HTTPHelpers.make_chat_request(chat_data1)116        if response1 is None:117            pytest.skip("Server not available")118        119        session_id = HTTPHelpers.assert_successful_chat_response(response1)120        121        # Second request - uses existing session122        chat_data2 = {123            "prompt": "Second message from same user",124            "max_new_tokens": 50,125            "use_search": True,  # Enable search this time126            "temperature": 0.7,127            "user_id": user_id128        }129        130        response2 = await HTTPHelpers.make_chat_request(chat_data2, session_id=session_id)131        if response2 is None:132            pytest.skip("Server not available")133        134        session_id2 = HTTPHelpers.assert_successful_chat_response(response2)135        136        # Should return same session ID137        assert session_id2 == session_id138        139        # Wait for data to be written140        await TestHelpers.wait_for_data_persistence(2.0)141        142        # Verify data was stored correctly143        session_valid = await TestHelpers.verify_session_data(144            session_id, user_id, expected_messages=2145        )146        assert session_valid147    148    @pytest.mark.asyncio149    @skip_if_no_server()150    async def test_anonymous_user_session_flow(self):151        """Test complete flow for anonymous user"""152        # First request - anonymous user153        chat_data1 = {154            "prompt": "First message from anonymous user",155            "max_new_tokens": 50,156            "use_search": False,157            "temperature": 0.7158            # No user_id field159        }160        161        response1 = await HTTPHelpers.make_chat_request(chat_data1)162        if response1 is None:163            pytest.skip("Server not available")164        165        session_id = HTTPHelpers.assert_successful_chat_response(response1)166        167        # Second request - same anonymous user168        chat_data2 = {169            "prompt": "Second message from anonymous user",170            "max_new_tokens": 50,171            "use_search": True,172            "temperature": 0.7173            # No user_id field174        }175        176        response2 = await HTTPHelpers.make_chat_request(chat_data2, session_id=session_id)177        if response2 is None:178            pytest.skip("Server not available")179        180        session_id2 = HTTPHelpers.assert_successful_chat_response(response2)181        assert session_id2 == session_id182        183        # Wait for data to be written184        await TestHelpers.wait_for_data_persistence(2.0)185        186        # Verify data was stored correctly (user_id should be None)187        session_valid = await TestHelpers.verify_session_data(188            session_id, None, expected_messages=2189        )190        assert session_valid191    192    @pytest.mark.asyncio193    @skip_if_no_server()194    async def test_mixed_user_sessions(self):195        """Test that different users get different sessions"""196        user_id1 = "test_user_1"197        user_id2 = "test_user_2"198        199        # Request from user 1200        chat_data1 = {201            "prompt": "Message from user 1",202            "max_new_tokens": 50,203            "use_search": False,204            "temperature": 0.7,205            "user_id": user_id1206        }207        208        response1 = await HTTPHelpers.make_chat_request(chat_data1)209        if response1 is None:210            pytest.skip("Server not available")211        212        session_id1 = HTTPHelpers.assert_successful_chat_response(response1)213        214        # Request from user 2215        chat_data2 = {216            "prompt": "Message from user 2",217            "max_new_tokens": 50,218            "use_search": False,219            "temperature": 0.7,220            "user_id": user_id2221        }222        223        response2 = await HTTPHelpers.make_chat_request(chat_data2)224        if response2 is None:225            pytest.skip("Server not available")226        227        session_id2 = HTTPHelpers.assert_successful_chat_response(response2)228        229        # Sessions should be different230        assert session_id1 != session_id2231    232    @pytest.mark.asyncio233    @skip_if_no_server()234    async def test_session_continuation_with_user_id(self):235        """Test that sessions can be continued with proper user_id"""236        user_id = "test_continuation_user"237        238        # First request creates session239        chat_data1 = {240            "prompt": "First message in session",241            "max_new_tokens": 50,242            "use_search": False,243            "temperature": 0.7,244            "user_id": user_id245        }246        247        response1 = await HTTPHelpers.make_chat_request(chat_data1)248        if response1 is None:249            pytest.skip("Server not available")250        251        session_id = HTTPHelpers.assert_successful_chat_response(response1)252        253        # Second request continues same session with same user_id254        chat_data2 = {255            "prompt": "Second message in same session",256            "max_new_tokens": 50,257            "use_search": True,258            "temperature": 0.7,259            "user_id": user_id260        }261        262        response2 = await HTTPHelpers.make_chat_request(chat_data2, session_id=session_id)263        if response2 is None:264            pytest.skip("Server not available")265        266        session_id2 = HTTPHelpers.assert_successful_chat_response(response2)267        268        # Should be same session269        assert session_id2 == session_id270 271 272class TestChatAnalyticsIntegration:273    """Test that chat requests properly trigger analytics collection"""274    275    @pytest.mark.asyncio276    @skip_if_no_server()277    async def test_chat_request_creates_analytics_data(self):278        """Test that chat requests create analytics data"""279        user_id = "analytics_integration_user"280        281        chat_data = {282            "prompt": "Test message for analytics collection",283            "max_new_tokens": 100,284            "use_search": True,285            "temperature": 0.7,286            "user_id": user_id287        }288        289        response = await HTTPHelpers.make_chat_request(chat_data)290        if response is None:291            pytest.skip("Server not available")292        293        session_id = HTTPHelpers.assert_successful_chat_response(response)294        295        # Wait for analytics data to be written296        await TestHelpers.wait_for_data_persistence(3.0)297        298        # Verify session was created299        session_valid = await TestHelpers.verify_session_data(300            session_id, user_id, expected_messages=1301        )302        assert session_valid303        304        # Check that we can count the user's data305        session_count = await TestHelpers.count_documents_by_user_id("sessions", user_id)306        message_count = await TestHelpers.count_documents_by_user_id("messages", user_id)307        308        assert session_count >= 1309        assert message_count >= 1310    311    @pytest.mark.asyncio312    @skip_if_no_server()313    async def test_anonymous_chat_request_creates_analytics_data(self):314        """Test that anonymous chat requests create analytics data"""315        chat_data = {316            "prompt": "Test anonymous message for analytics",317            "max_new_tokens": 100,318            "use_search": False,319            "temperature": 0.7320        }321        322        response = await HTTPHelpers.make_chat_request(chat_data)323        if response is None:324            pytest.skip("Server not available")325        326        session_id = HTTPHelpers.assert_successful_chat_response(response)327        328        # Wait for analytics data to be written329        await TestHelpers.wait_for_data_persistence(3.0)330        331        # Verify session was created with null user_id332        session_valid = await TestHelpers.verify_session_data(333            session_id, None, expected_messages=1334        )335        assert session_valid336        337        # Check that we can count anonymous data338        anon_session_count = await TestHelpers.count_documents_by_user_id("sessions", None)339        anon_message_count = await TestHelpers.count_documents_by_user_id("messages", None)340        341        assert anon_session_count >= 1342        assert anon_message_count >= 1343    344    @pytest.mark.asyncio345    @skip_if_no_server()346    async def test_search_analytics_collection(self):347        """Test that search analytics are collected when search is used"""348        user_id = "search_analytics_user"349        350        chat_data = {351            "prompt": "What is the weather like today?",352            "max_new_tokens": 100,353            "use_search": True,  # Enable search354            "temperature": 0.7,355            "user_id": user_id356        }357        358        response = await HTTPHelpers.make_chat_request(chat_data)359        if response is None:360            pytest.skip("Server not available")361        362        session_id = HTTPHelpers.assert_successful_chat_response(response)363        364        # Wait for analytics data to be written365        await TestHelpers.wait_for_data_persistence(5.0)  # Search might take longer366        367        # Verify session and message were created368        session_valid = await TestHelpers.verify_session_data(369            session_id, user_id, expected_messages=1370        )371        assert session_valid372        373        # Check for search analytics (if search was actually performed)374        search_count = await TestHelpers.count_documents_by_user_id("search_analytics", user_id)375        # Note: Search analytics might be 0 if search was not actually performed376        # This is acceptable as it depends on the search implementation377        assert search_count >= 0378 379 380class TestChatRequestPerformance:381    """Test performance of chat requests with user authentication"""382    383    @pytest.mark.asyncio384    @skip_if_no_server()385    async def test_authenticated_request_performance(self):386        """Test performance of authenticated chat requests"""387        user_id = "perf_test_user"388        389        # Warm up request390        warmup_data = {391            "prompt": "Warmup message",392            "max_new_tokens": 50,393            "use_search": False,394            "temperature": 0.7,395            "user_id": user_id396        }397        398        warmup_response = await HTTPHelpers.make_chat_request(warmup_data)399        if warmup_response is None:400            pytest.skip("Server not available")401        402        # Performance test403        num_requests = 3  # Keep small for CI404        total_time = 0405        406        for i in range(num_requests):407            chat_data = {408                "prompt": f"Performance test message {i}",409                "max_new_tokens": 50,410                "use_search": False,411                "temperature": 0.7,412                "user_id": user_id413            }414            415            start_time = time.time()416            response = await HTTPHelpers.make_chat_request(chat_data)417            end_time = time.time()418            419            if response is None:420                pytest.skip("Server not available")421            422            HTTPHelpers.assert_successful_chat_response(response)423            424            request_time = end_time - start_time425            total_time += request_time426        427        avg_time = total_time / num_requests428        429        # Performance assertion (requests should be reasonably fast)430        assert avg_time < 30.0, f"Requests too slow: {avg_time:.2f}s average"431    432    @pytest.mark.asyncio433    @skip_if_no_server()434    async def test_anonymous_vs_authenticated_performance(self):435        """Compare performance between anonymous and authenticated requests"""436        # Test anonymous requests437        anonymous_times = []438        for i in range(2):  # Keep small for CI439            chat_data = {440                "prompt": f"Anonymous performance test {i}",441                "max_new_tokens": 50,442                "use_search": False,443                "temperature": 0.7444            }445            446            start_time = time.time()447            response = await HTTPHelpers.make_chat_request(chat_data)448            end_time = time.time()449            450            if response is None:451                pytest.skip("Server not available")452            453            HTTPHelpers.assert_successful_chat_response(response)454            anonymous_times.append(end_time - start_time)455        456        # Test authenticated requests457        authenticated_times = []458        for i in range(2):  # Keep small for CI459            chat_data = {460                "prompt": f"Authenticated performance test {i}",461                "max_new_tokens": 50,462                "use_search": False,463                "temperature": 0.7,464                "user_id": "perf_auth_user"465            }466            467            start_time = time.time()468            response = await HTTPHelpers.make_chat_request(chat_data)469            end_time = time.time()470            471            if response is None:472                pytest.skip("Server not available")473            474            HTTPHelpers.assert_successful_chat_response(response)475            authenticated_times.append(end_time - start_time)476        477        avg_anonymous = sum(anonymous_times) / len(anonymous_times)478        avg_authenticated = sum(authenticated_times) / len(authenticated_times)479        480        # Performance should be similar (user authentication shouldn't add significant overhead)481        time_difference = abs(avg_authenticated - avg_anonymous)482        assert time_difference < 10.0, f"Too much performance difference: {time_difference:.2f}s"483 484 485class TestChatRequestErrorHandling:486    """Test error handling in chat requests"""487    488    @pytest.mark.asyncio489    @skip_if_no_server()490    async def test_malformed_request_handling(self):491        """Test handling of malformed requests"""492        malformed_requests = [493            {},  # Empty request494            {"prompt": ""},  # Empty prompt495            {"user_id": "valid_user"},  # Missing prompt496            {"prompt": "test", "user_id": "invalid@user"},  # Invalid user_id497        ]498        499        for malformed_data in malformed_requests:500            response = await HTTPHelpers.make_chat_request(malformed_data)501            if response is None:502                pytest.skip("Server not available")503            504            # Should return error status505            assert response.status_code >= 400506    507    @pytest.mark.asyncio508    @skip_if_no_server()509    async def test_request_with_invalid_session_id(self):510        """Test request with invalid session ID"""511        chat_data = {512            "prompt": "Test message with invalid session",513            "max_new_tokens": 50,514            "use_search": False,515            "temperature": 0.7,516            "user_id": "test_user"517        }518        519        # Use invalid session ID520        invalid_session_id = "invalid-session-id-12345"521        522        response = await HTTPHelpers.make_chat_request(chat_data, session_id=invalid_session_id)523        if response is None:524            pytest.skip("Server not available")525        526        # Should still work (create new session or handle gracefully)527        # The exact behavior depends on implementation528        assert response.status_code in [200, 400, 404]529 530 531class TestChatRequestWithMocks:532    """Test chat requests with mocked dependencies"""533    534    @pytest.mark.asyncio535    async def test_chat_request_with_mocked_ai(self):536        """Test chat request with mocked AI response"""537        with MockHelpers.mock_gemini_inference("Mocked AI response"), \538             MockHelpers.mock_web_search([]):539            540            chat_data = {541                "prompt": "Test prompt for mocked AI",542                "max_new_tokens": 100,543                "use_search": False,544                "temperature": 0.7,545                "user_id": "mock_test_user"546            }547            548            response = await HTTPHelpers.make_chat_request(chat_data)549            if response is None:550                pytest.skip("Server not available")551            552            HTTPHelpers.assert_successful_chat_response(response)553            554            # Verify the mocked response555            data = response.json()556            assert "Mocked AI response" in data["response"]557    558    @pytest.mark.asyncio559    async def test_chat_request_with_mocked_search(self):560        """Test chat request with mocked search results"""561        mock_results = [562            {"title": "Test Result", "url": "https://example.com", "snippet": "Test snippet"}563        ]564        565        with MockHelpers.mock_gemini_inference("AI response with search"), \566             MockHelpers.mock_web_search(mock_results):567            568            chat_data = {569                "prompt": "Test prompt with search",570                "max_new_tokens": 100,571                "use_search": True,572                "temperature": 0.7,573                "user_id": "search_mock_user"574            }575            576            response = await HTTPHelpers.make_chat_request(chat_data)577            if response is None:578                pytest.skip("Server not available")579            580            HTTPHelpers.assert_successful_chat_response(response)581 582 583if __name__ == "__main__":584    # Run tests manually for debugging585    async def run_basic_tests():586        test_validation = TestChatRequestValidation()587        # Note: These would need fixtures to run manually588        print("✅ Chat request validation tests defined")589        590        test_flow = TestChatRequestFlow()591        print("✅ Chat request flow tests defined")592        593        test_analytics = TestChatAnalyticsIntegration()594        print("✅ Chat analytics integration tests defined")595    596    asyncio.run(run_basic_tests())