@@ -427,8 +427,8 @@ describe('Theme', () => {
427
427
} ) ;
428
428
} ) ;
429
429
430
- describe ( 'BASE_THEME integration tests' , ( ) => {
431
- it ( 'merges BASE_THEME tokens with empty user theme' , ( ) => {
430
+ describe ( 'base theme integration tests' , ( ) => {
431
+ it ( 'merges base theme tokens with empty user theme' , ( ) => {
432
432
const baseTheme : AnyThemeConfig = {
433
433
token : {
434
434
colorPrimary : '#2893B3' ,
@@ -452,7 +452,7 @@ describe('Theme', () => {
452
452
expect ( serialized . algorithm ) . toBe ( ThemeAlgorithm . DEFAULT ) ;
453
453
} ) ;
454
454
455
- it ( 'allows user theme to override specific BASE_THEME tokens' , ( ) => {
455
+ it ( 'allows user theme to override specific base theme tokens' , ( ) => {
456
456
const baseTheme : AnyThemeConfig = {
457
457
token : {
458
458
colorPrimary : '#2893B3' ,
@@ -481,7 +481,7 @@ describe('Theme', () => {
481
481
expect ( theme . theme . borderRadius ) . toBe ( 4 ) ;
482
482
} ) ;
483
483
484
- it ( 'handles BASE_THEME_DARK with dark algorithm correctly' , ( ) => {
484
+ it ( 'handles base theme with dark algorithm correctly' , ( ) => {
485
485
const baseTheme : AnyThemeConfig = {
486
486
token : {
487
487
colorPrimary : '#2893B3' ,
@@ -508,8 +508,8 @@ describe('Theme', () => {
508
508
expect ( serialized . algorithm ) . toBe ( ThemeAlgorithm . DARK ) ;
509
509
} ) ;
510
510
511
- it ( 'works with real-world Superset BASE_THEME configuration' , ( ) => {
512
- // Simulate actual Superset BASE_THEME
511
+ it ( 'works with real-world Superset base theme configuration' , ( ) => {
512
+ // Simulate actual Superset base theme (THEME_DEFAULT/THEME_DARK from config)
513
513
const supersetBaseTheme : AnyThemeConfig = {
514
514
token : {
515
515
colorPrimary : '#2893B3' ,
@@ -548,7 +548,7 @@ describe('Theme', () => {
548
548
expect ( darkSerialized . algorithm ) . toBe ( ThemeAlgorithm . DARK ) ;
549
549
} ) ;
550
550
551
- it ( 'handles component overrides in BASE_THEME ' , ( ) => {
551
+ it ( 'handles component overrides in base theme ' , ( ) => {
552
552
const baseTheme : AnyThemeConfig = {
553
553
token : {
554
554
colorPrimary : '#2893B3' ,
@@ -704,5 +704,85 @@ describe('Theme', () => {
704
704
// fontFamily reverts to Ant Design default since base theme is not reapplied
705
705
expect ( theme . theme . fontFamily ) . not . toBe ( 'Inter' ) ;
706
706
} ) ;
707
+
708
+ it ( 'minimal theme preserves ALL base theme tokens except overridden ones' , ( ) => {
709
+ // Simulate a comprehensive base theme with many tokens
710
+ const baseTheme : AnyThemeConfig = {
711
+ token : {
712
+ colorPrimary : '#2893B3' ,
713
+ colorError : '#e04355' ,
714
+ colorWarning : '#fcc700' ,
715
+ colorSuccess : '#5ac189' ,
716
+ colorInfo : '#66bcfe' ,
717
+ fontFamily : 'Inter, Helvetica' ,
718
+ fontSize : 14 ,
719
+ borderRadius : 4 ,
720
+ lineWidth : 1 ,
721
+ controlHeight : 32 ,
722
+ // Custom Superset tokens
723
+ brandLogoAlt : 'CustomLogo' ,
724
+ menuHoverBackgroundColor : '#eeeeee' ,
725
+ } as Record < string , any > ,
726
+ algorithm : antdThemeImport . defaultAlgorithm ,
727
+ } ;
728
+
729
+ // Minimal theme that only overrides primary color and algorithm
730
+ const minimalTheme : AnyThemeConfig = {
731
+ token : {
732
+ colorPrimary : '#ff05dd' , // Only override this
733
+ } ,
734
+ algorithm : antdThemeImport . darkAlgorithm , // Change to dark
735
+ } ;
736
+
737
+ const theme = Theme . fromConfig ( minimalTheme , baseTheme ) ;
738
+
739
+ // User's override should apply
740
+ expect ( theme . theme . colorPrimary ) . toBe ( '#ff05dd' ) ;
741
+
742
+ // ALL base theme tokens should be preserved
743
+ expect ( theme . theme . colorError ) . toBe ( '#e04355' ) ;
744
+ expect ( theme . theme . colorWarning ) . toBe ( '#fcc700' ) ;
745
+ expect ( theme . theme . colorSuccess ) . toBe ( '#5ac189' ) ;
746
+ expect ( theme . theme . colorInfo ) . toBe ( '#66bcfe' ) ;
747
+ expect ( theme . theme . fontFamily ) . toBe ( 'Inter, Helvetica' ) ;
748
+ expect ( theme . theme . fontSize ) . toBe ( 14 ) ;
749
+ expect ( theme . theme . borderRadius ) . toBe ( 4 ) ;
750
+ expect ( theme . theme . lineWidth ) . toBe ( 1 ) ;
751
+ expect ( theme . theme . controlHeight ) . toBe ( 32 ) ;
752
+
753
+ // Custom tokens should also be preserved
754
+ expect ( ( theme . theme as any ) . brandLogoAlt ) . toBe ( 'CustomLogo' ) ;
755
+ expect ( ( theme . theme as any ) . menuHoverBackgroundColor ) . toBe ( '#eeeeee' ) ;
756
+
757
+ // Algorithm should be updated
758
+ const serialized = theme . toSerializedConfig ( ) ;
759
+ expect ( serialized . algorithm ) . toBe ( ThemeAlgorithm . DARK ) ;
760
+ } ) ;
761
+
762
+ it ( 'arrays in themes are replaced entirely, not merged by index' , ( ) => {
763
+ const baseTheme : AnyThemeConfig = {
764
+ token : {
765
+ colorPrimary : '#2893B3' ,
766
+ } ,
767
+ algorithm : [
768
+ antdThemeImport . compactAlgorithm ,
769
+ antdThemeImport . defaultAlgorithm ,
770
+ ] ,
771
+ } ;
772
+
773
+ const userTheme : AnyThemeConfig = {
774
+ algorithm : [ antdThemeImport . darkAlgorithm ] , // Replace with single item array
775
+ } ;
776
+
777
+ const theme = Theme . fromConfig ( userTheme , baseTheme ) ;
778
+ const serialized = theme . toSerializedConfig ( ) ;
779
+
780
+ // User's array should completely replace base array
781
+ expect ( Array . isArray ( serialized . algorithm ) ) . toBe ( true ) ;
782
+ expect ( serialized . algorithm ) . toHaveLength ( 1 ) ;
783
+ expect ( serialized . algorithm ) . toContain ( ThemeAlgorithm . DARK ) ;
784
+ expect ( serialized . algorithm ) . not . toContain ( ThemeAlgorithm . COMPACT ) ;
785
+ expect ( serialized . algorithm ) . not . toContain ( ThemeAlgorithm . DEFAULT ) ;
786
+ } ) ;
707
787
} ) ;
708
788
} ) ;
0 commit comments