@@ -441,6 +441,223 @@ def test_validate_import_data_not_list(self):
441441 self .assertIn ("must be a list" , errors [0 ])
442442
443443
444+ class TestActiveFieldCheckboxParsing (unittest .TestCase ):
445+ """Test the checkbox parsing logic for the active field."""
446+
447+ def test_checkbox_checked_returns_true (self ):
448+ """Test that checked checkbox results in active_value='true'."""
449+ # Simulate form data when checkbox is checked
450+ from unittest .mock import Mock
451+ form_data = Mock ()
452+ form_data .getlist .return_value = ["true" ]
453+
454+ # Apply the parsing logic from admin_supported_products.py
455+ active_value = "true" if "true" in form_data .getlist ("active" ) else "false"
456+
457+ self .assertEqual (active_value , "true" )
458+
459+ def test_checkbox_unchecked_returns_false (self ):
460+ """Test that unchecked checkbox results in active_value='false'."""
461+ # Simulate form data when checkbox is unchecked (empty list)
462+ from unittest .mock import Mock
463+ form_data = Mock ()
464+ form_data .getlist .return_value = []
465+
466+ # Apply the parsing logic from admin_supported_products.py
467+ active_value = "true" if "true" in form_data .getlist ("active" ) else "false"
468+
469+ self .assertEqual (active_value , "false" )
470+
471+ def test_checkbox_missing_field_defaults_to_false (self ):
472+ """Test that missing active field defaults to false."""
473+ # Simulate form data without active field at all
474+ from unittest .mock import Mock
475+ form_data = Mock ()
476+ form_data .getlist .return_value = []
477+
478+ active_value = "true" if "true" in form_data .getlist ("active" ) else "false"
479+
480+ self .assertEqual (active_value , "false" )
481+
482+ def test_checkbox_boolean_conversion (self ):
483+ """Test that string active_value converts correctly to boolean."""
484+ # Test conversion to boolean for database storage
485+ active_value_true = "true"
486+ active_value_false = "false"
487+
488+ self .assertTrue (active_value_true == "true" )
489+ self .assertFalse (active_value_false == "true" )
490+
491+ def test_checkbox_with_unexpected_value (self ):
492+ """Test that unexpected values default to false."""
493+ # Edge case: unexpected value
494+ from unittest .mock import Mock
495+ form_data = Mock ()
496+ form_data .getlist .return_value = ["yes" , "1" , "on" ]
497+
498+ active_value = "true" if "true" in form_data .getlist ("active" ) else "false"
499+
500+ # Should default to false since "true" is not in the list
501+ self .assertEqual (active_value , "false" )
502+
503+
504+ class TestMirrorConfigDataWithActiveField (unittest .TestCase ):
505+ """Test mirror configuration export includes active field."""
506+
507+ def test_exported_config_includes_active_true (self ):
508+ """Test that exported mirror config includes active=true."""
509+ mirror = Mock ()
510+ mirror .id = 1
511+ mirror .name = "Active Mirror"
512+ mirror .match_variant = "Red Hat Enterprise Linux"
513+ mirror .match_major_version = 9
514+ mirror .match_minor_version = None
515+ mirror .match_arch = "x86_64"
516+ mirror .active = True
517+ mirror .created_at = datetime (2024 , 1 , 1 , 10 , 0 , 0 )
518+ mirror .updated_at = None
519+
520+ # Mock supported product
521+ mirror .supported_product = Mock ()
522+ mirror .supported_product .id = 1
523+ mirror .supported_product .name = "Rocky Linux"
524+ mirror .supported_product .variant = "Rocky Linux"
525+ mirror .supported_product .vendor = "RESF"
526+
527+ # Mock repositories
528+ mirror .rpm_repomds = []
529+
530+ result = asyncio .run (_get_mirror_config_data (mirror ))
531+
532+ # Verify active field is included and true
533+ self .assertIn ("active" , result ["mirror" ])
534+ self .assertTrue (result ["mirror" ]["active" ])
535+
536+ def test_exported_config_includes_active_false (self ):
537+ """Test that exported mirror config includes active=false."""
538+ mirror = Mock ()
539+ mirror .id = 2
540+ mirror .name = "Inactive Mirror"
541+ mirror .match_variant = "Red Hat Enterprise Linux"
542+ mirror .match_major_version = 8
543+ mirror .match_minor_version = None
544+ mirror .match_arch = "x86_64"
545+ mirror .active = False
546+ mirror .created_at = datetime (2024 , 1 , 1 , 10 , 0 , 0 )
547+ mirror .updated_at = None
548+
549+ # Mock supported product
550+ mirror .supported_product = Mock ()
551+ mirror .supported_product .id = 1
552+ mirror .supported_product .name = "Rocky Linux"
553+ mirror .supported_product .variant = "Rocky Linux"
554+ mirror .supported_product .vendor = "RESF"
555+
556+ # Mock repositories
557+ mirror .rpm_repomds = []
558+
559+ result = asyncio .run (_get_mirror_config_data (mirror ))
560+
561+ # Verify active field is included and false
562+ self .assertIn ("active" , result ["mirror" ])
563+ self .assertFalse (result ["mirror" ]["active" ])
564+
565+
566+ class TestImportWithActiveField (unittest .TestCase ):
567+ """Test import validation with active field."""
568+
569+ def test_import_data_with_active_true_is_valid (self ):
570+ """Test that import data with active=true is valid."""
571+ valid_data = [
572+ {
573+ "product" : {
574+ "name" : "Rocky Linux" ,
575+ "variant" : "Rocky Linux" ,
576+ "vendor" : "RESF" ,
577+ },
578+ "mirror" : {
579+ "name" : "Rocky Linux 9 x86_64" ,
580+ "match_variant" : "Red Hat Enterprise Linux" ,
581+ "match_major_version" : 9 ,
582+ "match_arch" : "x86_64" ,
583+ "active" : True ,
584+ },
585+ "repositories" : [
586+ {
587+ "repo_name" : "BaseOS" ,
588+ "arch" : "x86_64" ,
589+ "production" : True ,
590+ "url" : "https://example.com/repo" ,
591+ }
592+ ],
593+ }
594+ ]
595+
596+ errors = asyncio .run (_validate_import_data (valid_data ))
597+ self .assertEqual (errors , [])
598+
599+ def test_import_data_with_active_false_is_valid (self ):
600+ """Test that import data with active=false is valid."""
601+ valid_data = [
602+ {
603+ "product" : {
604+ "name" : "Rocky Linux" ,
605+ "variant" : "Rocky Linux" ,
606+ "vendor" : "RESF" ,
607+ },
608+ "mirror" : {
609+ "name" : "Rocky Linux 8 x86_64" ,
610+ "match_variant" : "Red Hat Enterprise Linux" ,
611+ "match_major_version" : 8 ,
612+ "match_arch" : "x86_64" ,
613+ "active" : False ,
614+ },
615+ "repositories" : [
616+ {
617+ "repo_name" : "BaseOS" ,
618+ "arch" : "x86_64" ,
619+ "production" : True ,
620+ "url" : "https://example.com/repo" ,
621+ }
622+ ],
623+ }
624+ ]
625+
626+ errors = asyncio .run (_validate_import_data (valid_data ))
627+ self .assertEqual (errors , [])
628+
629+ def test_import_data_without_active_field_is_valid (self ):
630+ """Test that import data without active field is valid (backwards compatibility)."""
631+ valid_data = [
632+ {
633+ "product" : {
634+ "name" : "Rocky Linux" ,
635+ "variant" : "Rocky Linux" ,
636+ "vendor" : "RESF" ,
637+ },
638+ "mirror" : {
639+ "name" : "Rocky Linux 9 x86_64" ,
640+ "match_variant" : "Red Hat Enterprise Linux" ,
641+ "match_major_version" : 9 ,
642+ "match_arch" : "x86_64" ,
643+ # No active field - should default to true
644+ },
645+ "repositories" : [
646+ {
647+ "repo_name" : "BaseOS" ,
648+ "arch" : "x86_64" ,
649+ "production" : True ,
650+ "url" : "https://example.com/repo" ,
651+ }
652+ ],
653+ }
654+ ]
655+
656+ # Should still be valid - active field is optional for backwards compatibility
657+ errors = asyncio .run (_validate_import_data (valid_data ))
658+ self .assertEqual (errors , [])
659+
660+
444661if __name__ == "__main__" :
445662 # Run with verbose output
446663 unittest .main (verbosity = 2 )
0 commit comments