If I run DefaultPreferencesFactoryTest in my local, without special config (I think), various methods fail:
1) DefaultPreferencesFactoryTest::testShowRollbackConfIsHiddenForUsersWithoutRollbackRights
MWException: Default 'null' is invalid for preference echo-email-format of user
/var/www/html/w/includes/preferences/DefaultPreferencesFactory.php:354
/var/www/html/w/includes/preferences/DefaultPreferencesFactory.php:263
/var/www/html/w/tests/phpunit/includes/preferences/DefaultPreferencesFactoryTest.php:256
/var/www/html/w/tests/phpunit/MediaWikiIntegrationTestCase.php:527
=== Logs generated by test case
[objectcache] [debug] MainWANObjectCache using store {class} {"class":"HashBagOStuff"}
[localisation] [debug] LocalisationCache using store LCStoreNull []
[objectcache] [debug] MainWANObjectCache using store {class} {"class":"HashBagOStuff"}
[objectcache] [debug] MainObjectStash using store {class} {"class":"HashBagOStuff"}
[wfDebug] [debug] ParserFactory: using default preprocessor {"private":false}
[localisation] [debug] LocalisationCache::isExpired(en): cache missing, need to make one []
[MessageCache] [debug] MessageCache using store {class} {"class":"HashBagOStuff"}
[Parser] [debug] Parser::setOutputFlag: set user-signature flag on 'DefaultPreferencesFactoryTest'; User signature detected []
===
2) DefaultPreferencesFactoryTest::testShowRollbackConfIsShownForUsersWithRollbackRights
MWException: Default 'null' is invalid for preference echo-email-format of user
/var/www/html/w/includes/preferences/DefaultPreferencesFactory.php:354
/var/www/html/w/includes/preferences/DefaultPreferencesFactory.php:263
/var/www/html/w/tests/phpunit/includes/preferences/DefaultPreferencesFactoryTest.php:275
/var/www/html/w/tests/phpunit/MediaWikiIntegrationTestCase.php:527
=== Logs generated by test case
[objectcache] [debug] MainWANObjectCache using store {class} {"class":"HashBagOStuff"}
[localisation] [debug] LocalisationCache using store LCStoreNull []
[objectcache] [debug] MainWANObjectCache using store {class} {"class":"HashBagOStuff"}
[objectcache] [debug] MainObjectStash using store {class} {"class":"HashBagOStuff"}
[wfDebug] [debug] ParserFactory: using default preprocessor {"private":false}
[localisation] [debug] LocalisationCache::isExpired(en): cache missing, need to make one []
[MessageCache] [debug] MessageCache using store {class} {"class":"HashBagOStuff"}
[Parser] [debug] Parser::setOutputFlag: set user-signature flag on 'DefaultPreferencesFactoryTest'; User signature detected []
===
3) DefaultPreferencesFactoryTest::testVariantsSupport
MWException: Default 'null' is invalid for preference echo-email-format of user
/var/www/html/w/includes/preferences/DefaultPreferencesFactory.php:354
/var/www/html/w/includes/preferences/DefaultPreferencesFactory.php:263
/var/www/html/w/tests/phpunit/includes/preferences/DefaultPreferencesFactoryTest.php:411
/var/www/html/w/tests/phpunit/MediaWikiIntegrationTestCase.php:527
=== Logs generated by test case
[objectcache] [debug] MainWANObjectCache using store {class} {"class":"HashBagOStuff"}
[localisation] [debug] LocalisationCache using store LCStoreNull []
[objectcache] [debug] MainWANObjectCache using store {class} {"class":"HashBagOStuff"}
[objectcache] [debug] MainObjectStash using store {class} {"class":"HashBagOStuff"}
[wfDebug] [debug] ParserFactory: using default preprocessor {"private":false}
[localisation] [debug] LocalisationCache::isExpired(en): cache missing, need to make one []
[MessageCache] [debug] MessageCache using store {class} {"class":"HashBagOStuff"}
[Parser] [debug] Parser::setOutputFlag: set user-signature flag on 'DefaultPreferencesFactoryTest'; User signature detected []
===
4) DefaultPreferencesFactoryTest::testUserGroupMemberships
MWException: Default 'null' is invalid for preference echo-email-format of user
/var/www/html/w/includes/preferences/DefaultPreferencesFactory.php:354
/var/www/html/w/includes/preferences/DefaultPreferencesFactory.php:263
/var/www/html/w/tests/phpunit/includes/preferences/DefaultPreferencesFactoryTest.php:435
/var/www/html/w/tests/phpunit/MediaWikiIntegrationTestCase.php:527
=== Logs generated by test case
[objectcache] [debug] MainWANObjectCache using store {class} {"class":"HashBagOStuff"}
[localisation] [debug] LocalisationCache using store LCStoreNull []
[objectcache] [debug] MainWANObjectCache using store {class} {"class":"HashBagOStuff"}
[objectcache] [debug] MainObjectStash using store {class} {"class":"HashBagOStuff"}
[wfDebug] [debug] ParserFactory: using default preprocessor {"private":false}
[localisation] [debug] LocalisationCache::isExpired(en): cache missing, need to make one []
[MessageCache] [debug] MessageCache using store {class} {"class":"HashBagOStuff"}
[UserOptionsManager] [debug] Loading options from database {"user_id":0}
[Parser] [debug] Parser::setOutputFlag: set user-signature flag on 'DefaultPreferencesFactoryTest'; User signature detected []
===I haven't investigated this in depth, but it looks like the mocked UserOptionsManager doesn't run hooks, and Echo adds a default for echo-email-format in onUserGetDefaultOptions. There has to be something specific to my local that makes this test fail, because it passes in CI, but I haven't looked into what this might be. At any rate, the simple fix is to just provide a default value, and then potentially change it in the hook handler.