@@ -24,17 +24,26 @@ final class TestPlugin extends PluginBase<dynamic> {
2424 final List <Hook > _hooks;
2525 final bool shouldThrowOnGetHooks;
2626 final bool shouldThrowOnRegister;
27+ final bool shouldThrowOnGetMetadata;
2728 final PluginMetadata _metadata;
2829 int registerCallCount = 0 ;
2930 dynamic lastClientReceived;
3031 PluginEnvironmentMetadata ? lastEnvironmentMetadataReceived;
3132
3233 TestPlugin (this .pluginName, this ._hooks,
33- {this .shouldThrowOnGetHooks = false , this .shouldThrowOnRegister = false })
34+ {this .shouldThrowOnGetHooks = false ,
35+ this .shouldThrowOnRegister = false ,
36+ this .shouldThrowOnGetMetadata = false })
3437 : _metadata = PluginMetadata (name: pluginName);
3538
3639 @override
37- PluginMetadata get metadata => _metadata;
40+ PluginMetadata get metadata {
41+ if (shouldThrowOnGetMetadata) {
42+ throw Exception (
43+ 'Test exception accessing metadata for plugin $pluginName ' );
44+ }
45+ return _metadata;
46+ }
3847
3948 @override
4049 List <Hook > get hooks {
@@ -248,6 +257,36 @@ void main() {
248257 record.level == LDLogLevel .warn &&
249258 record.message.contains ('plugin-3' ))))).called (1 );
250259 });
260+
261+ test ('handles plugin that throws when accessing metadata' , () {
262+ final hook1 = TestHook ('hook-1' );
263+ final plugin1 = TestPlugin ('plugin-1' , [hook1]);
264+ final plugin2 = TestPlugin ('plugin-2' , [],
265+ shouldThrowOnGetHooks: true , shouldThrowOnGetMetadata: true );
266+ final hook3 = TestHook ('hook-3' );
267+ final plugin3 = TestPlugin ('plugin-3' , [hook3]);
268+
269+ final result = safeGetHooks ([plugin1, plugin2, plugin3], logger);
270+
271+ expect (result, isNotNull);
272+ expect (result! .length, equals (2 ));
273+ expect (result, containsAll ([hook1, hook3]));
274+
275+ // Verify warning was logged mentioning unknown plugin since metadata failed
276+ // This happens when safeGetHooks tries to get the plugin name for logging after hooks fails
277+ verify (() => mockLogAdapter.log (any (
278+ that: predicate <LDLogRecord >((record) =>
279+ record.level == LDLogLevel .warn &&
280+ record.message.contains ('unknown' ))))).called (1 );
281+
282+ // Also verify that the metadata access failure was logged
283+ verify (() => mockLogAdapter.log (any (
284+ that: predicate <LDLogRecord >((record) =>
285+ record.level == LDLogLevel .warn &&
286+ record.message.contains (
287+ 'Exception thrown access the name of a registered plugin' )))))
288+ .called (1 );
289+ });
251290 });
252291
253292 group ('safeRegisterPlugins' , () {
@@ -452,5 +491,37 @@ void main() {
452491 expect (plugin2.lastEnvironmentMetadataReceived,
453492 same (customEnvironmentMetadata));
454493 });
494+
495+ test (
496+ 'handles plugin that throws when accessing metadata during registration' ,
497+ () {
498+ final plugin1 = TestPlugin ('plugin-1' , []);
499+ final plugin2 = TestPlugin ('plugin-2' , [],
500+ shouldThrowOnRegister: true , shouldThrowOnGetMetadata: true );
501+ final plugin3 = TestPlugin ('plugin-3' , []);
502+
503+ safeRegisterPlugins (testClient, testEnvironmentMetadata,
504+ [plugin1, plugin2, plugin3], logger);
505+
506+ // All plugins should have attempted registration
507+ expect (plugin1.registerCallCount, equals (1 ));
508+ expect (plugin2.registerCallCount, equals (1 ));
509+ expect (plugin3.registerCallCount, equals (1 ));
510+
511+ // Verify warning was logged mentioning unknown plugin since metadata failed
512+ // This happens when safeRegisterPlugins tries to log the plugin name after registration fails
513+ verify (() => mockLogAdapter.log (any (
514+ that: predicate <LDLogRecord >((record) =>
515+ record.level == LDLogLevel .warn &&
516+ record.message.contains ('unknown' ))))).called (1 );
517+
518+ // Also verify that the metadata access failure was logged
519+ verify (() => mockLogAdapter.log (any (
520+ that: predicate <LDLogRecord >((record) =>
521+ record.level == LDLogLevel .warn &&
522+ record.message.contains (
523+ 'Exception thrown access the name of a registered plugin' )))))
524+ .called (1 );
525+ });
455526 });
456527}
0 commit comments