Hive Box not updating after clearing in other dart file/class

Viewed 393

i am clearing a hive box and updating it in the very next line. The update can be seen in the same file code (through debugging). But somehow for the other stateless widget/class/file box is empty.

boxT.clear() ;
setState(() { 
boxT.addAll({
[count2, totalEntries]
});});

Reason for clearing the box on everytime a specific button is pressed: I am adding a map. addAll() simply creates another entry. i dont want it. i have also tried put and putall but they are only showing the value and not the key.

1 Answers

That's because Hive is NOT a state management tool, if you add/remove something to/from your box, you need to let your state know. You should have a global state that listens to changes from that Box.

Example with a ValueNotifier.


class ItemsNotifier extends ValueNotifier<List<Item>> {
  ItemsNotifier() : super(getItemsFromBox());

  List<Item> _items = getItemsFromBox();

  @override
  List<Item> get value => _items;

  void addItem(Item item) {
    addItemToBox(item);
    _items = getItemsFromBox();
    notifyListeners();
  }

  Future<void> deleteAll() async {
    await clearBox();
    _items = getItemsFromBox();
    notifyListeners();
  }
}

List<Item> getItemsFromBox() {
  return Hive.box<Item>('items').values.toList();
}

Future<void> addItemToBox(Item item) async {
  await Hive.box<Item>('items').add(item);
}

Future<void> clearBox() async {
  await Hive.box<Item>('items').clear();
}

class MainPage extends StatefulWidget {
  const MainPage({Key? key}) : super(key: key);

  @override
  State<MainPage> createState() => _MainPageState();
}

class _MainPageState extends State<MainPage> {
  late final ItemsNotifier _notifier;

  @override
  void initState() {
    _notifier = ItemsNotifier();
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: ExampleWidget(notifier: _notifier),
      floatingActionButton: FloatingActionButton(
        onPressed: _notifier.deleteAll,
        child: const Icon(Icons.delete),
      ),
    );
  }

  @override
  void dispose() {
    _notifier.dispose();
    super.dispose();
  }
}

class ExampleWidget extends StatelessWidget {
  const ExampleWidget({required this.notifier, Key? key}) : super(key: key);

  final ItemsNotifier notifier;

  @override
  Widget build(BuildContext context) {
    return ValueListenableBuilder<List<Item>>(
      valueListenable: notifier,
      builder: (context, items, _) {
        return ListView.builder(
          itemBuilder: (context, index) => ListTile(
            title: Text(items[index].title),
          ),
          itemCount: items.length,
        );
      },
    );
  }
}

Note that if you have multiple pages using the data from this box, I would recommend using something like Provider and having a ChangeNotifier instead of the ValueNotifier or using flutter_bloc and having a Repository that handles communication with Hive.

Related