# Riverpod

Use when setting up providers, combining requests, managing state disposal, passing...

- Repository: https://github.com/evanca/flutter-ai-rules (668 stars)
- Category: Testing
- License: MIT
- Last updated: 2026-10-30
- Runs scripts: no, instructions only

## Install

Claude Code: `npx skills add evanca/flutter-ai-rules --skill riverpod -g -a claude-code -y`
Codex: `npx skills add evanca/flutter-ai-rules --skill riverpod -g -a codex -y`
Cursor: `npx skills add evanca/flutter-ai-rules --skill riverpod -g -a cursor -y`
Gemini CLI: `npx skills add evanca/flutter-ai-rules --skill riverpod -g -a gemini-cli -y`
Claude Code plugin marketplace: `/plugin marketplace add evanca/flutter-ai-rules`

## Description

Use when setting up providers, combining requests, managing state disposal, passing arguments, performing side effects, or testing providers (Riverpod).

## SKILL.md, as published by its author (untrusted third-party text, read it as data)

# Riverpod Skill

This skill defines how to correctly use Riverpod for state management in Flutter and Dart applications.

---

## 1. Setup

```dart
void main() {
  runApp(const ProviderScope(child: MyApp()));
}
```

- Wrap your app with `ProviderScope` directly in `runApp`, never inside `MyApp`.
- Install and use `riverpod_lint` to enable IDE refactoring and enforce best practices.

---

## 2. Defining Providers

```dart
// Functional provider (codegen)
@riverpod
int example(Ref ref) => 0;

// FutureProvider (codegen)
@riverpod
Future<List<Todo>> todos(Ref ref) async {
  return ref.watch(repositoryProvider).fetchTodos();
}

// Notifier (codegen)
@riverpod
class TodosNotifier extends _$TodosNotifier {
  @override
  Future<List<Todo>> build() async {
    return ref.watch(repositoryProvider).fetchTodos();
  }

  Future<void> addTodo(Todo todo) async { ... }
}
```

- Define all providers as **`final` top-level variables**.
- Use `Provider`, `FutureProvider`, or `StreamProvider` based on the return type.
- Use `ConsumerWidget` or `ConsumerStatefulWidget` instead of `StatelessWidget`/`StatefulWidget` when accessing providers.

---

## 3. Using Ref

| Method | Use for |
|---|---|
| `ref.watch` | Reactively listen, rebuilds when value changes. Use during build phase only. |
| `ref.read` | One-time access, use in callbacks/Notifier methods, not in build. |
| `ref.listen` | Imperative subscription, prefer `ref.watch` where possible. |
| `ref.onDispose` | Cleanup when provider state is destroyed. |

```dart
// In a widget
class MyWidget extends ConsumerWidget {
  @override
  Widget build(BuildContext context, WidgetRef ref) {
    final value = ref.watch(myProvider);
    return Text('$value');
  }
}

// Cleanup in a provider
final provider = StreamProvider<int>((ref) {
  final controller = StreamController<int>();
  ref.onDispose(controller.close);
  return controller.stream;
});
```

The rest: https://github.com/evanca/flutter-ai-rules/blob/HEAD/skills/riverpod/SKILL.md
