Flutter Web and Hive
Tags: flutter, dart, webdev, productivity
Published: 2020-10-10 01:54:34

*In case it helped :)*
<a href="https://www.buymeacoffee.com/aseemwangoo" target="_blank"><img src="https://www.buymeacoffee.com/assets/img/custom_images/orange_img.png" alt="Pass Me A Coffee!!" style="height: 41px !important;width: 174px !important;box-shadow: 0px 3px 2px 0px rgba(190, 190, 190, 0.5) !important;-webkit-box-shadow: 0px 3px 2px 0px rgba(190, 190, 190, 0.5) !important;" ></a>

<!-- wp:paragraph -->
<p><strong><em>Website: </em></strong><a href="https://web.flatteredwithflutter.com/#/" rel="noreferrer noopener" target="_blank"><strong><em>https://web.flatteredwithflutter.com/#/</em></strong></a></p>
<!-- /wp:paragraph -->

<!-- wp:paragraph -->
<p>We will cover briefly about</p>
<!-- /wp:paragraph -->

<!-- wp:list {"ordered":true} -->
<ol><li>Storing data using Hive</li><li>Data operations</li><li>Real-time UI updates</li></ol>
<!-- /wp:list -->

{% youtube 4u6TXhqUbHw %}

####Article here: https://flatteredwithflutter.com/using-hive-in-flutter-web/

<!-- wp:heading {"level":4} -->
<h4>Storing data using&nbsp;Hive</h4>
<!-- /wp:heading -->

<!-- wp:paragraph -->
<p>Hive is a lightweight and key-value database. It supports mobile, desktop, and browser.</p>
<!-- /wp:paragraph -->

<!-- wp:paragraph -->
<p>Basically, we can save data from primitives like strings to complex custom objects.</p>
<!-- /wp:paragraph -->

<!-- wp:paragraph -->
<p><em>Note: Install both </em><strong><em>hive</em></strong><em> and </em><strong><em>hive_flutter</em></strong></p>
<!-- /wp:paragraph -->

<!-- wp:separator -->
<hr class="wp-block-separator"/>
<!-- /wp:separator -->

<!-- wp:heading {"level":4} -->
<h4><strong>Data to&nbsp;save:</strong></h4>
<!-- /wp:heading -->

<!-- wp:paragraph -->
<p>We have generated a custom model (<strong>ArticlesModel</strong>) using <a href="https://flutter.dev/docs/development/data-and-backend/json" rel="noreferrer noopener" target="_blank">code generation.</a></p>
<!-- /wp:paragraph -->

<!-- wp:image -->
<figure class="wp-block-image"><img src="https://cdn-images-1.medium.com/max/1600/1*I5cIRjs8sAG5Wy4FOGfQaQ.png" alt="Flutter Web and Hive"/><figcaption>Flutter Web and&nbsp;Hive</figcaption></figure>
<!-- /wp:image -->

<!-- wp:paragraph -->
<p>Now we want to extend this model and make it Hive customizable.</p>
<!-- /wp:paragraph -->

<!-- wp:list -->
<ul><li>Include the following dev dependency</li></ul>
<!-- /wp:list -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">dev_dependencies:
  hive_generator: ^0.7.1</pre>
<!-- /wp:preformatted -->

<!-- wp:heading {"level":3} -->
<h3>Next Step</h3>
<!-- /wp:heading -->

<!-- wp:list -->
<ul><li>Add the following annotation on top of the model’s JSON annotation</li></ul>
<!-- /wp:list -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">@HiveType(typeId: 1) ------&gt; ADD THIS PART<br>@JsonSerializable(nullable: false)</pre>
<!-- /wp:preformatted -->

<!-- wp:paragraph -->
<p>typeId is an <strong>annotated id (integer)</strong>for a class.</p>
<!-- /wp:paragraph -->

<!-- wp:quote -->
<blockquote class="wp-block-quote"><p>Note: This annotation <strong>creates a default Adapter class</strong> with&nbsp;</p></blockquote>
<!-- /wp:quote -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">“YourClass” + “Adapter”<br>// FOR OUR CASE, ArticlesModelAdapter</pre>
<!-- /wp:preformatted -->

<!-- wp:list -->
<ul><li>Next, annotate each field with&nbsp;</li></ul>
<!-- /wp:list -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">@HiveField(0) ------&gt; ADD THIS PART<br>@JsonKey(name: 'article_id')<br>String articleID;</pre>
<!-- /wp:preformatted -->

<!-- wp:image -->
<figure class="wp-block-image"><img src="https://cdn-images-1.medium.com/max/1600/1*KHuEKSvlN2PWZ_TKKoRs1g.png" alt="Flutter Web and Hive"/><figcaption>Final Model — Hive&nbsp;Ready</figcaption></figure>
<!-- /wp:image -->

<!-- wp:list -->
<ul><li>Finally, run the code generation command.</li></ul>
<!-- /wp:list -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">flutter pub run build_runner build --delete-conflicting-outputs</pre>
<!-- /wp:preformatted -->

<!-- wp:separator -->
<hr class="wp-block-separator"/>
<!-- /wp:separator -->

<!-- wp:heading {"level":4} -->
<h4>Configure Hive</h4>
<!-- /wp:heading -->

<!-- wp:paragraph -->
<p>Inside your main.dart, initialize Hive using</p>
<!-- /wp:paragraph -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">await Hive.initFlutter();</pre>
<!-- /wp:preformatted -->

<!-- wp:paragraph -->
<p>and register the adapter which was generated using code generation above. We specify the type of model (in our case <strong>ArticlesModel</strong>).</p>
<!-- /wp:paragraph -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">Hive.registerAdapter&lt;ArticlesModel&gt;(ArticlesModelAdapter());</pre>
<!-- /wp:preformatted -->

<!-- wp:paragraph -->
<p>Note: <em>For web-browsers, the data is saved inside </em><strong><em>IndexedDB</em></strong><em>, which is done by Hive, we don’t write extra code for that.</em></p>
<!-- /wp:paragraph -->

<!-- wp:paragraph -->
<p>See how it looks inside the browser,</p>
<!-- /wp:paragraph -->

<!-- wp:image -->
<figure class="wp-block-image"><img src="https://cdn-images-1.medium.com/max/1600/1*qnplYxY6FQam0TLrYEMg4Q.png" alt="IndexedDB — Browser"/><figcaption>IndexedDB — Browser</figcaption></figure>
<!-- /wp:image -->

<!-- wp:paragraph -->
<p>We open a box (<strong>everything inside the Hive is a box</strong>)</p>
<!-- /wp:paragraph -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">await Hive.openBox&lt;ArticlesModel&gt;('favorites')</pre>
<!-- /wp:preformatted -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">//String field here is required and uniquely identifies a box</pre>
<!-- /wp:preformatted -->

<!-- wp:quote -->
<blockquote class="wp-block-quote"><p>In case the box is already open, we get the instance. No extra code for checking if the box is opened.</p></blockquote>
<!-- /wp:quote -->

<!-- wp:separator -->
<hr class="wp-block-separator"/>
<!-- /wp:separator -->

<!-- wp:image -->
<figure class="wp-block-image"><img src="https://cdn-images-1.medium.com/max/1600/1*oM37apQ_1yf0aheRqi0U1w.png" alt="Flutter Web and Hive"/><figcaption>Flutter Web and Hive — Add to fav on the heart&nbsp;press</figcaption></figure>
<!-- /wp:image -->

<!-- wp:heading {"level":4} -->
<h4>Data Operations</h4>
<!-- /wp:heading -->

<!-- wp:paragraph -->
<p>With Hive configured along with the data model in the previous step, hence we can now proceed with the implementation of operations:</p>
<!-- /wp:paragraph -->

<!-- wp:list {"ordered":true} -->
<ol><li>Insert data</li><li>Read data</li><li>Delete data</li></ol>
<!-- /wp:list -->

<!-- wp:list -->
<ul><li>Let’s <strong>get the opened box </strong>using</li></ul>
<!-- /wp:list -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">final _favBox = Hive.box&lt;ArticlesModel&gt;('favorites')</pre>
<!-- /wp:preformatted -->

<!-- wp:list -->
<ul><li>For data <strong>insertion</strong>,&nbsp;</li></ul>
<!-- /wp:list -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">_favBox.put('key', 'value') ---&gt; GENERIC</pre>
<!-- /wp:preformatted -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">_favBox.put(data.articleID, data) ---&gt; OUR CASE SPECIFIC</pre>
<!-- /wp:preformatted -->

<!-- wp:paragraph -->
<p>As the box is of type ArticlesModel, hence the <strong>data </strong>(‘<strong>value</strong>’) is of type ArticlesModel. We assign <strong>article id</strong> as the <strong>key</strong>.</p>
<!-- /wp:paragraph -->

<!-- wp:list -->
<ul><li>For <strong>reading</strong> data,</li></ul>
<!-- /wp:list -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">List&lt;ArticlesModel&gt; get fetchFromFavBox =&gt; _favBox.values.toList();</pre>
<!-- /wp:preformatted -->

<!-- wp:paragraph -->
<p>values: returns all the items inside the box</p>
<!-- /wp:paragraph -->

<!-- wp:list -->
<ul><li>For <strong>deleting</strong> data,</li></ul>
<!-- /wp:list -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">_favBox.delete('key') ---&gt; GENERIC
_favBox.delete(data.articleID); ---&gt; OUR CASE SPECIFIC</pre>
<!-- /wp:preformatted -->

<!-- wp:paragraph -->
<p>While inserting we assigned <strong>articleID</strong> as key, hence we delete using the same key.&nbsp;</p>
<!-- /wp:paragraph -->

<!-- wp:quote -->
<blockquote class="wp-block-quote"><p>Note: In case the key doesn’t exist, nothing happens!</p></blockquote>
<!-- /wp:quote -->

<!-- wp:heading {"level":4} -->
<h4>Real-time UI&nbsp;updates</h4>
<!-- /wp:heading -->

<!-- wp:paragraph -->
<p>In today’s world, we need everything instantly, the same goes for our insertion, deletion operations inside the Hive.</p>
<!-- /wp:paragraph -->

<!-- wp:paragraph -->
<p>What we want to achieve</p>
<!-- /wp:paragraph -->

<!-- wp:list -->
<ul><li>Show the insertion, deletion instantly</li><li>No, reload, please!</li></ul>
<!-- /wp:list -->

<!-- wp:paragraph -->
<p>Hive exposes <strong>listeners</strong> for the Hive Boxes. We utilize this listener on the box to show updates instantly.</p>
<!-- /wp:paragraph -->

<!-- wp:preformatted -->
<pre class="wp-block-preformatted">final _favBox = Hive.box&lt;ArticlesModel&gt;(HiveBoxes.favBox);
// FROM ABOVE

Box&lt;ArticlesModel&gt; get favBox =&gt; _favBox;
favBox.listenable() ----&gt; LISTENABLE exposed BY HIVE</pre>
<!-- /wp:preformatted -->

<!-- wp:quote -->
<blockquote class="wp-block-quote"><p>Note: listenable is present inside <strong>hive_flutter</strong></p></blockquote>
<!-- /wp:quote -->

<!-- wp:paragraph -->
<p>We can wrap this listenable inside <a href="https://api.flutter.dev/flutter/widgets/ValueListenableBuilder-class.html" rel="noreferrer noopener" target="_blank"><strong>ValueListenableBuilder</strong></a></p>
<!-- /wp:paragraph -->

<!-- wp:image -->
<figure class="wp-block-image"><img src="https://cdn-images-1.medium.com/max/1600/1*UwovrbdG3twQJUoR5cekRA.png" alt=""/><figcaption>Flutter Web and&nbsp;Hive</figcaption></figure>
<!-- /wp:image -->

<!-- wp:paragraph -->
<p>Each time any changes are made to the box’s entries, it gets notified to us.</p>
<!-- /wp:paragraph -->

<!-- wp:quote -->
<blockquote class="wp-block-quote"><p>Note: You can provide [keys] filter inside listenable for listening to specific keys.</p></blockquote>
<!-- /wp:quote -->

*In case it helped :)*
<a href="https://www.buymeacoffee.com/aseemwangoo" target="_blank"><img src="https://www.buymeacoffee.com/assets/img/custom_images/orange_img.png" alt="Pass Me A Coffee!!" style="height: 41px !important;width: 174px !important;box-shadow: 0px 3px 2px 0px rgba(190, 190, 190, 0.5) !important;-webkit-box-shadow: 0px 3px 2px 0px rgba(190, 190, 190, 0.5) !important;" ></a>

{% youtube 4u6TXhqUbHw %}

<!-- wp:quote -->
<blockquote class="wp-block-quote"><p>Hosted URL&nbsp;: <a href="https://web.flatteredwithflutter.com/#/" rel="noreferrer noopener" target="_blank">https://web.flatteredwithflutter.com/#/</a></p></blockquote>
<!-- /wp:quote -->

<!-- wp:quote -->
<blockquote class="wp-block-quote"><p><a href="https://github.com/AseemWangoo/experiments_with_web" rel="noreferrer noopener" target="_blank">Source code for Flutter Web App..</a></p></blockquote>
<!-- /wp:quote -->