@@ -697,6 +697,138 @@ async def test_bind_param_async_callable_value_success(self, tool_name, client):
697
697
bound_async_callable .assert_awaited_once ()
698
698
699
699
700
+ @pytest .mark .asyncio
701
+ async def test_bind_param_success (self , tool_name , client ):
702
+ """Tests 'bind_param' with a bound parameter specified."""
703
+ tool = await client .load_tool (tool_name )
704
+
705
+ assert len (tool .__signature__ .parameters ) == 2
706
+ assert "argA" in tool .__signature__ .parameters
707
+
708
+ tool = tool .bind_param ("argA" , 5 )
709
+
710
+ assert len (tool .__signature__ .parameters ) == 1
711
+ assert "argA" not in tool .__signature__ .parameters
712
+
713
+ res = await tool (True )
714
+ assert "argA" in res
715
+
716
+ @pytest .mark .asyncio
717
+ async def test_bind_callable_param_success (self , tool_name , client ):
718
+ """Tests 'bind_param' with a bound parameter specified."""
719
+ tool = await client .load_tool (tool_name )
720
+
721
+ assert len (tool .__signature__ .parameters ) == 2
722
+ assert "argA" in tool .__signature__ .parameters
723
+
724
+ tool = tool .bind_param ("argA" , lambda : 5 )
725
+
726
+ assert len (tool .__signature__ .parameters ) == 1
727
+ assert "argA" not in tool .__signature__ .parameters
728
+
729
+ res = await tool (True )
730
+ assert "argA" in res
731
+
732
+ @pytest .mark .asyncio
733
+ async def test_bind_param_fail (self , tool_name , client ):
734
+ """Tests 'bind_param' with a bound parameter that doesn't exist."""
735
+ tool = await client .load_tool (tool_name )
736
+
737
+ assert len (tool .__signature__ .parameters ) == 2
738
+ assert "argA" in tool .__signature__ .parameters
739
+
740
+ with pytest .raises (Exception ) as e :
741
+ tool .bind_param ("argC" , lambda : 5 )
742
+ assert "unable to bind parameters: no parameter named argC" in str (e .value )
743
+
744
+ @pytest .mark .asyncio
745
+ async def test_rebind_param_fail (self , tool_name , client ):
746
+ """
747
+ Tests that 'bind_param' fails when attempting to re-bind a
748
+ parameter that has already been bound.
749
+ """
750
+ tool = await client .load_tool (tool_name )
751
+
752
+ assert len (tool .__signature__ .parameters ) == 2
753
+ assert "argA" in tool .__signature__ .parameters
754
+
755
+ tool_with_bound_param = tool .bind_param ("argA" , lambda : 10 )
756
+
757
+ assert len (tool_with_bound_param .__signature__ .parameters ) == 1
758
+ assert "argA" not in tool_with_bound_param .__signature__ .parameters
759
+
760
+ with pytest .raises (ValueError ) as e :
761
+ tool_with_bound_param .bind_param ("argA" , lambda : 20 )
762
+
763
+ assert "cannot re-bind parameter: parameter 'argA' is already bound" in str (
764
+ e .value
765
+ )
766
+
767
+ @pytest .mark .asyncio
768
+ async def test_bind_param_static_value_success (self , tool_name , client ):
769
+ """
770
+ Tests bind_param method with a static value.
771
+ """
772
+
773
+ bound_value = "Test value"
774
+
775
+ tool = await client .load_tool (tool_name )
776
+ bound_tool = tool .bind_param ("argB" , bound_value )
777
+
778
+ assert bound_tool is not tool
779
+ assert "argB" not in bound_tool .__signature__ .parameters
780
+ assert "argA" in bound_tool .__signature__ .parameters
781
+
782
+ passed_value_a = 42
783
+ res_payload = await bound_tool (argA = passed_value_a )
784
+
785
+ assert res_payload == {"argA" : passed_value_a , "argB" : bound_value }
786
+
787
+ @pytest .mark .asyncio
788
+ async def test_bind_param_sync_callable_value_success (self , tool_name , client ):
789
+ """
790
+ Tests bind_param method with a sync callable value.
791
+ """
792
+
793
+ bound_value_result = True
794
+ bound_sync_callable = Mock (return_value = bound_value_result )
795
+
796
+ tool = await client .load_tool (tool_name )
797
+ bound_tool = tool .bind_param ("argB" , bound_sync_callable )
798
+
799
+ assert bound_tool is not tool
800
+ assert "argB" not in bound_tool .__signature__ .parameters
801
+ assert "argA" in bound_tool .__signature__ .parameters
802
+
803
+ passed_value_a = 42
804
+ res_payload = await bound_tool (argA = passed_value_a )
805
+
806
+ assert res_payload == {"argA" : passed_value_a , "argB" : bound_value_result }
807
+ bound_sync_callable .assert_called_once ()
808
+
809
+ @pytest .mark .asyncio
810
+ async def test_bind_param_async_callable_value_success (self , tool_name , client ):
811
+ """
812
+ Tests bind_param method with an async callable value.
813
+ """
814
+
815
+ bound_value_result = True
816
+ bound_async_callable = AsyncMock (return_value = bound_value_result )
817
+
818
+ tool = await client .load_tool (tool_name )
819
+ bound_tool = tool .bind_param ("argB" , bound_async_callable )
820
+
821
+ assert bound_tool is not tool
822
+ assert "argB" not in bound_tool .__signature__ .parameters
823
+ assert "argA" in bound_tool .__signature__ .parameters
824
+
825
+ passed_value_a = 42
826
+ res_payload = await bound_tool (argA = passed_value_a )
827
+
828
+ assert res_payload == {"argA" : passed_value_a , "argB" : bound_value_result }
829
+ bound_async_callable .assert_awaited_once ()
830
+
831
+
700
832
class TestUnusedParameterValidation :
701
833
"""
702
834
Tests for validation errors related to unused auth tokens or bound
0 commit comments