@@ -633,5 +633,259 @@ private Task ExecuteVerifyTest(AddOptions options, string config = INITIAL_CONFI
633633
634634 return Verify ( updatedRuntimeConfig , settings ) ;
635635 }
636+
637+ #region MCP Entity Configuration Tests
638+
639+ /// <summary>
640+ /// Test adding table entity with MCP dml-tools enabled or disabled
641+ /// </summary>
642+ [ DataTestMethod ]
643+ [ DataRow ( "true" , "books" , "Book" , DisplayName = "AddTableEntityWithMcpDmlToolsEnabled" ) ]
644+ [ DataRow ( "false" , "authors" , "Author" , DisplayName = "AddTableEntityWithMcpDmlToolsDisabled" ) ]
645+ public Task AddTableEntityWithMcpDmlTools ( string mcpDmlTools , string source , string entity )
646+ {
647+ AddOptions options = new (
648+ source : source ,
649+ permissions : new string [ ] { "anonymous" , "*" } ,
650+ entity : entity ,
651+ description : null ,
652+ sourceType : "table" ,
653+ sourceParameters : null ,
654+ sourceKeyFields : null ,
655+ restRoute : null ,
656+ graphQLType : null ,
657+ fieldsToInclude : Array . Empty < string > ( ) ,
658+ fieldsToExclude : Array . Empty < string > ( ) ,
659+ policyRequest : null ,
660+ policyDatabase : null ,
661+ cacheEnabled : null ,
662+ cacheTtl : null ,
663+ config : TEST_RUNTIME_CONFIG_FILE ,
664+ restMethodsForStoredProcedure : null ,
665+ graphQLOperationForStoredProcedure : null ,
666+ parametersNameCollection : null ,
667+ parametersDescriptionCollection : null ,
668+ parametersRequiredCollection : null ,
669+ parametersDefaultCollection : null ,
670+ fieldsNameCollection : [ ] ,
671+ fieldsAliasCollection : [ ] ,
672+ fieldsDescriptionCollection : [ ] ,
673+ fieldsPrimaryKeyCollection : [ ] ,
674+ mcpDmlTools : mcpDmlTools ,
675+ mcpCustomTool : null
676+ ) ;
677+
678+ VerifySettings settings = new ( ) ;
679+ settings . UseParameters ( mcpDmlTools , source ) ;
680+ return ExecuteVerifyTest ( options , settings : settings ) ;
681+ }
682+
683+ /// <summary>
684+ /// Test adding stored procedure with MCP custom-tool enabled (should serialize as object)
685+ /// </summary>
686+ [ TestMethod ]
687+ public Task AddStoredProcedureWithMcpCustomToolEnabled ( )
688+ {
689+ AddOptions options = new (
690+ source : "dbo.GetBookById" ,
691+ permissions : new string [ ] { "anonymous" , "execute" } ,
692+ entity : "GetBookById" ,
693+ description : null ,
694+ sourceType : "stored-procedure" ,
695+ sourceParameters : null ,
696+ sourceKeyFields : null ,
697+ restRoute : null ,
698+ graphQLType : null ,
699+ fieldsToInclude : Array . Empty < string > ( ) ,
700+ fieldsToExclude : Array . Empty < string > ( ) ,
701+ policyRequest : null ,
702+ policyDatabase : null ,
703+ cacheEnabled : null ,
704+ cacheTtl : null ,
705+ config : TEST_RUNTIME_CONFIG_FILE ,
706+ restMethodsForStoredProcedure : null ,
707+ graphQLOperationForStoredProcedure : null ,
708+ parametersNameCollection : null ,
709+ parametersDescriptionCollection : null ,
710+ parametersRequiredCollection : null ,
711+ parametersDefaultCollection : null ,
712+ fieldsNameCollection : [ ] ,
713+ fieldsAliasCollection : [ ] ,
714+ fieldsDescriptionCollection : [ ] ,
715+ fieldsPrimaryKeyCollection : [ ] ,
716+ mcpDmlTools : null ,
717+ mcpCustomTool : "true"
718+ ) ;
719+ return ExecuteVerifyTest ( options ) ;
720+ }
721+
722+ /// <summary>
723+ /// Test adding stored procedure with both MCP properties set to different values (should serialize as object with both)
724+ /// </summary>
725+ [ TestMethod ]
726+ public Task AddStoredProcedureWithBothMcpProperties ( )
727+ {
728+ AddOptions options = new (
729+ source : "dbo.UpdateBook" ,
730+ permissions : new string [ ] { "anonymous" , "execute" } ,
731+ entity : "UpdateBook" ,
732+ description : null ,
733+ sourceType : "stored-procedure" ,
734+ sourceParameters : null ,
735+ sourceKeyFields : null ,
736+ restRoute : null ,
737+ graphQLType : null ,
738+ fieldsToInclude : Array . Empty < string > ( ) ,
739+ fieldsToExclude : Array . Empty < string > ( ) ,
740+ policyRequest : null ,
741+ policyDatabase : null ,
742+ cacheEnabled : null ,
743+ cacheTtl : null ,
744+ config : TEST_RUNTIME_CONFIG_FILE ,
745+ restMethodsForStoredProcedure : null ,
746+ graphQLOperationForStoredProcedure : null ,
747+ parametersNameCollection : null ,
748+ parametersDescriptionCollection : null ,
749+ parametersRequiredCollection : null ,
750+ parametersDefaultCollection : null ,
751+ fieldsNameCollection : [ ] ,
752+ fieldsAliasCollection : [ ] ,
753+ fieldsDescriptionCollection : [ ] ,
754+ fieldsPrimaryKeyCollection : [ ] ,
755+ mcpDmlTools : "false" ,
756+ mcpCustomTool : "true"
757+ ) ;
758+ return ExecuteVerifyTest ( options ) ;
759+ }
760+
761+ /// <summary>
762+ /// Test adding stored procedure with both MCP properties enabled (common use case)
763+ /// </summary>
764+ [ TestMethod ]
765+ public Task AddStoredProcedureWithBothMcpPropertiesEnabled ( )
766+ {
767+ AddOptions options = new (
768+ source : "dbo.GetAllBooks" ,
769+ permissions : new string [ ] { "anonymous" , "execute" } ,
770+ entity : "GetAllBooks" ,
771+ description : null ,
772+ sourceType : "stored-procedure" ,
773+ sourceParameters : null ,
774+ sourceKeyFields : null ,
775+ restRoute : null ,
776+ graphQLType : null ,
777+ fieldsToInclude : Array . Empty < string > ( ) ,
778+ fieldsToExclude : Array . Empty < string > ( ) ,
779+ policyRequest : null ,
780+ policyDatabase : null ,
781+ cacheEnabled : null ,
782+ cacheTtl : null ,
783+ config : TEST_RUNTIME_CONFIG_FILE ,
784+ restMethodsForStoredProcedure : null ,
785+ graphQLOperationForStoredProcedure : null ,
786+ parametersNameCollection : null ,
787+ parametersDescriptionCollection : null ,
788+ parametersRequiredCollection : null ,
789+ parametersDefaultCollection : null ,
790+ fieldsNameCollection : [ ] ,
791+ fieldsAliasCollection : [ ] ,
792+ fieldsDescriptionCollection : [ ] ,
793+ fieldsPrimaryKeyCollection : [ ] ,
794+ mcpDmlTools : "true" ,
795+ mcpCustomTool : "true"
796+ ) ;
797+ return ExecuteVerifyTest ( options ) ;
798+ }
799+
800+ /// <summary>
801+ /// Test that adding table entity with custom-tool fails validation
802+ /// </summary>
803+ [ TestMethod ]
804+ public void AddTableEntityWithInvalidMcpCustomTool ( )
805+ {
806+ AddOptions options = new (
807+ source : "reviews" ,
808+ permissions : new string [ ] { "anonymous" , "*" } ,
809+ entity : "Review" ,
810+ description : null ,
811+ sourceType : "table" ,
812+ sourceParameters : null ,
813+ sourceKeyFields : null ,
814+ restRoute : null ,
815+ graphQLType : null ,
816+ fieldsToInclude : Array . Empty < string > ( ) ,
817+ fieldsToExclude : Array . Empty < string > ( ) ,
818+ policyRequest : null ,
819+ policyDatabase : null ,
820+ cacheEnabled : null ,
821+ cacheTtl : null ,
822+ config : TEST_RUNTIME_CONFIG_FILE ,
823+ restMethodsForStoredProcedure : null ,
824+ graphQLOperationForStoredProcedure : null ,
825+ parametersNameCollection : null ,
826+ parametersDescriptionCollection : null ,
827+ parametersRequiredCollection : null ,
828+ parametersDefaultCollection : null ,
829+ fieldsNameCollection : [ ] ,
830+ fieldsAliasCollection : [ ] ,
831+ fieldsDescriptionCollection : [ ] ,
832+ fieldsPrimaryKeyCollection : [ ] ,
833+ mcpDmlTools : null ,
834+ mcpCustomTool : "true"
835+ ) ;
836+
837+ RuntimeConfigLoader . TryParseConfig ( INITIAL_CONFIG , out RuntimeConfig ? runtimeConfig ) ;
838+
839+ Assert . IsFalse ( TryAddNewEntity ( options , runtimeConfig ! , out RuntimeConfig _ ) ,
840+ "Should fail to add table entity with custom-tool enabled" ) ;
841+ }
842+
843+ /// <summary>
844+ /// Test that invalid MCP option value fails
845+ /// </summary>
846+ [ DataTestMethod ]
847+ [ DataRow ( "invalid" , null , DisplayName = "Invalid dml-tools value" ) ]
848+ [ DataRow ( null , "invalid" , DisplayName = "Invalid custom-tool value" ) ]
849+ [ DataRow ( "yes" , "no" , DisplayName = "Invalid boolean-like values" ) ]
850+ public void AddEntityWithInvalidMcpOptions ( string ? mcpDmlTools , string ? mcpCustomTool )
851+ {
852+ AddOptions options = new (
853+ source : "MyTable" ,
854+ permissions : new string [ ] { "anonymous" , "*" } ,
855+ entity : "MyEntity" ,
856+ description : null ,
857+ sourceType : "table" ,
858+ sourceParameters : null ,
859+ sourceKeyFields : null ,
860+ restRoute : null ,
861+ graphQLType : null ,
862+ fieldsToInclude : Array . Empty < string > ( ) ,
863+ fieldsToExclude : Array . Empty < string > ( ) ,
864+ policyRequest : null ,
865+ policyDatabase : null ,
866+ cacheEnabled : null ,
867+ cacheTtl : null ,
868+ config : TEST_RUNTIME_CONFIG_FILE ,
869+ restMethodsForStoredProcedure : null ,
870+ graphQLOperationForStoredProcedure : null ,
871+ parametersNameCollection : null ,
872+ parametersDescriptionCollection : null ,
873+ parametersRequiredCollection : null ,
874+ parametersDefaultCollection : null ,
875+ fieldsNameCollection : [ ] ,
876+ fieldsAliasCollection : [ ] ,
877+ fieldsDescriptionCollection : [ ] ,
878+ fieldsPrimaryKeyCollection : [ ] ,
879+ mcpDmlTools : mcpDmlTools ,
880+ mcpCustomTool : mcpCustomTool
881+ ) ;
882+
883+ RuntimeConfigLoader . TryParseConfig ( INITIAL_CONFIG , out RuntimeConfig ? runtimeConfig ) ;
884+
885+ Assert . IsFalse ( TryAddNewEntity ( options , runtimeConfig ! , out RuntimeConfig _ ) ,
886+ "Should fail with invalid MCP option values" ) ;
887+ }
888+
889+ #endregion MCP Entity Configuration Tests
636890 }
637891}
0 commit comments