<?xml version="1.0" encoding="UTF-8"?>
<rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/"
    xmlns:atom="http://www.w3.org/2005/Atom" xmlns:media="http://search.yahoo.com/mrss/" version="2.0">
    <channel>
        
        <title>
            <![CDATA[ protocol-buffers - freeCodeCamp.org ]]>
        </title>
        <description>
            <![CDATA[ Browse thousands of programming tutorials written by experts. Learn Web Development, Data Science, DevOps, Security, and get developer career advice. ]]>
        </description>
        <link>https://www.freecodecamp.org/news/</link>
        <image>
            <url>https://cdn.freecodecamp.org/universal/favicons/favicon.png</url>
            <title>
                <![CDATA[ protocol-buffers - freeCodeCamp.org ]]>
            </title>
            <link>https://www.freecodecamp.org/news/</link>
        </image>
        <generator>Eleventy</generator>
        <lastBuildDate>Thu, 14 May 2026 09:14:31 +0000</lastBuildDate>
        <atom:link href="https://www.freecodecamp.org/news/tag/protocol-buffers/rss.xml" rel="self" type="application/rss+xml" />
        <ttl>60</ttl>
        
            <item>
                <title>
                    <![CDATA[ Android Proto DataStore – Should You Use It? ]]>
                </title>
                <description>
                    <![CDATA[ A few years back, Google announced the DataStore, which is a replacement for the tried and true SharedPreferences.  If you use or have used SharedPreferences in your applications, you might be thinking of making the switch. But as with everything, th... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/android-proto-datastore-should-you-use-it/</link>
                <guid isPermaLink="false">66ba4fdccabb4cb0aaa837f4</guid>
                
                    <category>
                        <![CDATA[ Android ]]>
                    </category>
                
                    <category>
                        <![CDATA[ protocol-buffers ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ Tomer ]]>
                </dc:creator>
                <pubDate>Tue, 02 Jan 2024 19:52:43 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2023/12/niklas-ohlrogge-j-0olYcaihg-unsplash.jpg" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>A few years back, Google announced the DataStore, which is a replacement for the tried and true SharedPreferences. </p>
<p>If you use or have used SharedPreferences in your applications, you might be thinking of making the switch. But as with everything, the main question here is: what is going to be the cost in development?</p>
<p><a target="_blank" href="https://developer.android.com/codelabs/android-proto-datastore#3">There are benefits</a> for using DataStore, but only the <strong>Proto DataStore</strong> allows you to save objects while providing type safety. </p>
<p>If you look at the <a target="_blank" href="https://developer.android.com/topic/libraries/architecture/datastore#proto-datastore">documentation</a> for Proto DataStore, you will find that it is a bit outdated and missing some crucial steps when working with it. So that is why, in this article, we are going to go over how to integrate Proto DataStore into your application and show that it’s not that big of a hassle to use it.</p>
<h2 id="heading-what-is-datastore">What is DataStore?</h2>
<p>Jetpack DataStore has two variants:</p>
<ul>
<li>Preferences DataStore</li>
<li>Proto DataStore</li>
</ul>
<p>We won’t be discussing the first, due to it’s similarity to SharedPreferences and also the fact that is has been covered widely. So now let’s understand what the Proto in Proto DataStore means.</p>
<p>Proto is the name Google chose to represent <a target="_blank" href="https://protobuf.dev/">Protocol Buffers</a>. These are (Google’s) mechanism that help you serialize structured data. They are not coding language-specific and in general, you define the type of data that you wish to work with and then code is generated that helps you read and write your data.</p>
<p>✋ We will be using the Proto 3 version in this article.</p>
<p>How does that definition look like?</p>
<pre><code class="lang-proto">message MyItem {
    string itemName = 1;
    int32 itemId = 2;
}
</code></pre>
<p>First, you define an object with the message keyword. Inside it, you list the fields associated with that object. The numbers at the end of each field are used to identify the field itself and <strong>cannot be changed once being set and the object is in use</strong>.</p>
<p>But what if we wanted to have multiple objects in our .proto file? Assuming the objects are related to one another, you can do this simply by adding more message objects:</p>
<pre><code class="lang-proto">message MyItem {
    string itemName = 1;
    int32 itemId = 2;
}

message MyListOfItems {
   repeated MyItem items = 1;
}
</code></pre>
<p>Notice that above we have added another message object that relies on the MyItem object defined above. If you want to define a list of objects, you need to use the <strong>repeated</strong> keyword.</p>
<h2 id="heading-how-to-set-up-proto-datastore">How to Set Up Proto DataStore</h2>
<p>To get started, you'll need to add the following dependencies to your application level build.gradle:</p>
<pre><code class="lang-groovy"> implementation "androidx.datastore:datastore-preferences:1.0.0"
 implementation  "com.google.protobuf:protobuf-javalite:3.18.0"
</code></pre>
<p>Then, you will need to create a proto directory inside your project. This directory needs to be a sibling of the Java folder in your project structure. </p>
<p>Inside of the proto directory, you will be creating a .proto file. This file is responsible for generating the data types you wish to store in Proto DataStore.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2023/12/1.jpg" alt="Image" width="600" height="400" loading="lazy"></p>
<p>Inside the proto directory, create a file with the .proto extension. Our .proto file will hold objects representing a Todo list (what else?). So we will call our file <strong>todo.proto</strong> and it will look like this:</p>
<pre><code class="lang-proto">syntax = "proto3";

option java_package = "com.yourPackageName.todo";
option java_multiple_files = true;

message TodoItem {
  string itemId = 1;
  string itemDescription = 2;
}

message TodoItems {
  repeated TodoItem items = 1;
}
</code></pre>
<p>Notice how we defined two message objects:</p>
<ol>
<li>TodoItem – that defines a todo item</li>
<li>TodoItems – that defines a list of TodoItem objects</li>
</ol>
<p>Next, build the project so that classes will be generated for TodoItem and TodoItems.</p>
<p>After our data objects have been defined, we need to create a class to serialize them. This class will tell the DataStore how to read/write our objects.</p>
<pre><code class="lang-kotlin"><span class="hljs-comment">// 1</span>
<span class="hljs-keyword">object</span> TodoItemSerializer: Serializer&lt;TodoItems&gt; {
   <span class="hljs-comment">// 2</span>
    <span class="hljs-keyword">override</span> <span class="hljs-keyword">val</span> defaultValue: TodoItems = TodoItems.getDefaultInstance()
    <span class="hljs-comment">// 3</span>
    <span class="hljs-keyword">override</span> <span class="hljs-keyword">suspend</span> <span class="hljs-function"><span class="hljs-keyword">fun</span> <span class="hljs-title">readFrom</span><span class="hljs-params">(input: <span class="hljs-type">InputStream</span>)</span></span>: TodoItems {
        <span class="hljs-keyword">try</span> {
            <span class="hljs-keyword">return</span> TodoItems.parseFrom(input)
        } <span class="hljs-keyword">catch</span> (exception: InvalidProtocolBufferException) {
            <span class="hljs-keyword">throw</span> CorruptionException(<span class="hljs-string">"Cannot read proto."</span>, exception)
        }
    }
    <span class="hljs-comment">// 3</span>
    <span class="hljs-keyword">override</span> <span class="hljs-keyword">suspend</span> <span class="hljs-function"><span class="hljs-keyword">fun</span> <span class="hljs-title">writeTo</span><span class="hljs-params">(
        t: <span class="hljs-type">TodoItems</span>,
        output: <span class="hljs-type">OutputStream</span>
    )</span></span> = t.writeTo(output)
}
</code></pre>
<p>Let’s review what we have in this class:</p>
<ol>
<li>When we declare the class, we need to implement the <strong>Serializer</strong> interface with our object as the type (T)</li>
<li>We define a default value for the serializer in case the file is not created</li>
<li>We override the readFrom/writeTo methods and we make sure to have our object as the data type there</li>
</ol>
<p>We have our .proto file with our data types and our serializer, so the next step is to instantiate the DataStore. We do this by using the property delegate created by dataStore, which requires giving a filename where our data will be saved and our serializer class (which we defined above).</p>
<pre><code class="lang-kotlin"><span class="hljs-keyword">private</span> <span class="hljs-keyword">const</span> <span class="hljs-keyword">val</span> DATA_STORE_FILE_NAME = <span class="hljs-string">"todo.pb"</span>

<span class="hljs-keyword">private</span> <span class="hljs-keyword">val</span> Context.todoItemDatastore: DataStore&lt;TodoItems&gt; <span class="hljs-keyword">by</span> dataStore(
    fileName = DATA_STORE_FILE_NAME,
    serializer = TodoItemSerializer,
)
</code></pre>
<p>This piece of code needs to reside at the top of a class of your choosing above the definition of the class itself. That is:</p>
<pre><code class="lang-kotlin"><span class="hljs-keyword">private</span> <span class="hljs-keyword">const</span> <span class="hljs-keyword">val</span> DATA_STORE_FILE_NAME = <span class="hljs-string">"todo.pb"</span>

<span class="hljs-keyword">private</span> <span class="hljs-keyword">val</span> Context.todoItemDatastore: DataStore&lt;TodoItems&gt; <span class="hljs-keyword">by</span> dataStore(
    fileName = DATA_STORE_FILE_NAME,
    serializer = TodoItemSerializer,
)

<span class="hljs-class"><span class="hljs-keyword">class</span> <span class="hljs-title">YourClassName</span> </span>{

}
</code></pre>
<p>To access this object in the rest of our application, we will need to use a context. An example is to use the application context in your viewmodel class:</p>
<pre><code class="lang-kotlin"><span class="hljs-class"><span class="hljs-keyword">class</span> <span class="hljs-title">MyViewModel</span></span>(application: Application): AndroidViewModel(application) {

   <span class="hljs-keyword">val</span> todoDataStore = application.todoItemDataStore
   <span class="hljs-comment">//...</span>
}
</code></pre>
<h2 id="heading-how-to-use-kotlin-flow">How to Use Kotlin Flow</h2>
<p>Now that we have gone through setting up everything we need for our DataStore, we'll discuss how we are actually going to interact with it. We'll want to read and write data to/from it. But the way we can do so is different from what you may be familiar with from SharedPreferences.</p>
<p>The DataStore we defined above has a data field that exposes a Flow for the properties we defined in our DataStore.</p>
<p>🚰 If you are not familiar with flows, <a target="_blank" href="https://developer.android.com/kotlin/flow">this</a> is a good place to start.</p>
<pre><code class="lang-kotlin"><span class="hljs-keyword">val</span> todoItemFlow: Flow&lt;TodoItems&gt; = todoItemDataStore.<span class="hljs-keyword">data</span>
        .<span class="hljs-keyword">catch</span> { exception -&gt;
            <span class="hljs-keyword">if</span> (exception <span class="hljs-keyword">is</span> IOException) {
                emit(TodoItems.getDefaultInstance())
            } <span class="hljs-keyword">else</span> {
                <span class="hljs-keyword">throw</span> exception
            }
        }
</code></pre>
<p>The code above shows how you can define a Flow that collects data from the Proto DataStore. A catch block was added in case an exception occurs. You can place this logic in the class where you defined your DataStore and use it like so in your viewmodel:</p>
<pre><code class="lang-kotlin"><span class="hljs-keyword">val</span> todoItemsFlow: LiveData&lt;TodoItems&gt; = todoItemsRepository.todoItemFlow.asLiveData()
</code></pre>
<p>Notice how we converted our Flow to LiveData. We did this for two reasons:</p>
<ol>
<li>Flows can stay active regardless of the activity/fragment that uses them</li>
<li>LiveData is something familiar to many developers, and I wanted to make this example as approachable as possible</li>
</ol>
<p>To be able to do this, you need to add the following dependency to your build.gradle file:</p>
<pre><code class="lang-groovy">implementation "androidx.lifecycle:lifecycle-livedata-ktx:2.6.2"
</code></pre>
<p>In your activity/fragment class, you can observe this live data like so:</p>
<pre><code class="lang-kotlin">myViewModel.todoItemFlow.observe(LocalLifecycleOwner.current) { todoItems -&gt;
                <span class="hljs-comment">// Logic to access data from DataStore</span>
            }
</code></pre>
<h2 id="heading-why-and-when-to-use-datastore">Why and When to Use DataStore</h2>
<p>After everything we reviewed, it’s time to talk about the elephant in the room. Should you go ahead and use DataStore (either Preferences or Proto) in your existing or next project?</p>
<p>In my opinion, the answer should be <strong>Yes</strong>. Besides the fact that Google is moving away from SharedPreferences, DataStore offers plenty of benefits to help you focus on your application and not the persistence of your data. </p>
<p>It’s safe to interact with the DataStore from the UI thread (as it moves work to I/O automatically), and it forces you to use Flow (if you haven’t still) and enjoy all the benefits within. There is also an option to migrate easily from SharedPreferences to Preferences DataStore.</p>
<p>If you are contemplating using Room instead of Proto DataStore, well that depends on your use case. If the amount of data you are going to save (or persist) is rather small and won’t require partial updating, the Proto DataStore is the way to go. If you have a larger data set or one that may be complex, you should opt for using Room instead.</p>
<p>If you want to see how all this code looks like in an application, you can see it here:</p>
<div class="embed-wrapper"><div class="embed-loading"><div class="loadingRow"></div><div class="loadingRow"></div></div><a class="embed-card" href="https://github.com/TomerPacific/Todo">https://github.com/TomerPacific/Todo</a></div>
<p>If you want to read other articles I have written, you can see them here:</p>
<div class="embed-wrapper"><div class="embed-loading"><div class="loadingRow"></div><div class="loadingRow"></div></div><a class="embed-card" href="https://github.com/TomerPacific/MediumArticles">https://github.com/TomerPacific/MediumArticles</a></div>
<p>Thanks for reading!</p>
<p>References:</p>
<ul>
<li><a target="_blank" href="https://protobuf.dev/programming-guides/proto3/">Protocol Buffers Documentation (proto 3)</a></li>
<li><a target="_blank" href="https://developer.android.com/codelabs/android-proto-datastore#0">Working With Proto DataStore Codelab</a></li>
<li><a target="_blank" href="https://developer.android.com/topic/libraries/architecture/datastore">DataStore Documentation</a></li>
</ul>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ What is gRPC? Protocol Buffers, Streaming, and Architecture Explained ]]>
                </title>
                <description>
                    <![CDATA[ By Pramono Winata gRPC is a powerful framework for working with Remote Procedure Calls. RPCs allow you to write code as though it will be run on a local computer, even though it may be executed on another computer. These past few days I have been div... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/what-is-grpc-protocol-buffers-stream-architecture/</link>
                <guid isPermaLink="false">66d460a2b6b7f664236cbe3f</guid>
                
                    <category>
                        <![CDATA[ communication ]]>
                    </category>
                
                    <category>
                        <![CDATA[ performance ]]>
                    </category>
                
                    <category>
                        <![CDATA[ protocol-buffers ]]>
                    </category>
                
                    <category>
                        <![CDATA[ software architecture ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ freeCodeCamp ]]>
                </dc:creator>
                <pubDate>Mon, 09 Nov 2020 21:33:37 +0000</pubDate>
                <media:content url="https://cdn-media-2.freecodecamp.org/w1280/5fa0296d49c47664ed8187bf.jpg" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>By Pramono Winata</p>
<p>gRPC is a powerful framework for working with Remote Procedure Calls. RPCs allow you to write code as though it will be run on a local computer, even though it may be executed on another computer.</p>
<p>These past few days I have been diving deep into gRPC. I'm going to share some of my big discoveries here in this article.</p>
<p>Note that I will focus more on concepts than implementation details. You will learn the core architecture of gRPC itself. You'll also learn:</p>
<ul>
<li>Why gRPC is so widely used by developers</li>
<li>How it performs so well</li>
<li>And how it all works under the hood.</li>
</ul>
<h2 id="heading-lets-go-back-a-bit">Let’s go back a bit</h2>
<p>Before we rush into gRPC, we should take a look at what <strong>Remote Procedure Calls</strong> are.</p>
<p>A RPC is a form of Client-Server Communication that uses a function call rather than a usual HTTP call.</p>
<p>It uses IDL (Interface Definition Language) as a form of contract on functions to be called and on the data type.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/11/operating-system-remote-call-procedure-working.png" alt="Image" width="600" height="400" loading="lazy">
<em>RPC Architecture</em></p>
<p>If you all haven’t realized it yet, the RPC in gRPC stands for Remote Procedure Call. And yes, gRPC does replicate this architectural style of client server communication, via function calls.</p>
<p>So gRPC is technically not a new concept. Rather it was adopted from this old technique and improved upon, making it very popular in just the span of 5 years.</p>
<h2 id="heading-overview-of-grpc">Overview of gRPC</h2>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/11/index.png" alt="Image" width="600" height="400" loading="lazy"></p>
<p>In 2015, Google open sourced their project which eventually would be the one called gRPC. But what does the "g" in gRPC actually stand for?</p>
<p>Lots of people might assume its for Google because Google made it, but it does not.</p>
<p>Google changes the meaning of the "g" for each version to the point where they even made a <a target="_blank" href="https://github.com/grpc/grpc/blob/master/doc/g_stands_for.md">README</a> to list all the meanings.</p>
<p>Since gRPC has been introduced it has gained quite a bit of popularity and many companies use it.</p>
<h3 id="heading-what-makes-grpc-so-popular">What makes gRPC so popular?</h3>
<p>There are plenty of reasons why gRPC is so popular:</p>
<ul>
<li>Abstraction is easy (it’s a function call)</li>
<li>It is supported in a lot of languages</li>
<li>It is very performant</li>
<li>HTTP calls are often confusing, so this makes it easier</li>
</ul>
<p>And aside from all of the reasons above, gRPC is popular because microservices are very popular.</p>
<p>Microservices will often be running several services in different programming languages. They'll also often have a lot of service to service interactions. </p>
<p>This is where gRPC helps out the most by providing the support and capability to solve the typical issues that arise from those situations.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/11/index.jpeg" alt="Image" width="600" height="400" loading="lazy">
<em>Microservices</em></p>
<p>gRPC is very popular in service to service calls, as often HTTP calls are harder to understand at first glance. </p>
<p>gRPC functions are much easier to reason about, so developers don't have to worry about writing a lot of documentation because the code itself should explain everything.</p>
<p>Some of the services might also be written in different languages and gRPC comes with multiple libraries to support that.</p>
<p>Performance is the cherry on top – and it’s a big cherry.</p>
<h2 id="heading-grpc-architecture">gRPC Architecture</h2>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/11/landing-2.png" alt="Image" width="600" height="400" loading="lazy">
<em>The rough architecture of gRPC. It's more or less the same as regular RPC.</em></p>
<p>I have mentioned several times that gRPC's performance is very good, but you might wonder what makes it so good? What makes gRPC so much better than RPC when their designs are pretty similar?</p>
<p>Here are a few key differences that make gRPC so performant.</p>
<h3 id="heading-http2">HTTP/2</h3>
<p>HTTP has been with us for a long time. Now, almost all backend services use this protocol.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/11/HTTP2-graphic.png" alt="Image" width="600" height="400" loading="lazy">
<em>History of HTTP</em></p>
<p>As the picture above shows, HTTP/1.1 stayed relevant for a long time.</p>
<p>Then in 2015, HTTP/2 came out and essentially replaced HTTP/1.1 as the most popular transport protocol on the internet.</p>
<p>If you remember that 2015 was also the year that gRPC came out, it was not a coincidence at all. HTTP/2 was also created by Google to be used by gRPC in its architecture.</p>
<p>HTTP/2 is one of the big reasons why gRPC can perform so well. And in this next section, you'll see why.</p>
<h3 id="heading-requestresponse-multiplexing">Request/Response Multiplexing</h3>
<p>In a traditional HTTP protocol, is not possible to send multiple requests or get multiple responses together in a single connection. A new connection will need to be created for each of them.</p>
<p>This kind of request/response multiplexing is made possible in HTTP/2 with the introduction of a new HTTP/2 layer called binary framing.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/11/Screenshot-from-2020-10-03-15-46-01.png" alt="Image" width="600" height="400" loading="lazy"></p>
<p>This binary layer encapsulates and encodes the data. In this layer, the HTTP request/response gets broken down into frames.</p>
<p>The headers frame contains typical HTTP headers information, and the data frame contains the payload. Using this mechanism, it's possible to have data from multiple requests in a single connection.</p>
<p>This allows payloads from multiple requests with the same header, thus identifying it as a single request.</p>
<h3 id="heading-header-compression">Header Compression</h3>
<p>You might have encountered many cases where HTTP headers are even bigger than the payload. And HTTP/2 has a very interesting strategy called HPack to handle that.</p>
<p>For one, everything in HTTP/2 is encoded before it's sent, including the headers. This does help with performance, but that’s not the most important thing about header compression.</p>
<p>HTTP/2 maps the header on both the client and the server side. From that, HTTP/2 is able to know if the header contains the same value and only sends the header value if it is different from the previous header.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/11/Screenshot-from-2020-11-04-22-32-12-1.png" alt="Image" width="600" height="400" loading="lazy"></p>
<p>As seen in the picture above, Request #2 will only send the path since the other values are exactly the same. And yes, this does cut down a lot on the payload size, and in turn, improves HTTP/2's performance even more.</p>
<h3 id="heading-protocol-buffer-aka-protobuf">Protocol Buffer, a.k.a. Protobuf</h3>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/11/protobuf.png" alt="Image" width="600" height="400" loading="lazy">
<em>Protocol Buffer</em></p>
<p>Protobuf is the most commonly used IDL (Interface Definition Language) for gRPC. It's where you basically store your data and function contracts in the form of a proto file.</p>
<pre><code class="lang-proto">message Person {
    required string name = 1;
    required int32 id = 2;
    optional string email = 3;
}
</code></pre>
<p>As this is in the form of a contract, both the client and server need to have the same proto file. The proto file acts as the intermediary contract for client to call any available functions from the server.</p>
<p>Protobuf also has it owns mechanisms, unlike a usual REST API that just sends over strings of JSON as bytes. These mechanisms allow the payload to be much smaller and enable faster performance. </p>
<p>The encoding method Protobuf uses is pretty complicated. If you want to take a deep dive into how it works, check out this <a target="_blank" href="https://developers.google.com/protocol-buffers/docs/encoding">comprehensive documentation</a>.</p>
<h2 id="heading-what-else-does-grpc-offer">What else does gRPC offer?</h2>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/04/image-257.png" alt="Image" width="600" height="400" loading="lazy">
_Photo by [Unsplash](https://unsplash.com/@kyledevaras?utm_source=ghost&amp;utm_medium=referral&amp;utm_campaign=api-credit"&gt;Kyle Gregory Devaras / &lt;a href="https://unsplash.com/?utm_source=ghost&amp;utm_medium=referral&amp;utm<em>campaign=api-credit)</em></p>
<p>Now you should have a basic understanding of the architecture of gRPC, how it works, and what it's capable of.</p>
<p>But here are a few other interesting things gRPC offers us.</p>
<h3 id="heading-metadata">Metadata</h3>
<p>Instead of using a usual HTTP request header, gRPC has something called metadata. Metadata is a type of key-value data that can be set from either the client or server side.</p>
<p><code>Header</code> can be assigned from the client side, while servers can assign <code>Header</code> and <code>Trailers</code> so long as they're both in the form of metadata.</p>
<h3 id="heading-streaming">Streaming</h3>
<p>Streaming is one of the core concepts of gRPC where several things can happen in a single request. This is made possible by the multiplexing capability of HTTP/2 mentioned earlier.</p>
<p>There are several types of streaming:</p>
<ul>
<li><strong>Server Streaming RPC:</strong> Where the client sends a single request and the server can send back multiple responses. For example, when a client sends a request for a homepage that has a list of multiple items, the server can send back responses separately, enabling the client to use lazy loading.</li>
<li><strong>Client Streaming RPC:</strong> Where the client sends multiple requests and the server only sends back a single response. For example, a zip/chunk uploaded by the client.</li>
<li><strong>Bidirectional Streaming RPC:</strong> Where both the client and server send messages to each other at the same time without waiting for a response.</li>
</ul>
<h3 id="heading-interceptors">Interceptors</h3>
<p>gRPC supports the usage of interceptors for its request/response. Interceptors, well, intercept messages and allow you to modify them.</p>
<p>Does this sound familiar? If you have played around with HTTP processes on a REST API, interceptors are very similar to middleware.</p>
<p>gRPC libraries usually support interceptors, and allow for easy implementation. Interceptors are usually used to:</p>
<ul>
<li>Modify the request/response before being passed on. It can be used to provide mandatory information before being sent to the client/server.</li>
<li>Allow you to manipulate each function call such as adding additional logging to track response time.</li>
</ul>
<h3 id="heading-load-balancing">Load Balancing</h3>
<p>If you aren't already familiar with load balancing, it's a mechanism that allows client requests to be spread out across multiple servers.</p>
<p>But load balancing is usually done at the proxy level (for example, NGINX). So why am I talking about it here?</p>
<p>Turns out that gRPC supports a method of load balancing by the client. It's already implemented in the Golang library, and can be used with ease.</p>
<p>While it might seem like some sort of crazy magic, it's not. There's some sort of DNS resolver to get an IP list, and a load balancing algorithm under the hood.</p>
<h3 id="heading-call-cancellation">Call Cancellation</h3>
<p>gRPC clients are able to cancel a gRPC call when it doesn't need a response anymore. Rollback on the server side is not possible, though.</p>
<p>This feature is especially useful for server side streaming where multiple server requests might be coming. The gRPC library comes equipped with an observer method pattern to know if a request is cancelled and allow it to cancel multiple corresponding requests at once.</p>
<h2 id="heading-wrapping-up">Wrapping Up</h2>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/04/image-258.png" alt="Image" width="600" height="400" loading="lazy">
_Photo by [Unsplash](https://unsplash.com/@rcrazy?utm_source=ghost&amp;utm_medium=referral&amp;utm_campaign=api-credit"&gt;Ricardo Rocha / &lt;a href="https://unsplash.com/?utm_source=ghost&amp;utm_medium=referral&amp;utm<em>campaign=api-credit)</em></p>
<p>Everything I shared today just scratches the surface of what gRPC is, what it's capable of, and roughly how it works.</p>
<p>I truly hope this article helped you understand more about gRPC. But there's still a lot more learn, so don't stop here! Keep digging.</p>
<p>Thanks for reading!</p>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ How to Use Google's Protocol Buffers in Python ]]>
                </title>
                <description>
                    <![CDATA[ By Tim Grossmann When people who speak different languages get together and talk, they try to use a language that everyone in the group understands.  To achieve this, everyone has to translate their thoughts, which are usually in their native languag... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/googles-protocol-buffers-in-python/</link>
                <guid isPermaLink="false">66d4614e73634435aafcefe4</guid>
                
                    <category>
                        <![CDATA[ protocol-buffers ]]>
                    </category>
                
                    <category>
                        <![CDATA[ Python ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ freeCodeCamp ]]>
                </dc:creator>
                <pubDate>Tue, 12 May 2020 11:52:44 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2020/05/unnamed-1.png" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>By Tim Grossmann</p>
<p>When people who speak different languages get together and talk, they try to use a language that everyone in the group understands. </p>
<p>To achieve this, everyone has to translate their thoughts, which are usually in their native language, into the language of the group. This “encoding and decoding” of language, however, leads to a loss of efficiency, speed, and precision.  </p>
<p>The same concept is present in computer systems and their components. Why should we send data in XML, JSON, or any other human-readable format if there is no need for us to understand what they are talking about directly? As long as we can still translate it into a human-readable format if explicitly needed.  </p>
<p>Protocol Buffers are a way to encode data before transportation, which efficiently shrinks data blocks and therefore increases speed when sending it. It abstracts data into a language- and platform-neutral format.</p>
<h3 id="heading-table-of-contents">Table of Contents</h3>
<ul>
<li><a class="post-section-overview" href="#heading-why-protocol-buffers">Why do we need Protocol Buffers?</a></li>
<li><a class="post-section-overview" href="#heading-what-are-protocol-buffers-and-how-do-they-work">What are Protocol Buffers and how do they work?</a></li>
<li><a class="post-section-overview" href="#heading-python-and-protocol-buffers">Protocol Buffers in Python</a></li>
<li><a class="post-section-overview" href="#heading-final-notes">Final notes</a></li>
</ul>
<h2 id="heading-why-protocol-buffers">Why Protocol Buffers?</h2>
<p>The initial purpose of Protocol Buffers was to simplify the work with request/response protocols. Before ProtoBuf, Google used a different format which required additional handling of <a target="_blank" href="https://en.wikipedia.org/wiki/Marshalling_(computer_science)">marshaling</a> for the messages sent. </p>
<p>In addition to that, new versions of the previous format required the developers to make sure that new versions are understood before replacing old ones, making it a hassle to work with.</p>
<p>This overhead motivated Google to design an interface that solves precisely those problems. </p>
<p>ProtoBuf allows changes to the protocol to be introduced without breaking compatibility. Also, servers can pass around the data and execute read operations on the data without modifying its content.</p>
<p>Since the format is somewhat self-describing, ProtoBuf is used as a base for automatic code generation for Serializers and Deserializers.</p>
<p>Another interesting use case is how Google uses it for short-lived <a target="_blank" href="https://searchapparchitecture.techtarget.com/definition/Remote-Procedure-Call-RPC">Remote Procedure Calls</a> (RPC) and to persistently store data in Bigtable. Due to their specific use case, they integrated RPC interfaces into ProtoBuf. This allows for quick and straightforward code stub generation that can be used as starting points for the actual implementation. (More on <a target="_blank" href="https://medium.com/@EmperorRXF/evaluating-performance-of-rest-vs-grpc-1b8bdf0b22da">ProtoBuf RPC</a>.)</p>
<p>Other examples of where ProtoBuf can be useful are for IoT devices that are connected through mobile networks in which the amount of sent data has to be kept small or for applications in countries where high bandwidths are still rare. Sending payloads in optimized, binary formats can lead to noticeable differences in operation cost and speed.</p>
<p>Using <code>gzip</code> compression in your HTTPS communication can further improve those metrics.</p>
<h2 id="heading-what-are-protocol-buffers-and-how-do-they-work">What are Protocol buffers and how do they work?</h2>
<p>Generally speaking, Protocol Buffers are a defined interface for the serialization of structured data. It defines a normalized way to communicate, utterly independent of languages and platforms.</p>
<p>Google advertises its ProtoBuf <a target="_blank" href="https://developers.google.com/protocol-buffers">like this</a>:</p>
<blockquote>
<p><em>Protocol buffers are Google's language-neutral, platform-neutral, extensible mechanism for serializing structured data – think XML, but smaller, faster, and simpler. You define how you want your data to be structured once …</em></p>
</blockquote>
<p>The ProtoBuf interface describes the structure of the data to be sent. Payload structures are defined as “messages” in what is called Proto-Files. Those files always end with a <code>.proto</code> extension.  </p>
<p>For example, the basic structure of a <strong>todolist.proto</strong> file looks like this. We will also look at a complete example in the next section.</p>
<pre><code class="lang-javascript">syntax = <span class="hljs-string">"proto3"</span>;

<span class="hljs-comment">// Not necessary for Python, should still be declared to avoid name collisions </span>
<span class="hljs-comment">// in the Protocol Buffers namespace and non-Python languages</span>
package protoblog;

message TodoList {
   <span class="hljs-comment">// Elements of the todo list will be defined here</span>
   ...
}
</code></pre>
<p>Those files are then used to generate integration classes or stubs for the language of your choice using code generators within the protoc compiler. The current version, Proto3, already supports all the major programming languages. The community supports many more in third-party open-source implementations.</p>
<p>Generated classes are the core elements of Protocol Buffers. They allow the creation of elements by instantiating new messages, based on the <code>.proto</code> files, which are then used for serialization. We’ll look at how this is done with Python in detail in the next section.</p>
<p>Independent of the language for serialization, the messages are serialized into a non-self-describing, binary format that is pretty useless without the initial structure definition.</p>
<p>The binary data can then be stored, sent over the network, and used any other way human-readable data like JSON or XML is. After transmission or storage, the byte-stream can be deserialized and restored using <strong>any</strong> language-specific, compiled protobuf class we generate from the .proto file.  </p>
<p>Using Python as an example, the process could look something like this:</p>
<p><img src="https://lh4.googleusercontent.com/1cHvUkBU5WKklD0ErnHpdVIdal-SBh5wfLQr5n-75jE6mj62ScOZ7mTc-AZLu9LBeYRaKxLim0OWQi4GNKgmYHFtd-AVQjlE6pX2O3j7wa-9wX69JkcetgQt5fAHqM1gNCGo-iv8" alt="Image" width="1600" height="529" loading="lazy"></p>
<p>First, we create a new todo list and fill it with some tasks. This todo list is then serialized and sent over the network, saved in a file, or persistently stored in a database.</p>
<p>The sent byte stream is deserialized using the parse method of our language-specific, compiled class.  </p>
<p>Most current architectures and infrastructures, especially microservices, are based on REST, WebSockets, or GraphQL communication. However, when speed and efficiency are essential, low-level RPCs can make a huge difference.</p>
<p>Instead of high overhead protocols, we can use a fast and compact way to move data between the different entities into our service without wasting many resources. </p>
<h3 id="heading-but-why-isnt-it-used-everywhere-yet"><strong>But why isn’t it used everywhere yet?</strong></h3>
<p>Protocol Buffers are a bit more complicated than other, human-readable formats. This makes them comparably harder to debug and integrate into your applications.</p>
<p>Iteration times in engineering also tend to increase since updates in the data require updating the proto files before usage.</p>
<p>Careful considerations have to be made since ProtoBuf might be an over-engineered solution in many cases.</p>
<h3 id="heading-what-alternatives-do-i-have">What alternatives do I have?</h3>
<p>Several projects take a similar approach to Google’s Protocol Buffers.</p>
<p><a target="_blank" href="https://google.github.io/flatbuffers/">Google’s Flatbuffers</a> and a third party implementation, called <a target="_blank" href="https://capnproto.org/">Cap’n Proto</a>, are more focused on removing the parsing and unpacking step, which is necessary to access the actual data when using ProtoBufs. They have been designed explicitly for performance-critical applications, making them even faster and more memory efficient than ProtoBuf.  </p>
<p>When focusing on the RPC capabilities of ProtoBuf (used with gRPC), there are projects from other large companies like Facebook (Apache Thrift) or Microsoft (Bond protocols) that can offer alternatives.</p>
<h2 id="heading-python-and-protocol-buffers">Python and Protocol Buffers</h2>
<p>Python already provides some ways of data persistence using pickling. Pickling is useful in Python-only applications. It's not well suited for more complex scenarios where data sharing with other languages or changing schemas is involved.  </p>
<p>Protocol Buffers, in contrast, are developed for exactly those scenarios.<br>The <code>.proto</code> files, we’ve quickly covered before, allow the user to generate code for many supported languages.</p>
<p>To compile the <code>.proto</code> file to the language class of our choice, we use <strong>protoc,</strong> the proto compiler.  </p>
<p>If you don’t have the protoc compiler installed, there are excellent guides on how to do that:</p>
<ul>
<li><a target="_blank" href="http://google.github.io/proto-lens/installing-protoc.html">MacOS / Linux</a></li>
<li><a target="_blank" href="https://github.com/protocolbuffers/protobuf/blob/master/src/README.md#c-installation---windows">Windows</a> </li>
</ul>
<p>Once we’ve installed protoc on our system, we can use an extended example of our todo list structure from before and generate the Python integration class from it.</p>
<pre><code class="lang-javascript">syntax = <span class="hljs-string">"proto3"</span>;

<span class="hljs-comment">// Not necessary for Python but should still be declared to avoid name collisions </span>
<span class="hljs-comment">// in the Protocol Buffers namespace and non-Python languages</span>
package protoblog;

<span class="hljs-comment">// Style guide prefers prefixing enum values instead of surrounding</span>
<span class="hljs-comment">// with an enclosing message</span>
enum TaskState {
    TASK_OPEN = <span class="hljs-number">0</span>;
    TASK_IN_PROGRESS = <span class="hljs-number">1</span>;
    TASK_POST_PONED = <span class="hljs-number">2</span>;
    TASK_CLOSED = <span class="hljs-number">3</span>;
    TASK_DONE = <span class="hljs-number">4</span>;
}

message TodoList {
    int32 owner_id = <span class="hljs-number">1</span>;
    string owner_name = <span class="hljs-number">2</span>;

    message ListItems {
        TaskState state = <span class="hljs-number">1</span>;
        string task = <span class="hljs-number">2</span>;
        string due_date = <span class="hljs-number">3</span>;
    }

    repeated ListItems todos = <span class="hljs-number">3</span>;
}
</code></pre>
<p>Let’s take a more detailed look at the structure of the <code>.proto</code> file to understand it.<br>In the first line of the proto file, we define whether we’re using Proto2 or 3. In this case, we’re using <a target="_blank" href="https://developers.google.com/protocol-buffers/docs/proto3">Proto3</a>.</p>
<p>The most uncommon elements of proto files are the numbers assigned to each entity of a message. Those dedicated numbers make each attribute unique and are used to identify the assigned fields in the binary encoded output. </p>
<p>One important concept to grasp is that only values 1-15 are encoded with one less byte (Hex), which is useful to understand so we can assign higher numbers to the less frequently used entities. The numbers define <strong>neither</strong> <strong>the order</strong> of encoding <strong>nor the position</strong> of the given attribute in the encoded message.</p>
<p>The package definition helps prevent name clashes. In Python, packages are defined by their directory. Therefore providing a package attribute doesn’t have any effect on the generated Python code. </p>
<p>Please note that this should still be declared to avoid protocol buffer related name collisions and for other languages like Java.</p>
<p>Enumerations are simple listings of possible values for a given variable.<br>In this case, we define an Enum for the possible states of each task on the todo list.<br>We’ll see how to use them in a bit when we look at the usage in Python.  </p>
<p>As we can see in the example, we can also nest messages inside messages.<br>If we, for example, want to have a list of todos associated with a given todo list, we can use the <strong>repeated</strong> keyword, which is comparable to dynamically sized arrays.</p>
<p>To generate usable integration code, we use the proto compiler which compiles a given .proto file into language-specific integration classes. In our case we use the <strong>--python-out</strong> argument to generate Python-specific code.</p>
<p><code>protoc -I=. --python_out=. ./todolist.proto</code></p>
<p>In the terminal, we invoke the protocol compiler with three parameters:</p>
<ol>
<li><strong>-I</strong>: defines the directory where we search for any dependencies (we use . which is the current directory)</li>
<li><strong>--python_out</strong>: defines the location we want to generate a Python integration class in (again we use <strong>.</strong> which is the current directory)</li>
<li>The last <strong>unnamed parameter</strong> defines the .proto file that will be compiled (we use the todolist.proto file in the current directory)</li>
</ol>
<p><img src="https://lh6.googleusercontent.com/eZJUxepo7Ath2NalDKS75Aezx7DFnZlt0IuvfteCIczCgZBkBg2sgdoMVxr8FSiQf6u4gDkEDFcewGyrvqZqzoYUzdZnGi_WoU8-lXKamFrnGudnZy31pmQkt1LaLNCTWOTB3y3v" alt="Image" width="1162" height="602" loading="lazy"></p>
<p>This creates a new Python file called _pb2.py. In our case, it is todolist_pb2.py. When taking a closer look at this file, we won’t be able to understand much about its structure immediately. </p>
<p>This is because the generator doesn’t produce direct data access elements, but further abstracts away the complexity using <a target="_blank" href="https://stackoverflow.com/questions/100003/what-are-metaclasses-in-python">metaclasses</a> and descriptors for each attribute. They describe how a class behaves instead of each instance of that class.  </p>
<p>The more exciting part is how to use this generated code to create, build, and serialize data. A straightforward integration done with our recently generated class is seen in the following:</p>
<pre><code class="lang-python"><span class="hljs-keyword">import</span> todolist_pb2 <span class="hljs-keyword">as</span> TodoList

my_list = TodoList.TodoList()
my_list.owner_id = <span class="hljs-number">1234</span>
my_list.owner_name = <span class="hljs-string">"Tim"</span>

first_item = my_list.todos.add()
first_item.state = TodoList.TaskState.Value(<span class="hljs-string">"TASK_DONE"</span>)
first_item.task = <span class="hljs-string">"Test ProtoBuf for Python"</span>
first_item.due_date = <span class="hljs-string">"31.10.2019"</span>

print(my_list)
</code></pre>
<p>It merely creates a new todo list and adds one item to it. We then print the todo list element itself and can see the non-binary, non-serialized version of the data we just defined in our script.</p>
<pre><code class="lang-json">owner_id: <span class="hljs-number">1234</span>
owner_name: <span class="hljs-string">"Tim"</span>
todos {
  state: TASK_DONE
  task: <span class="hljs-string">"Test ProtoBuf for Python"</span>
  due_date: <span class="hljs-string">"31.10.2019"</span>
}
</code></pre>
<p>Each Protocol Buffer class has methods for reading and writing messages using a <a target="_blank" href="https://developers.google.com/protocol-buffers/docs/encoding">Protocol Buffer-specific encoding</a>, that encodes messages into binary format.<br>Those two methods are <code>SerializeToString()</code> and <code>ParseFromString()</code>.</p>
<pre><code class="lang-python"><span class="hljs-keyword">import</span> todolist_pb2 <span class="hljs-keyword">as</span> TodoList

my_list = TodoList.TodoList()
my_list.owner_id = <span class="hljs-number">1234</span>

<span class="hljs-comment"># ...</span>

<span class="hljs-keyword">with</span> open(<span class="hljs-string">"./serializedFile"</span>, <span class="hljs-string">"wb"</span>) <span class="hljs-keyword">as</span> fd:
    fd.write(my_list.SerializeToString())


my_list = TodoList.TodoList()
<span class="hljs-keyword">with</span> open(<span class="hljs-string">"./serializedFile"</span>, <span class="hljs-string">"rb"</span>) <span class="hljs-keyword">as</span> fd:
    my_list.ParseFromString(fd.read())

print(my_list)
</code></pre>
<p>In the code example above, we write the Serialized string of bytes into a file using the <strong>wb</strong> flags.</p>
<p>Since we have already written the file, we can read back the content and Parse it using ParseFromString. ParseFromString calls on a new instance of our Serialized class using the <strong>rb</strong> flags and parses it.</p>
<p>If we serialize this message and print it in the console, we get the byte representation which looks like this.</p>
<p><code>b'\x08\xd2\t\x12\x03Tim\x1a(\x08\x04\x12\x18Test ProtoBuf for Python\x1a\n31.10.2019'</code></p>
<p>Note the b in front of the quotes. This indicates that the following string is composed of byte octets in Python.</p>
<p>If we directly compare this to, e.g., XML, we can see the impact ProtoBuf serialization has on the size.</p>
<pre><code class="lang-xml"><span class="hljs-tag">&lt;<span class="hljs-name">todolist</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">owner_id</span>&gt;</span>1234<span class="hljs-tag">&lt;/<span class="hljs-name">owner_id</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">owner_name</span>&gt;</span>Tim<span class="hljs-tag">&lt;/<span class="hljs-name">owner_name</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">todos</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">todo</span>&gt;</span>
            <span class="hljs-tag">&lt;<span class="hljs-name">state</span>&gt;</span>TASK_DONE<span class="hljs-tag">&lt;/<span class="hljs-name">state</span>&gt;</span>
            <span class="hljs-tag">&lt;<span class="hljs-name">task</span>&gt;</span>Test ProtoBuf for Python<span class="hljs-tag">&lt;/<span class="hljs-name">task</span>&gt;</span>
            <span class="hljs-tag">&lt;<span class="hljs-name">due_date</span>&gt;</span>31.10.2019<span class="hljs-tag">&lt;/<span class="hljs-name">due_date</span>&gt;</span>
        <span class="hljs-tag">&lt;/<span class="hljs-name">todo</span>&gt;</span>
    <span class="hljs-tag">&lt;/<span class="hljs-name">todos</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">todolist</span>&gt;</span>
</code></pre>
<p>The JSON representation, non-uglified, would look like this.</p>
<pre><code class="lang-json">{
    <span class="hljs-attr">"todoList"</span>: {
        <span class="hljs-attr">"ownerId"</span>: <span class="hljs-string">"1234"</span>,
        <span class="hljs-attr">"ownerName"</span>: <span class="hljs-string">"Tim"</span>,
        <span class="hljs-attr">"todos"</span>: [
            {
                <span class="hljs-attr">"state"</span>: <span class="hljs-string">"TASK_DONE"</span>,
                <span class="hljs-attr">"task"</span>: <span class="hljs-string">"Test ProtoBuf for Python"</span>,
                <span class="hljs-attr">"dueDate"</span>: <span class="hljs-string">"31.10.2019"</span>
            }
        ] 
    }
}
</code></pre>
<p>Judging the different formats only by the total number of bytes used, ignoring the memory needed for the overhead of formatting it, we can of course see the difference.  </p>
<p>But in addition to the memory used for the data, we also have <strong>12 extra bytes in ProtoBuf</strong> for formatting serialized data. Comparing that to XML, we have <strong>171 extra bytes in XML</strong> for formatting serialized data.</p>
<p>Without Schema, we need <strong>136 extra bytes in JSON</strong> for formatting serialized data<strong>.</strong></p>
<p>If we’re talking about several thousands of messages sent over the network or stored on disk, ProtoBuf can make a difference.</p>
<p>However, there is a catch. The platform Auth0.com created an extensive comparison between ProtoBuf and JSON. It shows that, when compressed, the size difference between the two can be marginal (only around 9%).</p>
<p>If you’re interested in the exact numbers, please refer to the <a target="_blank" href="https://auth0.com/blog/beating-json-performance-with-protobuf/">full article</a>, which gives a detailed analysis of several factors like size and speed.</p>
<p>An interesting side note is that each data type has a default value. If attributes are not assigned or changed, they will maintain the default values. In our case, if we don’t change the TaskState of a ListItem, it has the state of “TASK_OPEN” by default. The significant advantage of this is that non-set values are not serialized, saving additional space.</p>
<p>If we, for example, change the state of our task from TASK_DONE to TASK_OPEN, it will not be serialized.</p>
<pre><code class="lang-json">owner_id: <span class="hljs-number">1234</span>
owner_name: <span class="hljs-string">"Tim"</span>
todos {
  task: <span class="hljs-string">"Test ProtoBuf for Python"</span>
  due_date: <span class="hljs-string">"31.10.2019"</span>
}
</code></pre>
<p><code>b'\x08\xd2\t\x12\x03Tim\x1a&amp;\x12\x18Test ProtoBuf for Python\x1a\n31.10.2019'</code></p>
<h2 id="heading-final-notes">Final Notes</h2>
<p>As we have seen, Protocol Buffers are quite handy when it comes to speed and efficiency when working with data. Due to its powerful nature, it can take some time to get used to the ProtoBuf system, even though the syntax for defining new messages is straightforward. </p>
<p>As a last note, I want to point out that there were/are discussions going on about whether Protocol Buffers are “useful” for regular applications. They were developed explicitly for problems Google had in mind.  </p>
<p>If you have any questions or feedback, feel free to reach out to me on any social media like <a target="_blank" href="https://twitter.com/timigrossmann">twitter</a> or <a target="_blank" href="mailto:contact.timgrossmann@gmail.com">email</a> :)</p>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ How to Protocol Buffer Bluetooth Low Energy Service Part 3 ]]>
                </title>
                <description>
                    <![CDATA[ By Jared Wolff This post is originally from www.jaredwolff.com In Part 1 we’ve learned the anatomy of a Protocol Buffer. In Part 2 we’ve learned how a Bluetooth Low Energy Service gets pieced together on the Nordic NRF52 SDK. This final post brings t... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/how-to-protocol-buffer-bluetooth-low-energy-service-part-3/</link>
                <guid isPermaLink="false">66d850524540581f6454411a</guid>
                
                    <category>
                        <![CDATA[ Bluetooth Low Energy ]]>
                    </category>
                
                    <category>
                        <![CDATA[ protocol-buffers ]]>
                    </category>
                
                    <category>
                        <![CDATA[ Tutorial ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ freeCodeCamp ]]>
                </dc:creator>
                <pubDate>Thu, 11 Jul 2019 16:02:24 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2019/07/Protocol-Buffers-Part-2-2.jpg" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>By Jared Wolff</p>
<p><strong>This post is originally from <a target="_blank" href="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-3/">www.jaredwolff.com</a></strong></p>
<p>In <a target="_blank" href="https://www.jaredwolff.com/how-to-define-your-own-bluetooth-low-energy-configuration-service-using-protobuf">Part 1</a> we’ve learned the anatomy of a Protocol Buffer. In <a target="_blank" href="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-2">Part 2</a> we’ve learned how a Bluetooth Low Energy Service gets pieced together on the Nordic NRF52 SDK. This final post brings together all the elements in an end-to-end working example.</p>
<p>Let’s get going!</p>
<p>P.S. this post is lengthy. If you want something to download, <a target="_blank" href="https://www.jaredwolff.com/files/how-to-define-a-protocol-buffer-ble-service-pdf/">click here for a a beautifully formatted PDF.</a> (Added bonus, the PDF has all three parts of this series!)</p>
<h2 id="heading-setting-everything-up">Setting Everything Up</h2>
<p><img src="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-3/images/Untitled-6880beab-c5c2-4184-9012-4a6e68bcebc8.png" alt="Goose attack" width="600" height="400" loading="lazy"></p>
<p>Go look at the <code>Readme.md</code> in each of the example repositories. (You will have to clone the repositories, <a target="_blank" href="https://www.jaredwolff.com/files/protobuf">sign up here to get the code</a>).</p>
<p>I’ve made the setup for the firmware dead simple. For the javascript side, it’s a bit more hairy but’ doable! I’ll also include the instructions here as well:</p>
<h3 id="heading-firmware-setup-for-mac">Firmware Setup (For Mac)</h3>
<ol>
<li>Initialize the full repository (there are submodules!): <code>git submodule update --init</code></li>
<li>Install <code>protoc</code> using Homebrew: <code>brew install protobuf</code></li>
<li>Run <code>make sdk</code>. This will download your SDK files.</li>
<li>Run <code>make tools_osx</code>. This will download your ARMGCC toolchain (for Mac). For other environments see below.</li>
<li>Run <code>make gen_key</code> once (and only once)! This will set up your key for DFU.</li>
<li>Run <code>make</code> and this will build your bootloader and main app.</li>
</ol>
<p><strong>Note:</strong> You only have to do steps 1-5 once.</p>
<h3 id="heading-javascript-app-setup-for-mac">Javascript App Setup (For Mac)</h3>
<p><strong>Prerequisite:</strong> you will need Xcode command line tools. You can get those <a target="_blank" href="https://developer.apple.com/download/more/">here</a>.</p>
<ol>
<li>Clone this repo to a place on your computer</li>
<li>Make sure you have <a target="_blank" href="https://github.com/nvm-sh/nvm/blob/master/README.md">nvm installed</a></li>
<li>Run <code>nvm install v8.0.0</code></li>
<li>Run <code>nvm install v10.15.3</code></li>
<li>Run <code>nvm use v8.0.0</code></li>
<li>Run <code>yarn</code> (if you don’t have yarn <code>npm install yarn -g</code>)</li>
<li>Once installed, run <code>nvm use v10.15.3</code></li>
<li>Then run <code>node index.js</code> to start the example</li>
</ol>
<p>Using NVM helps mitigate a compile issue with the Bluetooth library. You mileage may vary on this one.</p>
<h2 id="heading-how-the-heck-does-this-work">How the heck does this work?</h2>
<p>In this project, the Protocol Buffer has two functions. The first as a “command” to the bluetooth device. Secondly, a “response” to that command from the device.</p>
<p>Our example javascript app command uses “This is” as the payload. With the power of some string operations, let's make a full sentence out of it!</p>
<p>The series of events looks something like this:</p>
<ol>
<li>The test app connects and sends that data using our Bluetooth Low Energy service.</li>
<li>On the firmware decodes the message.</li>
<li>The firmware modifies the original data by adding “ cool.” Resulting in "This is cool"</li>
<li>The firmware encodes the payload and makes the data available for reading.</li>
<li>The app finally reads the characteristic, decodes and displays the result!</li>
</ol>
<p>Seems complicated but there's some benefits to this:</p>
<ol>
<li>In Protocol Buffers, data structures are well defined. This means that it has some great error checking abilities. If you're using any type of data structure you may have to code your own data validation.</li>
<li>Encoding and decoding is simple and straight forward. You can encode same data on different platforms and always get the same decoded result.</li>
</ol>
<p>Want to get the example up and running? Seeing is believing after all. Let's do this.</p>
<h2 id="heading-is-this-thing-on">Is This Thing On?</h2>
<p><img src="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-3/images/Untitled-c72fcf71-f0db-49e5-92d7-44fe601e75fa.png" alt="Phone in hand running NRF connect" width="600" height="400" loading="lazy"></p>
<p>Once you're done with the setup (above), let's get this firmware programmed! Lucky for you it's only two quick steps!</p>
<ol>
<li>Plug in your NRF52 DK board</li>
<li>Run <code>make flash_all</code>. (This compiles and flashes <em>all</em> the code for the project.)</li>
</ol>
<p>Once flashed, the easiest way to know if things are working is when Led 1 is blinking. That means it’s advertising and ready for a connection.</p>
<p><img src="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-3/images/Untitled-6c58e8c5-d005-4b61-a32b-29eea61b1ce7.png" alt="NRF52 DK" width="600" height="400" loading="lazy"></p>
<p>Let’s make sure it’s advertising correctly though. You can grab a tool like NRF Connect for <a target="_blank" href="https://itunes.apple.com/cn/app/nrf-connect/id1054362403?l=en">iOS</a> or Android. Or, you can grab LightBlue. (Also available for <a target="_blank" href="https://apps.apple.com/ru/app/lightblue-explorer/id557428110?l=en">iOS</a> and Android)</p>
<p>Open up one of the app and scan for advertising devices. You’ll be looking for <strong>Nordic_Buttonless</strong>.</p>
<p><img src="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-3/images/Untitled-062f5e84-ec22-4525-a591-4330a55fe30f.png" alt="BLE Apps scanning" width="600" height="400" loading="lazy"></p>
<p>Now let’s connect and double check our connectable services &amp; characteristics:</p>
<p><img src="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-3/images/Untitled-0466566a-1d8a-4e8b-a1c9-f2f76faa116b.png" alt="BLE Apps showing services" width="600" height="400" loading="lazy"></p>
<p>As you can see there are two services. One is Nordic’s DFU service. The other is our Protocol Buffer service!</p>
<p>You can compare <code>PROTOBUF_UUID_BASE</code> in <code>ble_protobuf.h</code> with the UUID of the “Unknown Service”. Nordic’s chips are Little Endian while the data here is Big Endian format. (i.e. you’ll have to reverse the bytes to see that they’re the same!)</p>
<p>You can even click in further to see the characteristics in NRF Connect. In the case of LightBlue, the characteristic UUIDs are already shown.</p>
<h2 id="heading-using-the-javascript-app">Using the Javascript App</h2>
<p>So, once we’re up and advertising, it’s time to run the app.</p>
<p><img src="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-3/images/Untitled-7e92193a-4dbe-4e08-9ebe-ee41be501580.png" alt="Bluetooth javascript app results" width="600" height="400" loading="lazy"></p>
<p>Simply change to the <code>ble-protobuf-js</code> directory and run <code>node index.js</code></p>
<p>If you've installed everything correctly, you should start seeing output like:</p>
<p>    example started
    scanning
    peripheral with ID 06f9b62ec5334454875b9f53d2f3fa74 found with name: Nordic_Buttonles</p>
<p>It should then immediately connect and send data to the device. It should receive the response immediately and print it to the screen.</p>
<p>    connected to Nordic_Buttonles
    Sent: This is
    Received: This is cool.</p>
<p>Bingo!</p>
<h2 id="heading-youve-made-it">You’ve made it!</h2>
<p>? Congrats if you made it this far through the tutorial. You should now be feeling confident enough to start playing with the software code. Maybe you’ll cook up something cool?</p>
<p>Here’s links to some resources that you may find handy.</p>
<ul>
<li><a target="_blank" href="https://developers.google.com/protocol-buffers">Protocol Buffer documentation</a></li>
<li><a target="_blank" href="https://www.github.com/nanopb/nanopb">NanoPB</a> - (the implementation of Protocol Buffers we used for this project)</li>
<li><a target="_blank" href="https://www.nordicsemi.com/DocLib/Content/SDK_Doc/nRF5_SDK/v15-2-0/index">Nordic SDK Documentation</a></li>
<li>Again, here are the links to <a target="_blank" href="https://www.jaredwolff.com/how-to-define-your-own-bluetooth-low-energy-configuration-service-using-protobuf">Part 1</a> and <a target="_blank" href="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-2">Part 2</a></li>
<li>If you haven’t already, <a target="_blank" href="https://www.jaredwolff.com/files/protobuf">get all the code for this project</a></li>
</ul>
<h2 id="heading-conclusion">Conclusion</h2>
<p>Protocol Buffers are quite versatile and convenient. Using them with Bluetooth Low Energy service is one way that you can take advantage. As the connected world of IoT continues to expand, I have no doubt that we'll be seeing more use cases in the future!</p>
<p>I hope this has inspired you to incorporate Protocol Buffers into your own project(s). Make sure you <a target="_blank" href="https://www.jaredwolff.com/files/protobuf">download the sample code</a> and get started right now.</p>
<p>Has this tutorial been useful for you? Let me know what you think.</p>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ Improve Your Bluetooth Project With This Valuable Tool: Part 2! ]]>
                </title>
                <description>
                    <![CDATA[ By Jared Wolff This post is originally from www.jaredwolff.com. This is Part 2 of configuring your own Bluetooth Low Energy Service using a Nordic NRF52 series processor. If you haven’t seen Part 1 go back and check it out. I’ll be waiting right here... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/improve-your-bluetooth-project-with-this-valuable-tool-part-2/</link>
                <guid isPermaLink="false">66d8505dda89a73e2ddf57b2</guid>
                
                    <category>
                        <![CDATA[ Bluetooth Low Energy ]]>
                    </category>
                
                    <category>
                        <![CDATA[ protocol-buffers ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ freeCodeCamp ]]>
                </dc:creator>
                <pubDate>Mon, 01 Jul 2019 07:57:49 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2019/07/Protocol-Buffers-Part-2.jpg" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>By Jared Wolff</p>
<p><strong>This post is originally from <a target="_blank" href="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-2/">www.jaredwolff.com.</a></strong></p>
<p>This is Part 2 of configuring your own Bluetooth Low Energy Service using a Nordic NRF52 series processor. If you haven’t seen <a target="_blank" href="https://www.jaredwolff.com/how-to-define-your-own-bluetooth-low-energy-configuration-service-using-protobuf">Part 1</a> go back and check it out. I’ll be waiting right here..</p>
<p>If you’re with me thus far,  high five. ?</p>
<p>Let’s jump in!</p>
<p>So far we’ve created an efficient cross platform data structure using Protocol Buffers. This Protocol Buffer in particular can be used to send these defined data structures a Bluetooth Low Energy Service. In this part, I’ll show you the inner workings of creating the service from scratch.</p>
<p>P.S. this post is lengthy. If you want something to download, <a target="_blank" href="https://www.jaredwolff.com/files/how-to-define-a-protocol-buffer-ble-service-pdf/">click here for a a beautifully formatted PDF.</a> (Added bonus, the PDF has all three parts of this series!)</p>
<h2 id="heading-creating-the-service">Creating the Service</h2>
<p><img src="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-2/images/doorman.jpg" alt="Door Peoeple" width="600" height="400" loading="lazy"></p>
<p>Dealing with Bluetooth Low Energy in general can seem overwhelming. As I discussed <a target="_blank" href="https://www.jaredwolff.com/get-started-with-bluetooth-low-energy/">here</a>,  there’s a few moving parts that you need to keep in mind.</p>
<p>The best way to create a new service is to copy an already existing one! I’ve done this by:</p>
<ol>
<li>Go to the sdk -&gt; components -&gt; ble -&gt; ble_services -&gt; ble_bas</li>
<li>Copy <code>ble_bas.h</code> to <code>include/ble</code></li>
<li>Copy <code>ble_bas.c</code> to <code>src/ble</code></li>
</ol>
<p>I’ve then renamed them from <code>ble_bas</code> to <code>ble_protobuf</code> to be consistent. I’ve also done the same inside the files. (BAS is the battery level service used to report battery voltage or relative charge using a percentage)</p>
<p>I’ve also gone ahead and removed all the battery measurement  functions as they will be replaced.  This part of the process is fairly tedious and prone to error. If you’re new to the Nordic SDK, <a target="_blank" href="https://www.jaredwolff.com/files/protobuf/">I highly recommend you download the example code for this post.</a></p>
<h3 id="heading-adding-a-uuid">Adding a UUID</h3>
<p>Normally, for a vendor defined service you’ll have to use your own UUID. There are certain ranges of UUIDs that are reserved for the Bluetooth SIG. Supposedly you can also reserve your own UUID if you’re a member. <a target="_blank" href="https://stackoverflow.com/questions/10243769/what-range-of-bluetooth-uuids-can-be-used-for-vendor-defined-profiles">Here’s a handy post on Stack Overflow on the subject.</a></p>
<p>In our case, I’ve defined a UUID that I’ve used for other projects. If you go to <code>ble_protobuf.h</code> you can see the UUIDs for both the service and the characteristic:</p>
<pre><code class="lang-c"><span class="hljs-comment">// UUID for the Service &amp; Char</span>
<span class="hljs-meta">#<span class="hljs-meta-keyword">define</span> PROTOBUF_UUID_BASE   {0x72, 0x09, 0x1a, 0xb3, 0x5f, 0xff, 0x4d, 0xf6, \
                               0x80, 0x62, 0x45, 0x8d, 0x00, 0x00, 0x00, 0x00}</span>
<span class="hljs-meta">#<span class="hljs-meta-keyword">define</span> PROTOBUF_UUID_SERVICE     0xf510</span>
<span class="hljs-meta">#<span class="hljs-meta-keyword">define</span> PROTOBUF_UUID_CONFIG_CHAR (PROTOBUF_UUID_SERVICE + 1)</span>
</code></pre>
<p>Both <code>PROTOBUF_UUID_BASE</code> <code>PROTOBUF_UUID_SERVICE</code>  are used in <code>ble_protobuf_init</code> The last one is used in <code>command_char_add</code> (I’ll describe that a bit more below).</p>
<p>You can go without defining a BASE ID but I highly recommend you go the extra mile. That way your application will be impervious to future Bluetooth protocol updates.</p>
<h2 id="heading-creating-the-characteristic">Creating the Characteristic</h2>
<p><img src="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-2/images/man-641691_1280.jpg" alt="Open Those PICKLES!" width="600" height="400" loading="lazy"></p>
<p>Nordic has a fairly straight forward way of initializing separate characteristics in each service. For each characteristic, there is a <code>char_add</code> function which then configures and add the characteristic to the service.</p>
<h3 id="heading-configure-your-characteristic-withbleaddcharparamst">Configure your Characteristic with<code>ble_add_char_params_t</code></h3>
<p>Nordic has put the configurations parameters for a BLE Characteristic into a logical (and helpful) struct. If you’re developing on a different platform you may find the same settings though all not in one place! (Or handled logically… ?)</p>
<p>Here’s the breakdown of the struct:</p>
<pre><code class="lang-c"><span class="hljs-keyword">typedef</span> <span class="hljs-class"><span class="hljs-keyword">struct</span>
{</span>
    <span class="hljs-keyword">uint16_t</span>                    uuid;
    <span class="hljs-keyword">uint8_t</span>                     uuid_type;
    <span class="hljs-keyword">uint16_t</span>                    max_len;
    <span class="hljs-keyword">uint16_t</span>                    init_len;
    <span class="hljs-keyword">uint8_t</span> *                   p_init_value;
    <span class="hljs-keyword">bool</span>                        is_var_len;
    <span class="hljs-keyword">ble_gatt_char_props_t</span>       char_props;
    <span class="hljs-keyword">ble_gatt_char_ext_props_t</span>   char_ext_props;
    <span class="hljs-keyword">bool</span>                        is_defered_read;
    <span class="hljs-keyword">bool</span>                        is_defered_write;
    <span class="hljs-keyword">security_req_t</span>              read_access;
    <span class="hljs-keyword">security_req_t</span>              write_access;
    <span class="hljs-keyword">security_req_t</span>              cccd_write_access;
    <span class="hljs-keyword">bool</span>                        is_value_user;
    <span class="hljs-keyword">ble_add_char_user_desc_t</span>    *p_user_descr;
    <span class="hljs-keyword">ble_gatts_char_pf_t</span>         *p_presentation_format;
} <span class="hljs-keyword">ble_add_char_params_t</span>;
</code></pre>
<p>It’s here that you tell the BLE Stack about what type of characteristic this is. In this example I use a handful of parameters to define the Protobuf Command Characteristic.</p>
<p><code>uuid</code> defines the address of how the characteristic will be accessed. If you’re defining your own service.
<code>max_len</code> is the maximum length of data that you may send though the characteristic. That’s why it’s important to set <code>max_size</code> in your Protocol Buffer <code>.options</code> file for all variable length parameters. Once you compile your Protocol Buffers you’ll get a <code>*_size</code> variable much like the one defined in <code>command.pb.h</code> Here's a snippet of what it looks like below:</p>
<pre><code class="lang-c"><span class="hljs-comment">/* Maximum encoded size of messages (where known) */</span>
<span class="hljs-meta">#<span class="hljs-meta-keyword">define</span> event_size                               67</span>
</code></pre>
<p>Thus when defining <code>ble_add_char_params_t</code> I set <code>max_len</code> to <code>event_size</code>:</p>
<pre><code class="lang-c">add_char_params.uuid                      = PROTOBUF_UUID_CONFIG_CHAR;
add_char_params.max_len                   = event_size;
add_char_params.is_var_len                = <span class="hljs-literal">true</span>;
</code></pre>
<p>Along the same lines, because we’re using a <em>string</em> as one of the parameters in the Protocol Buffer, this data can be of variable size.  <code>is_var_len</code> is handy to make sure that the right amount of bytes is sent and received. The decode function of the Protocol Buffers will fail if more data is fed in than necessary. (I learned this the hard way!)</p>
<p><code>char_props</code> define the permissions for the characteristic. If you’re familiar with file system permissions on a computer, this will be second nature to you. In this example, <strong>read</strong> and <strong>write</strong> is what we’re looking for.</p>
<p>Finally, parameters ending in <code>_access</code> determine the security type used. In most cases <code>SEC_OPEN</code> or <code>SEC_JUST_WORKS</code>is more than sufficient. If you’re handling critical data (passwords, etc) you may have to implement a second layer of encryption or enable a higher level security mode.</p>
<p>If you’re looking on more info about Bluetooth Low Energy security, <a target="_blank" href="https://duo.com/decipher/understanding-bluetooth-security">here’s a useful post on the subject.</a></p>
<h3 id="heading-add-dat-char">Add. dat. char.</h3>
<p>Once you’ve defined your params, it’s as easy as calling the <code>characteristic_add</code> function. This will associate this new characteristic with the related service. The first argument is the service handle, the second the configuration parameters and the third is a pointer to the handles for the characteristic. (See below)</p>
<pre><code class="lang-c"><span class="hljs-function"><span class="hljs-keyword">uint32_t</span> <span class="hljs-title">characteristic_add</span><span class="hljs-params">(<span class="hljs-keyword">uint16_t</span>                   service_handle,
                            <span class="hljs-keyword">ble_add_char_params_t</span> *    p_char_props,
                            <span class="hljs-keyword">ble_gatts_char_handles_t</span> * p_char_handle)</span></span>
</code></pre>
<h2 id="heading-getting-it-running">Getting it Running</h2>
<p>Setting everything up inside <code>ble_protobuf.c</code> is 90% of the battle. The final mile requires some bits being added to  <code>services_init</code> in <code>main.c</code></p>
<pre><code class="lang-c">    <span class="hljs-keyword">ble_protobuf_init_t</span>       protobuf_init = {<span class="hljs-number">0</span>};

    protobuf_init.evt_handler          = ble_protobuf_evt_hanlder;
    protobuf_init.bl_rd_sec            = SEC_JUST_WORKS;
    protobuf_init.bl_cccd_wr_sec       = SEC_JUST_WORKS;
    protobuf_init.bl_wr_sec            = SEC_JUST_WORKS;

    err_code = ble_protobuf_init(&amp;m_protobuf,&amp;protobuf_init);
    APP_ERROR_CHECK(err_code);
</code></pre>
<p>The above allows events to be funneled back to the main context. That way your app becomes much more interactive with the core logic of your firmware code. In Nordic’s examples they’ve also brought the security parameters out so they can be defined in the main context as well.</p>
<p><em>Side note:</em> <code>m_protobuf</code> is defined using a macro from <code>ble_protobuf.h</code> It not only creates a static instance of the service but it also defines the callback that is used for handling events.</p>
<pre><code class="lang-c"><span class="hljs-comment">/**@brief Macro for defining a ble_protobuf instance.
 *
 * @param   _name  Name of the instance.
 * @hideinitializer
 */</span>
<span class="hljs-meta">#<span class="hljs-meta-keyword">define</span> BLE_PROTOBUF_DEF(_name)                          \
    static ble_protobuf_t _name;                         \
    NRF_SDH_BLE_OBSERVER(_name ## _obs,             \
                         BLE_PROTOBUF_BLE_OBSERVER_PRIO, \
                         ble_protobuf_on_ble_evt,        \
                         &amp;_name)</span>
</code></pre>
<p>If you're making your own service, you'll have to update the function name for the event handler. If you need to tweak priorities you can define/update that as well.</p>
<h2 id="heading-what-happens-when-this-characteristic-is-written-to">What happens when this characteristic is written to?</h2>
<p><img src="https://www.jaredwolff.com/how-to-protocol-buffer-bluetooth-low-energy-service-part-2/images/person-629676_1280.jpg" alt="Smoke Signal" width="600" height="400" loading="lazy"></p>
<p><code>ble_protobuf_on_ble_evt</code> is the main way that events are handled within Bluetooth Low Energy services. We’re most concerned with the <code>BLE_GATTS_EVT_WRITE</code> event but you can trigger on any GATT event that tickles your fancy.</p>
<p><code>on_write</code> is where the action happens. It takes the data that is written to the characteristic and decodes it according to <code>event_fields</code> It’s all put conveniently into a struct for additional processing, etc. If an error happens in decoding, <code>pb_decode</code> returns an error. Once modified, the data is encoded and made available for reading. Since reading <a target="_blank" href="https://www.jaredwolff.com/how-to-define-your-own-bluetooth-low-energy-configuration-service-using-protobuf">Part 1</a>, the calls to <code>pb_decode</code> and <code>pb_encode</code> should look very familiar!</p>
<p>Of course, you can have your firmware do whatever you want to. The Bluetooth Energy World is your oyster.</p>
<h2 id="heading-final-notes">Final Notes</h2>
<p>When adding new services to a Bluetooth Low Energy example, you may have to make some changes to the underlying code.</p>
<p>For example, <code>sdk_config.h</code> may need some changes. Particularly <code>NRF_SDH_BLE_VS_UUID_COUNT</code> needs to be increased depending how many service UUIDs are made available. For this project, I am also using the  DFU service (as it should be a default for all connected projects!!)</p>
<p>Another important aspect is memory and flash management. The default <code>.ld</code> file that comes with the BLE DFU service may not be sufficient for another BLE Service. The only way you’ll know there’s not enough is when you compile and flash it to a NRF52 device. If the device boots up stating there’s not enough memory, you’ll have to make the suggested changes. The error will show up on the debug console where this message normally shows up:</p>
<pre><code class="lang-bash">&lt;info&gt; app: Setting vector table to bootloader: 0x00078000
&lt;info&gt; app: Setting vector table to main app: 0x00026000
</code></pre>
<p>Learn more about how to get the Debug Console set up <a target="_blank" href="https://www.jaredwolff.com/files/protobuf/">in the example code here.</a></p>
<h2 id="heading-conclusion">Conclusion</h2>
<p>In this part I’ve shown you the inner workings of a custom Bluetooth Low Energy service using Protocol Buffers. In the last part, I’ll show you how to load the firmware, run the example javascript app and test our freshly developed Protocol Buffer!</p>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ UPDATED: Improve Your Bluetooth Project With This Valuable Tool ]]>
                </title>
                <description>
                    <![CDATA[ By Jared Wolff This post is originally from www.jaredwolff.com One of the most confusing things about Bluetooth Low Energy is how data is moved around. Depending on your application, your device state may be fairly complex. That means having an indiv... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/improve-your-bluetooth-project-with-this-valueable-tool/</link>
                <guid isPermaLink="false">66d8505ec15439a8d5631e81</guid>
                
                    <category>
                        <![CDATA[ Bluetooth Low Energy ]]>
                    </category>
                
                    <category>
                        <![CDATA[ protocol-buffers ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ freeCodeCamp ]]>
                </dc:creator>
                <pubDate>Tue, 11 Jun 2019 15:05:54 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2019/06/protobuf.jpg" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>By Jared Wolff</p>
<p><strong>This post is originally from <a target="_blank" href="https://www.jaredwolff.com/how-to-define-your-own-bluetooth-low-energy-configuration-service-using-protobuf/">www.jaredwolff.com</a></strong></p>
<p>One of the most confusing things about Bluetooth Low Energy is how data is moved around. Depending on your application, your device state may be fairly complex. That means having an individual endpoint for every piece of data is suicide by Bluetooth.</p>
<p>So, what’s he solution?</p>
<p><a target="_blank" href="https://developers.google.com/protocol-buffers/">Protocol Buffers.</a></p>
<p>A protocol buffer is a programatic way to encode/decode optimized structured data. They can be shared and manipulated across almost any platform. Nordic actually uses a variant of it for their DFU service.</p>
<p>There was a lot of buzz words in the first few sentences. Hopefully, by the end of this post you’ll understand exactly what I’m talking about.</p>
<p>In this tutorial, i'll include fully flushed out example code that you can clone and start using immediately. All you need is one of these:</p>
<p><img src="https://www.jaredwolff.com/how-to-define-your-own-bluetooth-low-energy-configuration-service-using-protobuf/images/DSC01544.jpg" alt="NRF52 Development Kit" width="600" height="400" loading="lazy"></p>
<p>So, how do you use this magical software?</p>
<p>Read on!</p>
<p>P.S. this post is lengthy. If you want something to download, <a target="_blank" href="https://www.jaredwolff.com/files/how-to-define-a-protocol-buffer-ble-service-pdf/">click here for a a beautifully formatted PDF.</a> (Added bonus, the PDF has all three parts of this series!)</p>
<h2 id="heading-install">Install</h2>
<p>The first part of the process is to make sure you’ve installed all the correct utilities.  Depending on what programming language will determine what you install and use. In this case I’ll outline the utilities that I have used for several projects in the past using C, Go and Javascript.</p>
<p><code>protoc</code> is the most important utility you’ll have to install here. It's the Protobuf "compiler" which takes your <code>.proto</code> and <code>.options</code> files and turns them into static code.</p>
<ol>
<li>For Mac, download the appropriate release <a target="_blank" href="https://github.com/google/protobuf/releases">here</a>.</li>
<li>Unzip the folder</li>
<li>Run <code>./autogen.sh &amp;&amp; ./configure &amp;&amp; make</code> in the folder</li>
<li>If you get an error <code>autoreconf: failed to run aclocal: No such file or directory</code> install <code>autoconf</code> using Homebrew:</li>
</ol>
<p><code>brew install autoconf &amp;&amp; brew install automake</code></p>
<p>Then, re-run step 3.</p>
<ol>
<li>Then run:</li>
</ol>
<pre><code>make check
sudo make install
which protoc
</code></pre><p>Consider <code>protoc</code> the compiler for Protocol Buffers. It can either output raw files or libraries directly. That’s because it’s got Go support built in.</p>
<p>That raw data can also be used to generate static libraries for other languages. That usually requires an extra utility (or utilities). I describe the two that the Dondi Lib project used below.</p>
<ol start="2">
<li><p><code>nanopb</code> is a python script used to create C libraries that encode/decode your structured data.
It can be installed by navigating to the <a target="_blank" href="https://github.com/nanopb/nanopb">nanopb git repo</a> and downloading the appropriate files. The most important pieces to include:</p>
</li>
<li><p><code>pb_encode.c</code>, <code>pb_decode.c</code> and <code>pb_common.c</code></p>
</li>
<li><code>/generator/nanopb_generator.py</code></li>
<li><p>And the <code>/generator/nanopb/</code>directory co-located with <code>nanopb_generator.py</code></p>
<p> <code>nanopb</code> is meant for deployment on embedded platforms. It's different from <code>protoc-c</code> (the regular C variant) because it is optimized for resource constrained systems like embedded processors. Buffers have finite sizes. There's no memory allocation! Depending on if there's bi-directional communication, you can only import and use the encoding functionality or decoding functionality.</p>
</li>
<li><p><code>pbjs</code> uses the output from <code>protoc</code> to generate a static javascript library. This is powerful because you can then use it in any javascript application. The best way to install <code>pbjs</code> is by running:</p>
<pre><code>   npm install -g protobufjs
</code></pre></li>
</ol>
<p>I've simplified this step a bit in the example code. <a target="_blank" href="https://www.jaredwolff.com/files/protobuf/">Get started by cloning the repos here.</a></p>
<h2 id="heading-setting-up-the-protocol-buffer">Setting up the protocol buffer</h2>
<p>Create a file called <code>command.proto</code>. You can make the contents of that file what's below:</p>
<pre><code>syntax = <span class="hljs-string">"proto3"</span>;

message event {
  enum event_type {
    command = <span class="hljs-number">0</span>;
    response = <span class="hljs-number">1</span>;
  }
  event_type type = <span class="hljs-number">1</span>;
  string message = <span class="hljs-number">2</span>;
}
</code></pre><p>It may look foreign at first but once you take a deeper look, it’s not that much different than a standard C struct or hash table.</p>
<p>I'm using two types of data in this example: a <code>string</code> and <code>enum</code> as a type. There are actually a few more which you can read up at the <a target="_blank" href="https://developers.google.com/protocol-buffers/docs/proto">documentation</a>. When compiled, the equivalent c struct looks like:</p>
<pre><code><span class="hljs-comment">/* Struct definitions */</span>
typedef struct _event {
    event_event_type type;
    char message[<span class="hljs-number">64</span>];
<span class="hljs-comment">/* @@protoc_insertion_point(struct:event) */</span>
} event;
</code></pre><p>Where <code>event_event_type</code> is</p>
<pre><code><span class="hljs-comment">/* Enum definitions */</span>
typedef enum _event_event_type {
    event_event_type_command = <span class="hljs-number">0</span>,
    event_event_type_response = <span class="hljs-number">1</span>
} event_event_type;
</code></pre><p>You can nest as many messages inside each other as your hearts content. Typically though, a message is as small as possible so data transmission is as efficient as possible. This is particularly important for resource constrained systems or LTE deployments where you're charged for <em>every</em> megabyte used. <strong>Note:</strong> when elements are not used or defined they are typically <em>not</em> included in the encoded Protocol Buffer payload.</p>
<p>Normally, when you create a generic message like this, there is no limit to the size of the string <code>message</code>. That option can be set in the <code>.options</code> file:</p>
<pre><code>event.message    max_size:<span class="hljs-number">64</span>
</code></pre><p>This way, the memory can be statically allocated in my microprocessor code at compile time. If the message size is greater than 64 bytes then it will get chopped off in the code (or you'll simply get an error during decode). It's up to you, the software engineer, to figure out the absolute maximum amount of bytes  (or characters) that you may need for this type of data.</p>
<p>You can look at more of the <code>nanopb</code> related features at <a target="_blank" href="https://jpa.kapsi.fi/nanopb/docs/concepts.html">their documentation.</a></p>
<h2 id="heading-generating-the-appropriate-static-libraries">Generating the appropriate static libraries</h2>
<p>In order to make this as easy as possible, I put all the following code into a Makefile. When you make a change to the Protocol Buffer, that every library for every language used gets generated.</p>
<p>If we want to generate a static Go file the command looks like:</p>
<pre><code class="lang-bash">protoc -I&lt;directory with .proto&gt; --go_out=&lt;output directory&gt; command.proto
</code></pre>
<p>If you've installed the nanopb plugin, you can do something similar to generate C code:</p>
<pre><code class="lang-bash">protoc -I&lt;directory with .proto&gt; -ocommand.pb command.proto
&lt;path&gt;/&lt;to&gt;/protogen/nanopb_generator.py -I&lt;directory with .proto&gt; <span class="hljs-built_in">command</span>
</code></pre>
<p>The first file creates a generic "object" file. The second actually creates the static C library.</p>
<p>For javascript:</p>
<pre><code class="lang-bash">pbjs -t static-module -p&lt;directory with .proto&gt; command.proto &gt; command.pb.js
</code></pre>
<p>You can test each of these commands with the <code>.proto</code> and <code>.options</code> file examples above. I also built this manual process into one command in the example repository. <a target="_blank" href="https://www.jaredwolff.com/files/protobuf/">Get access here.</a></p>
<h2 id="heading-encoding-and-decoding">Encoding and Decoding</h2>
<p><img src="https://www.jaredwolff.com/how-to-define-your-own-bluetooth-low-energy-configuration-service-using-protobuf/images/data-3432628_1920.jpg" alt="Encoding" width="600" height="400" loading="lazy"></p>
<p>In the examples below, I show you how to use your freshly compiled static code! This is where the fun begins.</p>
<h3 id="heading-encoding-using-javascript">Encoding using Javascript</h3>
<p>Here’s a typical flow that you can follow when using a statically generated javascript library. First, initialize the library.</p>
<pre><code><span class="hljs-comment">// Import the config message</span>
<span class="hljs-keyword">var</span> protobuf  = <span class="hljs-built_in">require</span>(<span class="hljs-string">'./command.pb.js'</span>);
</code></pre><p>Then create an instance of <code>event</code>:</p>
<pre><code><span class="hljs-comment">// setup command</span>
<span class="hljs-keyword">var</span> event = protobuf.event.create();
event.type = protobuf.event.event_type.command;
event.message = <span class="hljs-string">"This is"</span>;
</code></pre><p>Then, compile the payload. i.e. turn human readable JSON into nicely packed binary. See below.</p>
<pre><code><span class="hljs-comment">// make sure it's valid</span>
<span class="hljs-keyword">var</span> err = protobuf.event.verify(event);
<span class="hljs-keyword">if</span>( err != <span class="hljs-literal">null</span> ) {
   <span class="hljs-built_in">console</span>.log(<span class="hljs-string">"verify failed: "</span> + err);
   <span class="hljs-keyword">return</span>;
}
</code></pre><p>You'll get errors during this step if your object is malformed or if if you are missing <code>required</code> elements. I don't recommend using the <code>required</code> prefix when defining your <code>.proto</code> file. Any checks for required elements can be easily done in your application code.</p>
<p>Finally, the last step is to encode and turn it into raw bytes:</p>
<pre><code><span class="hljs-comment">// encode into raw bytes</span>
<span class="hljs-keyword">var</span> payload = protobuf.event.encode(event).finish();
</code></pre><p>You can then use payload and send it over BLE, HTTP or whatever. If there's a communication protocol, you can send this buffer over it!</p>
<h3 id="heading-decoding-in-c">Decoding in C</h3>
<p>Once the data is received it’s decoded on the embedded end. <code>nanopb</code> is confusing. But luckily I have some code here that will work for you:</p>
<pre><code><span class="hljs-comment">// Setitng up protocol buffer data</span>
event evt;

<span class="hljs-comment">// Read in buffer</span>
pb_istream_t istream = pb_istream_from_buffer((pb_byte_t *)data, data_len);

<span class="hljs-keyword">if</span> (!pb_decode(&amp;istream, event_fields, &amp;evt)) {
   NRF_LOG_ERROR(<span class="hljs-string">"Unable to decode: %s"</span>, PB_GET_ERROR(&amp;istream));
   <span class="hljs-keyword">return</span>;
}

<span class="hljs-comment">// Validate code &amp; type</span>
<span class="hljs-keyword">if</span>( evt.type != event_event_type_command ) {
   <span class="hljs-keyword">return</span>;
}
</code></pre><p>First, you create an input stream based on the raw data and the size of the data.</p>
<p>Then, you use the <code>pb_decode</code> function. You point the first argument to the input stream. The second to the definition of our Protocol Buffer we’ve been working with. It's located in the <code>command.pb.h</code> file.</p>
<pre><code><span class="hljs-comment">/* Defines for backwards compatibility with code written before nanopb-0.4.0 */</span>
#define event_fields &amp;event_msg
</code></pre><p>The last argument is a pointer to the struct to put the decoded data into. (In this case it's <code>evt</code> defined right before <code>pb_istream_from_buffer</code> above).</p>
<h3 id="heading-encoding-in-c">Encoding in C</h3>
<p>Let's now say we're going to reply to the message that was just decoded above. So now we have to create data, encode it and send it back. Here's the process:</p>
<pre><code><span class="hljs-comment">// Encode value</span>
pb_byte_t output[event_size];

<span class="hljs-comment">// Output buffer</span>
pb_ostream_t ostream = pb_ostream_from_buffer(output,sizeof(output));

<span class="hljs-keyword">if</span> (!pb_encode(&amp;ostream, event_fields, &amp;evt)) {
   NRF_LOG_ERROR(<span class="hljs-string">"Unable to encode: %s"</span>, PB_GET_ERROR(&amp;ostream));
   <span class="hljs-keyword">return</span>;
}
</code></pre><p>First create a buffer that holds the maximum amount of bytes that your Protocol buffer takes up. This is also defined in your <code>command.pb.h</code>. In this case <code>event_size</code> is set to <code>67</code>. Then, similarly to the decode command, you create a stream and connect it to your buffer. Then finally encode the data by pointing your <code>evt</code> struct along with the stream and <code>event_fields</code>.</p>
<p>As long as <code>pb_encode</code> returns without error, the encoded data has been written to <code>output</code>! The structure can be variable length so the best way to handle when sending it is to get the <code>bytes_written</code> from <code>ostream</code>:</p>
<pre><code>NRF_LOG_INFO(<span class="hljs-string">"bytes written %d"</span>,ostream.bytes_written);
</code></pre><h2 id="heading-conclusion">Conclusion</h2>
<p>Nice you made it! I hope you're starting to grasp the power of Protocol Buffers. Don't worry, it took me a little while to figure it all out. <em>You too can be a Protocol Buffer master!</em> ?</p>
<p>If you're not too thrilled with Protocol Buffers, there are other alternatives. I've used <a target="_blank" href="https://msgpack.org">MessagePack</a> with some success on previous products. It's straightforward and has tons of support for a majority of programming languages.</p>
<p>If you are interested how to roll this into a Bluetooth Low Energy project, stay tuned for Part Two. In Part two, I’ll show you how to set up a very simple Bluetooth Service and Characteristic that will be used to transfer our freshly encoded data to-and-fro.</p>
<p>Also, if you want to see all the code in action, <a target="_blank" href="https://www.jaredwolff.com/files/protobuf/">you can download everything here.</a></p>
 ]]>
                </content:encoded>
            </item>
        
    </channel>
</rss>
