Logo

dev-resources.site

for different kinds of informations.

gRPC between Web and Server.

Published at
8/30/2024
Categories
grpc
web
go
browser
Author
ehsaniara
Categories
4 categories in total
grpc
open
web
open
go
open
browser
open
Author
9 person written this
ehsaniara
open
gRPC between Web and Server.

This project demonstrates how to set up a simple gRPC communication between a web client and server with an Envoy proxy.

I’m using the gRPC-Web library for this purpose. gRPC-Web is a JavaScript client library that allows web applications to interact with gRPC services. Since browsers don't support HTTP/2 or the binary protocol used by standard gRPC, gRPC-Web provides a way to bridge the gap by using HTTP/1.1 or HTTP/2 and encoding gRPC messages in a way that browsers can handle. Here's how gRPC-Web works:

  1. The client sends requests to the server using gRPC-Web, which typically communicates via HTTP/1.1 or HTTP/2. Metadata (like headers) can be attached to the request, such as for authentication (e.g., JWT tokens).

The request is encoded in a gRPC-Web format, typically using base64 encoding for the binary gRPC payload. The client sends this request over HTTP/1.1 or HTTP/2.

  1. Envoy (or another reverse proxy like Nginx) acts as an intermediary between the gRPC-Web client and the gRPC server. Envoy receives the gRPC-Web request, decodes the gRPC-Web payload, and forwards it as a standard gRPC request to the gRPC server using HTTP/2.

The gRPC server processes the request as if it were a native gRPC request, using HTTP/2 for communication.

  1. The gRPC server processes the incoming gRPC request, performs the necessary business logic, and generates a response (in this example it’s the Go written application). The response is encoded in the standard gRPC format and sent back to Envoy.

  2. Envoy receives the gRPC response, encodes it in the gRPC-Web format (typically using base64), and sends it back to the gRPC-Web client over HTTP/1.1 or HTTP/2. Any metadata included in the gRPC response, such as status codes, is translated appropriately.

  3. The gRPC-Web client decodes the response and converts it into a usable format within the web application. The web application processes the response, updating the UI or handling errors as needed.

Image description

NOTE: client-side and bi-directional streaming is not currently supported (see streaming roadmap)

Advantages of gRPC-Web

  • Browser Compatibility: Allows modern web applications to interact with gRPC services without needing native support for HTTP/2 and binary protocols.
  • Efficiency: Leverages the performance and efficiency of gRPC while adapting it for the web.

Here is a GitHub project for it:

https://github.com/ehsaniara/gRPC-web-example

proto file

syntax = "proto3";

package helloworld;

option go_package = "./proto"; // Add this line

service Greeter {
  rpc SayHello (HelloRequest) returns (HelloReply);
}

message HelloRequest {
  string name = 1;
}

message HelloReply {
  string message = 1;
}
Enter fullscreen mode Exit fullscreen mode

server side (go)

package main

import (
   "context"
   "google.golang.org/grpc/reflection"
   "log"
   "net"

   pb "github.com/ehsaniara/gRPC-web-example/proto"
   "google.golang.org/grpc"
)

type server struct {
 pb.UnimplementedGreeterServer
}

func (s *server) SayHello(ctx context.Context, in *pb.HelloRequest) (*pb.HelloReply, error) {
 return &pb.HelloReply{Message: "Hello " + in.Name}, nil
}

func main() {
 lis, err := net.Listen("tcp", ":50051")
 if err != nil {
  log.Fatalf("failed to listen: %v", err)
 }
 s := grpc.NewServer()
 pb.RegisterGreeterServer(s, &server{})

 // Register reflection service on gRPC server.
 reflection.Register(s)
 if err := s.Serve(lis); err != nil {
  log.Fatalf("failed to serve: %v", err)
 }

 log.Println("Server is running on port 50051")
 if err := s.Serve(lis); err != nil {
  log.Fatalf("failed to serve: %v", err)
 }
}
Enter fullscreen mode Exit fullscreen mode

Envoy config

...
http_filters:
  - name: envoy.filters.http.grpc_web
    typed_config:
      "@type": type.googleapis.com/envoy.extensions.filters.http.grpc_web.v3.GrpcWeb
  - name: envoy.filters.http.cors
    typed_config:
      "@type": type.googleapis.com/envoy.extensions.filters.http.cors.v3.Cors
  - name: envoy.filters.http.router
    typed_config:
      "@type": type.googleapis.com/envoy.extensions.filters.http.router.v3.Router
...
Enter fullscreen mode Exit fullscreen mode

JS Web Client (webpack)

// Import the generated gRPC-Web client stubs and message classes
import {GreeterClient} from './generated/helloworld_grpc_web_pb';
import {HelloRequest} from './generated/helloworld_pb';

// Create an instance of the Greeter client
const client = new GreeterClient('http://localhost:8080');

// Function to send a greeting request
function sayHello(name) {
    // Create a new request
    const request = new HelloRequest();
    request.setName(name);

    // Call the sayHello method on the Greeter client
    client.sayHello(request, {}, (err, response) => {
        if (err) {
            console.error('Error:', err.message);
            document.getElementById('output').textContent = 'Error: ' + err.message;
        } else {
            console.log('Greeting:', response.getMessage());
            document.getElementById('output').textContent = 'Greeting: ' + response.getMessage();
        }
    });
}

// Example usage: sending a request when the page loads
document.addEventListener('DOMContentLoaded', () => {
    const name = 'World';
    sayHello(name);
});
Enter fullscreen mode Exit fullscreen mode

Here is a GitHub project related to this project

https://github.com/ehsaniara/gRPC-web-example

grpc Article's
30 articles in total
Favicon
How to Handle Excessive Warning Messages When Running `pecl install grpc`
Favicon
Protocol Buffers as a Serialization Format
Favicon
gRPC, Haskell, Nix, love, hate
Favicon
πŸš€Build, Implement, and Test gRPC Services with .NET9
Favicon
Using OpenTelemetry with gRPC in Node.js and Express Hybrid Applications
Favicon
Exploring gRPC: The High-Performance Communication in Distributed Systems
Favicon
Wednesday Links - Edition 2024-11-06
Favicon
Part 3: Compiling the Protos and Setting up the gRPC server
Favicon
Mocking gRPC Clients in C#: Fake It Till You Make It
Favicon
How gRPC Works
Favicon
Part 2: Defining the Authentication gRPC Interface
Favicon
How Does gRPC Actually Work?
Favicon
gRPC Streaming: Best Practices and Performance Insights
Favicon
Why is gRPC so much faster than a JSON-based REST API?
Favicon
Strongly typed web APIs with gRPC
Favicon
Use RBAC to protect your gRPC service right on proto definition
Favicon
gRPC and Go: Building High-Performance Web Services
Favicon
Connecting NestJS and ASP.NET Core with gRPC: A Step-by-Step Guide
Favicon
gRPC: what is it? An introduction...
Favicon
gRPC: onde vive? o que come?
Favicon
Understanding the Importance of gRPC and Its Applications in Modern Software Development
Favicon
Mastering Go gRPC Services with Docker: A One-Stop Guide
Favicon
Hybrid NestJs Microservice Responding to Both HTTP and gRPC Requests
Favicon
Part 1: How to build Auth API in Rust using gRPC
Favicon
gRPC between Web and Server.
Favicon
FauxRPC
Favicon
Why should we use Protobuf in Web API as data transfer protocol.
Favicon
Browser Client to gRPC Server Routing options: Connect, gRPC-web, gRPC-gateway and more!
Favicon
gRPC vs REST: A Comprehensive Comparison
Favicon
gRPC - Unimplemented Error 12

Featured ones: