Priority 1 (COMPLETE): - Add riverpod_lint and custom_lint packages - Update analysis_options.yaml with custom_lint plugin - Update AGENTS.md with Riverpod 3.0 best practices - Fix unsafe ref usage in modern_chat_input.dart - All tests passing, zero breaking changes Priority 2 (PLANNED): - Complete migration plan for 39 providers (RIVERPOD_PRIORITY2_PLAN.md) - Quick reference guide (RIVERPOD_PRIORITY2_QUICKREF.md) - Progress tracker (RIVERPOD_PRIORITY2_TRACKER.md) - Master documentation index (RIVERPOD_MIGRATION_INDEX.md) - Analysis and summary documents Documentation includes: - Step-by-step migration examples - 6-phase implementation plan (23-33 hours) - Testing strategies and rollback procedures - Risk assessment and mitigation - Timeline and resource estimates
5.5 KiB
Riverpod 3.0 Quick Start Guide
Immediate Actions (30 minutes)
Step 1: Add riverpod_lint (5 minutes)
- Update
pubspec.yaml:
cd /Users/cogwheel/Documents/conduit
Add to dev_dependencies section:
dev_dependencies:
# ... existing dependencies ...
riverpod_lint: ^3.0.0
custom_lint: ^0.8.0
- Install packages:
flutter pub get
- Update
analysis_options.yaml:
Add this at the top level (same level as linter:):
analyzer:
plugins:
- custom_lint
Full file should look like:
include: package:flutter_lints/flutter.yaml
analyzer:
plugins:
- custom_lint
linter:
rules:
avoid_print: true
- Run the linter:
dart run custom_lint
This will show Riverpod-specific issues if any exist.
Step 2: Fix Any Linter Issues (10 minutes)
The linter will identify issues like:
- ❌ Using
refoutside of widgets/providers - ❌ Missing
ref.mountedchecks - ❌ Incorrect provider usage patterns
Example Fix:
If you see: "ref should not be used outside of a widget/provider"
// ❌ Bad
class MyService {
void doSomething(WidgetRef ref) { // ref as parameter
ref.read(someProvider);
}
}
// ✅ Good
@riverpod
class MyService extends _$MyService {
@override
void build() {}
void doSomething() {
ref.read(someProvider); // ref is available in Notifier
}
}
Step 3: Update AGENTS.md (5 minutes)
Replace the state management section in AGENTS.md:
Find (around line 166):
### State Management
* **Built-in Solutions:** Prefer Flutter's built-in state management solutions.
Do not use a third-party package unless explicitly requested.
Replace with:
### State Management
* **Riverpod 3.0:** This project uses Riverpod 3.0 for state management.
* **Code Generation:** Always use `@riverpod` annotation with code generation
for new providers. See existing examples in `lib/core/providers/`.
* **Notifier Classes:** Use `Notifier` and `AsyncNotifier` for mutable state:
```dart
@riverpod
class Counter extends _$Counter {
@override
int build() => 0;
void increment() => state++;
}
- Provider Functions: Use
@riverpodfunctions for computed/derived state:@riverpod int doubled(DoubledRef ref) { final count = ref.watch(counterProvider); return count * 2; } - Keep Alive: Use
@Riverpod(keepAlive: true)for singletons:@Riverpod(keepAlive: true) class AuthManager extends _$AuthManager { ... } - Async Safety: Always check
ref.mountedbefore state updates in async ops:Future<void> loadData() async { final data = await fetchData(); if (!ref.mounted) return; // ✅ Prevent updates after disposal state = data; } - Automatic Retry: Providers automatically retry on failure with exponential
backoff. Customize if needed:
@riverpod Future<Data> myData(MyDataRef ref) async { ref.onDispose(() { // Cleanup }); return await fetchData(); } - Lint Rules: Use
custom_lintwithriverpod_lintto catch common mistakes. Rundart run custom_lintbefore committing.
---
## Validation (10 minutes)
### 1. Run All Checks
```bash
# Code generation (if needed)
dart run build_runner build --delete-conflicting-outputs
# Custom lint
dart run custom_lint
# Standard analysis
flutter analyze
# Tests
flutter test
2. Expected Results
All should pass ✅ without new errors. You may see some warnings from riverpod_lint which are informational.
3. Common Warnings and Fixes
Warning: "Provider could use autoDispose"
// Current
@riverpod
Future<Data> myData(MyDataRef ref) async {
return await fetch();
}
// Suggested (if data is short-lived)
@riverpod
Future<Data> myData(MyDataRef ref) async {
ref.cacheFor(const Duration(minutes: 5)); // Auto-dispose after 5 min
return await fetch();
}
Warning: "Missing ref.mounted check"
// Current
Future<void> save() async {
await someAsyncOp();
state = newValue; // ⚠️ Might be disposed
}
// Fixed
Future<void> save() async {
await someAsyncOp();
if (!ref.mounted) return; // ✅
state = newValue;
}
Next Steps (Optional)
After completing the quick start, you can:
- Read the full analysis: See
RIVERPOD_3_ANALYSIS.md - Start migration: Follow Phase 2 in the analysis document
- Add provider docs: Document provider purposes with dartdoc
Troubleshooting
Issue: custom_lint not found
# Reinstall
flutter pub get
flutter pub global activate custom_lint
Issue: Analysis takes too long
# Restart Dart analysis server
# In VS Code: Cmd+Shift+P -> "Dart: Restart Analysis Server"
# In Android Studio: File -> Invalidate Caches / Restart
Issue: Generated files out of sync
# Clean and rebuild
flutter clean
flutter pub get
dart run build_runner build --delete-conflicting-outputs
Benefits You'll See Immediately
After adding riverpod_lint:
✅ Compile-time safety - Catch errors before runtime
✅ Better autocomplete - IDE knows provider types
✅ Quick fixes - Automatic solutions for common issues
✅ Consistency checks - Enforced best practices
✅ Refactoring confidence - Compiler catches all usages
Questions?
Refer to:
- Full analysis:
RIVERPOD_3_ANALYSIS.md - Official docs: https://riverpod.dev
- Linter docs: https://riverpod.dev/docs/concepts/about_riverpod_lint