@@ -235,6 +235,57 @@ const mockParameterWithIcon = createMockParameter({
235
235
icon : "/test-icon.png" ,
236
236
} ) ;
237
237
238
+ // ADDITIONAL_MOCKS_START
239
+ // Mock for a numeric input parameter that enforces min/max constraints
240
+ const mockNumberInputParameter = createMockParameter ( {
241
+ name : "number_input_param" ,
242
+ display_name : "Number Input Parameter" ,
243
+ description : "A numeric input parameter with min/max validations" ,
244
+ type : "number" ,
245
+ form_type : "input" ,
246
+ default_value : { value : "5" , valid : true } ,
247
+ validations : [
248
+ {
249
+ validation_min : 1 ,
250
+ validation_max : 10 ,
251
+ validation_error : "Value must be between 1 and 10" ,
252
+ validation_regex : null ,
253
+ validation_monotonic : null ,
254
+ } ,
255
+ ] ,
256
+ } ) ;
257
+
258
+ // Mock for a masked input parameter (e.g. secrets)
259
+ const mockMaskedInputParameter = createMockParameter ( {
260
+ name : "masked_input_param" ,
261
+ display_name : "Masked Input Parameter" ,
262
+ type : "string" ,
263
+ form_type : "input" ,
264
+ styling : {
265
+ placeholder : "********" ,
266
+ disabled : false ,
267
+ label : "" ,
268
+ mask_input : true ,
269
+ } ,
270
+ } ) ;
271
+
272
+ // Mock parameter that contains a warning diagnostic
273
+ const mockWarningParameter = createMockParameter ( {
274
+ name : "warning_param" ,
275
+ display_name : "Warning Parameter" ,
276
+ description : "Parameter with a warning diagnostic" ,
277
+ form_type : "input" ,
278
+ diagnostics : [
279
+ {
280
+ severity : "warning" ,
281
+ summary : "This is a warning" ,
282
+ detail : "Something might be wrong" ,
283
+ extra : { code : "warning" } ,
284
+ } ,
285
+ ] ,
286
+ } ) ;
287
+ // ADDITIONAL_MOCKS_END
288
+
238
289
describe ( "DynamicParameter" , ( ) => {
239
290
const mockOnChange = jest . fn ( ) ;
240
291
@@ -532,23 +583,6 @@ describe("DynamicParameter", () => {
532
583
expect ( slider ) . toHaveAttribute ( "aria-valuenow" , "50" ) ;
533
584
} ) ;
534
585
535
- it ( "handles slider value changes" , async ( ) => {
536
- render (
537
- < DynamicParameter
538
- parameter = { mockSliderParameter }
539
- value = "50"
540
- onChange = { mockOnChange }
541
- /> ,
542
- ) ;
543
-
544
- const slider = screen . getByRole ( "slider" ) ;
545
-
546
- fireEvent . keyDown ( slider , { key : "ArrowRight" } ) ;
547
-
548
- expect ( slider ) . toHaveAttribute ( "tabindex" , "0" ) ;
549
- expect ( slider ) . not . toHaveAttribute ( "aria-disabled" ) ;
550
- } ) ;
551
-
552
586
it ( "respects min/max constraints from validation_condition" , ( ) => {
553
587
render (
554
588
< DynamicParameter
@@ -911,4 +945,80 @@ describe("DynamicParameter", () => {
911
945
) . toBeInTheDocument ( ) ;
912
946
} ) ;
913
947
} ) ;
948
+
949
+ describe ( "Number Input Parameter" , ( ) => {
950
+ it ( "renders number input with correct min/max attributes" , ( ) => {
951
+ render (
952
+ < DynamicParameter
953
+ parameter = { mockNumberInputParameter }
954
+ value = "5"
955
+ onChange = { mockOnChange }
956
+ /> ,
957
+ ) ;
958
+
959
+ const input = screen . getByRole ( "spinbutton" ) ;
960
+ expect ( input ) . toHaveAttribute ( "min" , "1" ) ;
961
+ expect ( input ) . toHaveAttribute ( "max" , "10" ) ;
962
+ } ) ;
963
+
964
+ it ( "calls onChange when numeric value changes (debounced)" , ( ) => {
965
+ jest . useFakeTimers ( ) ;
966
+ render (
967
+ < DynamicParameter
968
+ parameter = { mockNumberInputParameter }
969
+ value = "5"
970
+ onChange = { mockOnChange }
971
+ /> ,
972
+ ) ;
973
+
974
+ const input = screen . getByRole ( "spinbutton" ) ;
975
+ fireEvent . change ( input , { target : { value : "7" } } ) ;
976
+
977
+ // onChange is debounced, so advance timers
978
+ act ( ( ) => {
979
+ jest . runAllTimers ( ) ;
980
+ } ) ;
981
+
982
+ expect ( mockOnChange ) . toHaveBeenCalledWith ( "7" ) ;
983
+ jest . useRealTimers ( ) ;
984
+ } ) ;
985
+ } ) ;
986
+
987
+ describe ( "Masked Input Parameter" , ( ) => {
988
+ it ( "renders a password field by default and toggles visibility on mouse events" , async ( ) => {
989
+ render (
990
+ < DynamicParameter
991
+ parameter = { mockMaskedInputParameter }
992
+ value = "secret123"
993
+ onChange = { mockOnChange }
994
+ /> ,
995
+ ) ;
996
+
997
+ const input = screen . getByLabelText ( "Masked Input Parameter" ) ;
998
+ expect ( input ) . toHaveAttribute ( "type" , "password" ) ;
999
+
1000
+ const toggleButton = screen . getByRole ( "button" ) ;
1001
+ // Reveal the input
1002
+ fireEvent . mouseDown ( toggleButton ) ;
1003
+ expect ( input ) . toHaveAttribute ( "type" , "text" ) ;
1004
+ // Hide again
1005
+ fireEvent . mouseUp ( toggleButton ) ;
1006
+ expect ( input ) . toHaveAttribute ( "type" , "password" ) ;
1007
+ } ) ;
1008
+ } ) ;
1009
+
1010
+ describe ( "Parameter Diagnostics" , ( ) => {
1011
+ it ( "renders warning diagnostics for non-error parameters" , ( ) => {
1012
+ render (
1013
+ < DynamicParameter
1014
+ parameter = { mockWarningParameter }
1015
+ value = ""
1016
+ onChange = { mockOnChange }
1017
+ /> ,
1018
+ ) ;
1019
+
1020
+ expect ( screen . getByText ( "This is a warning" ) ) . toBeInTheDocument ( ) ;
1021
+ expect ( screen . getByText ( "Something might be wrong" ) ) . toBeInTheDocument ( ) ;
1022
+ } ) ;
1023
+ } ) ;
914
1024
} ) ;
0 commit comments