Ответ
Да, Provider был моим основным инструментом для state management в первых Flutter-проектах. Это обёртка над InheritedWidget, которая реализует паттерн поставщика зависимостей (dependency injection) для эффективного распространения и обновления состояния.
Как я его использовал:
Чаще всего с ChangeNotifier для реактивности. Создаётся класс модели, который расширяет ChangeNotifier и уведомляет слушателей при изменении состояния.
Пример модели и провайдера:
// Модель состояния
class CartModel with ChangeNotifier {
final List<Item> _items = [];
List<Item> get items => List.unmodifiable(_items);
void addItem(Item item) {
_items.add(item);
notifyListeners(); // Критически важный вызов
}
}
// Инициализация в main.dart
void main() {
runApp(
MultiProvider(
providers: [
ChangeNotifierProvider(create: (_) => CartModel()),
Provider(create: (_) => SomeOtherService()), // Простой провайдер
],
child: MyApp(),
),
);
}
Потребление состояния в виджете:
// Способ 1: Provider.of с listen: true (по умолчанию)
class CartBadge extends StatelessWidget {
@override
Widget build(BuildContext context) {
final cart = Provider.of<CartModel>(context); // Виджет перестроится при notifyListeners
return Text('Items in cart: ${cart.items.length}');
}
}
// Способ 2: Consumer для оптимизации перестроек
class ProductList extends StatelessWidget {
@override
Widget build(BuildContext context) {
return Consumer<CartModel>(
builder: (context, cart, child) {
// Перестраивается только этот блок
return ListView.builder(
itemCount: cart.items.length,
itemBuilder: (context, index) => ProductItem(cart.items[index]),
);
},
);
}
}
Мои выводы по Provider:
- Сильные стороны: Официальная рекомендация от команды Flutter на момент его активного использования, отличная документация, простота для понимания основных концепций DI и реактивности.
- Идеален для: Небольших и средних приложений, а также для обучения основам управления состоянием.
MultiProviderотлично организует глобальные зависимости приложения. - Эволюция: Со временем для более сложных сценариев я перешёл на Riverpod, который решает некоторые ограничения Provider (например, работу вне контекста BuildContext).