4

Here is a very curious case with Riverpod which is probably a bug.

The existence of a simple watch line prevents a listen from executing. When watching a base provider and listening to a provider that depends on it, listen only executes if you do not watch the base.

Here are the providers:

final baseProvider = Provider<int>(
  (ref) => 0,
);

final dependentProvider = Provider<String>(
  (ref) {
    final q = ref.watch(baseProvider);
    return '$q';
  },
  dependencies: [baseProvider],
);

Here is the code that overrides it:

class _MainPageState extends State<MainPage> {
  var overridingValue = 1;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: Column(
          mainAxisSize: MainAxisSize.min,
          children: [
            ProviderScope(
              overrides: [
                baseProvider.overrideWithValue(overridingValue),
              ],
              child: const MyConsumer(),
            ),
            ElevatedButton(
              onPressed: () {
                setState(() {++overridingValue;});
              },
              child: const Text('increment'),
            ),
          ],
        ),
      ),
    );
  }
}

And here's the code under that override that exhibits the curious behavior. Simply uncommenting the ref.watch line prevents the ref.listen from firing.

class MyConsumer extends ConsumerWidget {
  const MyConsumer({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context, WidgetRef ref) {
    // the print line in listen below is executed only when this line is commented out
    // If you uncomment this line, the print line is not executed anymore.
    //
    // final q = ref.watch(baseProvider);

    ref.listen(
      dependentProvider,
      (previous, next) {
        print('Listened to $previous -> $next');
      },
    );

    return const SizedBox.shrink();
  }
}

This difference in behavior resulting from a harmless .watch() is really curious. Is there an explanation on why this may be happening? Is this a bug?

Please find a repo here that demonstrates this behavior: https://github.com/gazialankus/riverpod_query_play The stateprovider_instead_of_scope branch there shows that this only happens with a ProviderScope override.

And here is a DartPad for an easy experience: https://dartpad.dev/?id=3aefed6429499de5a939a6c50d158534

Gazihan Alankus
  • 11,256
  • 7
  • 46
  • 57

0 Answers0