mirror of https://github.com/grpc/grpc.io.git
Merge pull request #119 from lucperkins/lperkins/css-framework
Use CSS framework for site
This commit is contained in:
commit
21072b6f4d
|
|
@ -9,7 +9,3 @@ indent_style = tab
|
|||
[*.{html,js,json,md,sass,yaml}]
|
||||
indent_style = space
|
||||
indent_size = 2
|
||||
|
||||
[*.py]
|
||||
indent_style = space
|
||||
indent_size = 4
|
||||
|
|
|
|||
2
Makefile
2
Makefile
|
|
@ -1,5 +1,5 @@
|
|||
HUGO_VERSION = 0.66.0
|
||||
DOCKER_IMG := klakegg/hugo:$(HUGO_VERSION)
|
||||
DOCKER_IMG := klakegg/hugo:$(HUGO_VERSION)-ext
|
||||
SERVE_CMD = server --buildDrafts --buildFuture --disableFastRender --ignoreCache
|
||||
|
||||
clean:
|
||||
|
|
|
|||
|
|
@ -1,6 +1,5 @@
|
|||
---
|
||||
title: "{{ replace .Name "-" " " | title }}"
|
||||
date: {{ .Date }}
|
||||
date: {{ dateFormat "2006-01-02" .Date }}
|
||||
draft: true
|
||||
---
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,278 @@
|
|||
@charset "utf-8"
|
||||
{{ $fontAwesomeVersion := site.Params.font_awesome_version }}
|
||||
{{ $fonts := site.Params.fonts }}
|
||||
{{ if $fonts }}
|
||||
{{ $fontSlice := (slice) }}
|
||||
{{ range $fonts }}
|
||||
{{ $fontSlice = $fontSlice | append (printf "%s:%s" (replace .name " " "+") (delimit .sizes ",")) }}
|
||||
{{ end }}
|
||||
{{ $fontsUrl := printf "https://fonts.googleapis.com/css?family=%s" (delimit $fontSlice "|") }}
|
||||
@import url("{{ $fontsUrl }}")
|
||||
{{ end }}
|
||||
|
||||
{{ with $fontAwesomeVersion }}
|
||||
{{ $fontAwesomeUrl := printf "https://use.fontawesome.com/releases/v%s/css/all.css" . }}
|
||||
@import url("{{ $fontAwesomeUrl }}")
|
||||
{{ end }}
|
||||
|
||||
// Site-specific variables here
|
||||
$grpc-green: #244c5a
|
||||
$grpc-blue: #5ac5c5
|
||||
$twitter-blue: rgb(29, 161, 242)
|
||||
$reddit-orange: rgba(255, 86, 0, 1)
|
||||
$gitter-magenta: rgb(237, 25, 101)
|
||||
|
||||
// Initial Bulma imports
|
||||
@import "bulma/sass/utilities/initial-variables"
|
||||
@import "bulma/sass/utilities/functions"
|
||||
|
||||
// Bulma-specific overrides
|
||||
$primary: $grpc-green
|
||||
$secondary: $grpc-blue
|
||||
$secondary-dark: darken($secondary, 15%)
|
||||
$link: $secondary-dark
|
||||
$code: $primary
|
||||
$code-background: $white-bis
|
||||
$section-padding: 3rem 1.5rem
|
||||
|
||||
// Font overrides
|
||||
{{ if $fonts }}
|
||||
// Sans-serif font
|
||||
{{ with (index (where $fonts ".type" "sans_serif") 0).name }}
|
||||
$family-sans-serif: "{{ . }}", BlinkMacSystemFont, -apple-system, "Segoe UI", "Roboto", "Oxygen", "Ubuntu", "Cantarell", "Fira Sans", "Droid Sans", "Helvetica Neue", "Helvetica", "Arial", sans-serif
|
||||
{{ end }}
|
||||
|
||||
// Monospace font
|
||||
{{ with (index (where $fonts ".type" "monospace") 0).name }}
|
||||
$family-monospace: "{{ . }}", monospace
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
|
||||
$font-heading: {{ $.Site.Params.heading_font | default "'Fira Sans', sans-serif" }}
|
||||
|
||||
// Final Bulma imports
|
||||
@import "bulma/sass/utilities/derived-variables"
|
||||
|
||||
// Bulma variable overrdides that require derived variables like $dark
|
||||
$colors: mergeColorMaps(("secondary": ($secondary, $white), "twitter-blue": ($twitter-blue, $white), "reddit-orange": ($reddit-orange, $white), "gitter-magenta": ($gitter-magenta, $white)), $colors)
|
||||
|
||||
// Bulma core
|
||||
@import "bulma/sass/utilities/_all"
|
||||
@import "bulma/sass/base/_all"
|
||||
@import "bulma/sass/elements/container"
|
||||
@import "bulma/sass/grid/columns"
|
||||
@import "bulma/sass/grid/tiles"
|
||||
@import "bulma/sass/layout/hero"
|
||||
@import "bulma/sass/layout/section"
|
||||
@import "bulma/sass/layout/footer"
|
||||
|
||||
// Elements
|
||||
|
||||
// @import "bulma/sass/elements/box"
|
||||
@import "bulma/sass/elements/button"
|
||||
@import "bulma/sass/elements/content"
|
||||
@import "bulma/sass/elements/icon"
|
||||
// @import "bulma/sass/elements/image"
|
||||
// @import "bulma/sass/elements/notification"
|
||||
// @import "bulma/sass/elements/progress"
|
||||
// @import "bulma/sass/elements/table"
|
||||
// @import "bulma/sass/elements/tag"
|
||||
@import "bulma/sass/elements/title"
|
||||
// @import "bulma/sass/elements/other"
|
||||
|
||||
// Forms
|
||||
// @import "bulma/sass/form/shared"
|
||||
// @import "bulma/sass/form/input-textarea"
|
||||
// @import "bulma/sass/form/checkbox-radio"
|
||||
// @import "bulma/sass/form/select"
|
||||
// @import "bulma/sass/form/file"
|
||||
// @import "bulma/sass/form/tools"
|
||||
|
||||
// Components
|
||||
// @import "bulma/sass/components/breadcrumb"
|
||||
@import "bulma/sass/components/card"
|
||||
// @import "bulma/sass/components/dropdown"
|
||||
@import "bulma/sass/components/level"
|
||||
// @import "bulma/sass/components/list"
|
||||
// @import "bulma/sass/components/media"
|
||||
@import "bulma/sass/components/menu"
|
||||
// @import "bulma/sass/components/message"
|
||||
@import "bulma/sass/components/modal"
|
||||
@import "bulma/sass/components/navbar"
|
||||
// @import "bulma/sass/components/pagination"
|
||||
// @import "bulma/sass/components/panel"
|
||||
@import "bulma/sass/components/tabs"
|
||||
|
||||
.has-background-image
|
||||
background-image: url("/img/graphic-04.svg")
|
||||
background-repeat: no-repeat
|
||||
background-size: cover
|
||||
|
||||
=logo($d, $t)
|
||||
+desktop
|
||||
width: $d
|
||||
+touch
|
||||
width: $t
|
||||
|
||||
.is-cncf-logo
|
||||
+logo(50%, 90%)
|
||||
|
||||
+desktop
|
||||
margin-top: 1.25rem
|
||||
+touch
|
||||
margin-top: 0.75rem
|
||||
|
||||
.is-hero-logo
|
||||
+logo(50%, 80%)
|
||||
|
||||
+desktop
|
||||
margin-bottom: 2rem
|
||||
+touch
|
||||
margin-bottom: 1rem
|
||||
|
||||
.is-footer-logo
|
||||
+logo(50%, 40%)
|
||||
|
||||
.is-feature-icon
|
||||
+tablet
|
||||
width: 80%
|
||||
+mobile
|
||||
width: 30%
|
||||
|
||||
+touch
|
||||
margin: 0 auto
|
||||
|
||||
.is-testimonial-logo
|
||||
max-height: 5rem
|
||||
margin-bottom: 1.5rem
|
||||
|
||||
.is-page
|
||||
display: flex
|
||||
flex-direction: column
|
||||
min-height: 100vh
|
||||
|
||||
.is-main
|
||||
flex: 1
|
||||
|
||||
|
||||
.is-feature-pane
|
||||
margin-bottom: 2rem
|
||||
|
||||
.has-bottom-padding
|
||||
padding-bottom: 8rem
|
||||
|
||||
.user-logo
|
||||
margin-bottom: 1.5rem
|
||||
|
||||
img
|
||||
+desktop
|
||||
max-height: 7rem
|
||||
+touch
|
||||
max-height: 5rem
|
||||
|
||||
.content
|
||||
.button
|
||||
margin: 1rem 0
|
||||
|
||||
@for $i from 1 through 6
|
||||
h#{$i}
|
||||
&::before
|
||||
margin-top: 5rem
|
||||
|
||||
img
|
||||
&:hover
|
||||
cursor: pointer
|
||||
|
||||
.highlight
|
||||
margin-bottom: 1rem
|
||||
|
||||
p a
|
||||
font-weight: $weight-medium
|
||||
|
||||
&:hover
|
||||
color: $secondary
|
||||
|
||||
.section
|
||||
&.has-extra-padding
|
||||
padding: 6rem 2rem
|
||||
|
||||
=sticky
|
||||
position: sticky
|
||||
position: -webkit-sticky
|
||||
|
||||
.is-sticky
|
||||
+sticky
|
||||
top: $navbar-height + 3rem
|
||||
|
||||
.is-constrained
|
||||
max-width: 90ch
|
||||
|
||||
=active
|
||||
color: $secondary-dark
|
||||
font-weight: 700
|
||||
|
||||
.nav
|
||||
&-section
|
||||
&-title
|
||||
color: $dark
|
||||
|
||||
&.is-active
|
||||
+active
|
||||
|
||||
&-toc
|
||||
padding: 0.5rem 0 0.75rem 2.5rem
|
||||
|
||||
li a
|
||||
color: $grey
|
||||
|
||||
li + li
|
||||
margin-top: 0.5rem
|
||||
|
||||
ul.nav-section-links
|
||||
margin: 0 0 2rem 1.25rem
|
||||
|
||||
li.nav-section-link
|
||||
font-size: 1.1rem
|
||||
|
||||
&.is-active
|
||||
+active
|
||||
|
||||
& + li.nav-section-link
|
||||
margin-top: 0.5rem
|
||||
|
||||
& + &
|
||||
margin-top: 1.5rem
|
||||
|
||||
.blog-list
|
||||
ul
|
||||
margin-bottom: 2rem
|
||||
|
||||
li + li
|
||||
margin-top: .5rem
|
||||
|
||||
=admon($color)
|
||||
.icon
|
||||
color: $color
|
||||
|
||||
.admonition
|
||||
margin-bottom: 2rem
|
||||
padding: 1.5rem 2rem
|
||||
border-radius: .5rem
|
||||
border: 1.5px solid $secondary
|
||||
|
||||
&.is-warning
|
||||
+admon($warning)
|
||||
&.is-success
|
||||
+admon($success)
|
||||
&.is-note
|
||||
+admon($info)
|
||||
&.is-requirement
|
||||
+admon($grey)
|
||||
|
||||
.toc
|
||||
li
|
||||
font-size: 1.1rem
|
||||
line-height: 1.3
|
||||
|
||||
& + li
|
||||
margin-top: 0.75rem
|
||||
160
config.toml
160
config.toml
|
|
@ -2,13 +2,57 @@ baseURL = "https://grpc.io/"
|
|||
languageCode = "en-us"
|
||||
title = "gRPC"
|
||||
pygmentsCodeFences = true
|
||||
disableKinds = ["taxonomy", "taxonomyTerm"]
|
||||
|
||||
[markup.goldmark.renderer]
|
||||
unsafe = true
|
||||
|
||||
[markup.highlight]
|
||||
style = "manni"
|
||||
|
||||
[params]
|
||||
grpc_release_tag = "v1.27.2"
|
||||
grpc_release_tag_no_v = "1.27.2"
|
||||
grpc_java_release_tag = "v1.27.2"
|
||||
google_analytics_id = "UA-60127042-1"
|
||||
font_awesome_version = "5.12.1"
|
||||
|
||||
milestones_link = "https://github.com/grpc/grpc/milestones"
|
||||
description = "A high-performance, open source universal RPC framework"
|
||||
why = """
|
||||
gRPC is a modern open source high performance RPC framework that can run in any environment. It can efficiently connect services in and across data centers with pluggable support for load balancing, tracing, health checking and authentication. It is also applicable in last mile of distributed computing to connect devices, mobile applications and browsers to backend services.
|
||||
"""
|
||||
|
||||
[params.social]
|
||||
twitter = "https://twitter.com/grpcio"
|
||||
gitter = "https://gitter.im/grpc/grpc"
|
||||
reddit = "https://www.reddit.com/r/grpc"
|
||||
|
||||
[[params.features]]
|
||||
title = "Simple service definition"
|
||||
description = "Define your service using Protocol Buffers, a powerful binary serialization toolset and language"
|
||||
icon = "feature-1.svg"
|
||||
|
||||
[[params.features]]
|
||||
title = "Start quickly and scale"
|
||||
description = "Install runtime and dev environments with a single line and also scale to millions of RPCs per second with the framework"
|
||||
icon = "feature-2.svg"
|
||||
|
||||
[[params.features]]
|
||||
title = "Works across languages and platforms"
|
||||
description = "Automatically generate idiomatic client and server stubs for your service in a variety of languages and platforms"
|
||||
icon = "feature-3.svg"
|
||||
|
||||
[[params.features]]
|
||||
title = "Bi-directional streaming and integrated auth"
|
||||
description = "Bi-directional streaming and fully integrated pluggable authentication with HTTP/2-based transport"
|
||||
icon = "feature-4.svg"
|
||||
|
||||
|
||||
[params.logos]
|
||||
navbar = "grpc-horizontal-white.png"
|
||||
hero = "grpc-logo.png"
|
||||
footer = "grpc-horizontal-white.png"
|
||||
|
||||
# Configuration required for auto-generating the Netlify _redirects file
|
||||
[mediaTypes."text/netlify"]
|
||||
|
|
@ -27,72 +71,138 @@ baseName = "release"
|
|||
[outputs]
|
||||
home = ["HTML", "REDIRECTS", "RSS", "RELEASE"]
|
||||
|
||||
[[params.fonts]]
|
||||
name = "Open Sans"
|
||||
sizes = [300, 400, 600, 700]
|
||||
type = "sans_serif"
|
||||
|
||||
# Site menus
|
||||
[menu]
|
||||
[[menu.dropdown]]
|
||||
[[menu.main]]
|
||||
name = "About"
|
||||
url = "/about"
|
||||
weight = 1
|
||||
|
||||
[[menu.main]]
|
||||
name = "Docs"
|
||||
url = "/docs"
|
||||
identifier = "docs"
|
||||
weight = 2
|
||||
|
||||
[[menu.main]]
|
||||
name = "Guides"
|
||||
url = "/docs/guides"
|
||||
identifier = "guides"
|
||||
weight = 3
|
||||
|
||||
[[menu.main]]
|
||||
name = "Blog"
|
||||
url = "/blog"
|
||||
weight = 4
|
||||
|
||||
[[menu.main]]
|
||||
name = "Community"
|
||||
url = "/community"
|
||||
weight = 5
|
||||
|
||||
[[menu.main]]
|
||||
name = "Packages"
|
||||
url = "https://packages.grpc.io"
|
||||
weight = 6
|
||||
|
||||
[[menu.main]]
|
||||
name = "Overview"
|
||||
url = "/docs"
|
||||
weight = 1
|
||||
parent = "docs"
|
||||
|
||||
[[menu.dropdown]]
|
||||
[[menu.main]]
|
||||
name = "Quick Start"
|
||||
url = "/docs/quickstart/"
|
||||
weight = 2
|
||||
parent = "docs"
|
||||
|
||||
[[menu.dropdown]]
|
||||
name = "Guides"
|
||||
url = "/docs/guides/"
|
||||
weight = 3
|
||||
|
||||
[[menu.dropdown]]
|
||||
[[menu.main]]
|
||||
name = "Tutorials"
|
||||
url = "/docs/tutorials/"
|
||||
weight = 4
|
||||
weight = 3
|
||||
parent = "docs"
|
||||
|
||||
[[menu.dropdown]]
|
||||
[[menu.main]]
|
||||
name = "Reference"
|
||||
url = "/docs/reference/"
|
||||
weight = 5
|
||||
weight = 4
|
||||
parent = "docs"
|
||||
|
||||
[[menu.dropdown]]
|
||||
[[menu.main]]
|
||||
name = "Samples"
|
||||
url = "/docs/samples/"
|
||||
weight = 6
|
||||
weight = 5
|
||||
parent = "docs"
|
||||
|
||||
[[menu.dropdown]]
|
||||
[[menu.main]]
|
||||
name = "Presentations"
|
||||
url = "/docs/talks"
|
||||
weight = 7
|
||||
url = "/docs/talks/"
|
||||
weight = 6
|
||||
parent = "docs"
|
||||
|
||||
[[menu.guides]]
|
||||
[[menu.main]]
|
||||
name = "FAQ"
|
||||
url = "/faq"
|
||||
weight = 7
|
||||
parent = "docs"
|
||||
|
||||
[[menu.main]]
|
||||
name = "What is gRPC?"
|
||||
url = "/docs/guides/"
|
||||
weight = 1
|
||||
parent = "guides"
|
||||
|
||||
[[menu.guides]]
|
||||
[[menu.main]]
|
||||
name = "gRPC Concepts"
|
||||
url = "/docs/guides/concepts/"
|
||||
weight = 2
|
||||
parent = "guides"
|
||||
|
||||
[[menu.guides]]
|
||||
[[menu.main]]
|
||||
name = "Authentication"
|
||||
url = "/docs/guides/auth/"
|
||||
weight = 3
|
||||
parent = "guides"
|
||||
|
||||
[[menu.guides]]
|
||||
[[menu.main]]
|
||||
name = "Error handling and debugging"
|
||||
url = "/docs/guides/error/"
|
||||
weight = 4
|
||||
parent = "guides"
|
||||
|
||||
[[menu.guides]]
|
||||
[[menu.main]]
|
||||
name = "Benchmarking"
|
||||
url = "/docs/guides/benchmarking/"
|
||||
weight = 5
|
||||
parent = "guides"
|
||||
|
||||
[[menu.guides]]
|
||||
[[menu.main]]
|
||||
name = "gRPC Wire Format"
|
||||
url = "https://github.com/grpc/grpc/blob/master/doc/PROTOCOL-HTTP2.md"
|
||||
weight = 6
|
||||
parent = "guides"
|
||||
|
||||
[markup.goldmark.renderer]
|
||||
unsafe = true
|
||||
[[menu.buttons]]
|
||||
name = "Quick Start"
|
||||
url = "/docs/quickstart"
|
||||
weight = 1
|
||||
|
||||
[[menu.buttons]]
|
||||
name = "Docs"
|
||||
url = "/docs"
|
||||
weight = 2
|
||||
|
||||
[[menu.buttons]]
|
||||
name = "Concepts"
|
||||
url = "/docs/guides/concepts"
|
||||
weight = 3
|
||||
|
||||
[[menu.buttons]]
|
||||
name = "Community"
|
||||
url = "/community"
|
||||
weight = 4
|
||||
|
|
@ -1,102 +0,0 @@
|
|||
---
|
||||
|
||||
---
|
||||
|
||||
|
||||
<div class="section2">
|
||||
|
||||
<a name="arrow"><h1>Why gRPC?</h1></a>
|
||||
gRPC is a modern open source high performance RPC framework that can run in any environment. It can efficiently connect services in and across data centers with pluggable support for load balancing, tracing, health checking and authentication. It is also applicable in last mile of distributed computing to connect devices, mobile applications and browsers to backend services.
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
<div class="cols" >
|
||||
|
||||
<div class="col1">
|
||||
|
||||
<div class="colpart1">
|
||||
<img class="col1image" src="img/grpc-newicon-1.svg" style="padding:2%;display:block">
|
||||
|
||||
<div class="coltext1">
|
||||
<h6>Simple service definition</h6>
|
||||
Define your service using Protocol Buffers, a powerful binary serialization toolset and language
|
||||
</div>
|
||||
</div>
|
||||
<div class="colpart2">
|
||||
<img class="col1image" src="img/grpc-newicon-2.svg" style="padding:2%;display:block">
|
||||
<div class="coltext1">
|
||||
<h6>Start quickly and scale</h6>Install runtime and dev environments with a single line and also scale to millions of RPCs per second with the framework
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col2">
|
||||
|
||||
<div class="colpart1">
|
||||
|
||||
<img class="col1image" src="img/grpc-newicon-3.svg" style="padding:2%;display:block">
|
||||
<div class="coltext1">
|
||||
<h6>Works across languages and platforms</h6>Automatically generate idiomatic client and server stubs for your service in a variety of languages and platforms</div>
|
||||
</div>
|
||||
|
||||
<div class="colpart2">
|
||||
<img class="col1image" src="img/grpc-newicon-4.svg" style="padding:2%;display:block">
|
||||
<div class="coltext1">
|
||||
<h6>Bi-directional streaming and integrated auth</h6>Bi-directional streaming and fully integrated pluggable authentication with http/2 based transport
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div></div>
|
||||
|
||||
|
||||
<div class="section3">
|
||||
<h1>Used By</h1>
|
||||
<div class="companybox">
|
||||
<img src="img/square.png">
|
||||
</div>
|
||||
<div class="companybox">
|
||||
<img src="img/netflix.png">
|
||||
</div>
|
||||
<div class="companybox">
|
||||
<img src="img/coreos.png">
|
||||
</div>
|
||||
<div class="companybox">
|
||||
<img src="img/cockroach-labs.png">
|
||||
</div>
|
||||
<div class="companybox">
|
||||
<img src="img/wisconsin.png">
|
||||
</div>
|
||||
<div class="companybox">
|
||||
<img src="img/carbon.png">
|
||||
</div>
|
||||
<div class="companybox">
|
||||
<img src="img/cisco.png">
|
||||
</div>
|
||||
<div class="companybox">
|
||||
<img src="img/juniper.png">
|
||||
</div>
|
||||
<div class="companybox" style="margin-right:0% !important">
|
||||
<img src="img/pingcap7.png">
|
||||
</div>
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
<div class="section3 cncf-section">
|
||||
<p>
|
||||
We are a <a href="https://cncf.io" target="_blank">Cloud Native Computing Foundation</a> incubating project.
|
||||
</p>
|
||||
|
||||
<br />
|
||||
|
||||
<img src="/img/cncf-color.png">
|
||||
</div>
|
||||
|
||||
|
||||
<div class="section4">
|
||||
<h1 style="color:white">Want to Learn More?</h1>
|
||||
Get started by learning concepts and doing our hello world quickstart in language of your choice. <br>
|
||||
<div class="button" style="margin-top:3%">
|
||||
<a href="docs/guides/concepts/"><button>GET STARTED</button></a>
|
||||
</div>
|
||||
</div>
|
||||
126
content/about.md
126
content/about.md
|
|
@ -1,5 +1,6 @@
|
|||
---
|
||||
title: About gRPC
|
||||
description: Who is using it, why they're using it, and which platforms support it
|
||||
---
|
||||
|
||||
gRPC is a modern open source high performance RPC framework that can run in any
|
||||
|
|
@ -8,21 +9,19 @@ pluggable support for load balancing, tracing, health checking and
|
|||
authentication. It is also applicable in last mile of distributed computing to
|
||||
connect devices, mobile applications and browsers to backend services.
|
||||
|
||||
**The main usage scenarios:**
|
||||
### The main usage scenarios
|
||||
|
||||
* Efficiently connecting polyglot services in microservices style architecture
|
||||
* Connecting mobile devices, browser clients to backend services
|
||||
* Generating efficient client libraries
|
||||
|
||||
**Core Features that make it awesome:**
|
||||
### Core features that make it awesome
|
||||
|
||||
* Idiomatic client libraries in 10 languages
|
||||
* Highly efficient on wire and with a simple service definition framework
|
||||
* Bi-directional streaming with http/2 based transport
|
||||
* Pluggable auth, tracing, load balancing and health checking
|
||||
|
||||
<hr>
|
||||
|
||||
## Who’s using gRPC and why?
|
||||
|
||||
Many companies are already using gRPC for connecting multiple services in their
|
||||
|
|
@ -32,122 +31,11 @@ Below are details and quotes from some of our early adopters.
|
|||
|
||||
Check out what people are saying below.
|
||||
|
||||
<div class="testimonialrow">
|
||||
<div class="testimonialsection">
|
||||
<div class="testimonialimage">
|
||||
<a href="https://www.youtube.com/watch?v=-2sWDr3Z0Wo"><img src="../img/square-icon.png" style="width:45%"/></a>
|
||||
</div>
|
||||
<div>
|
||||
<span class="testimonialquote">“ </span>
|
||||
At Square, we have been collaborating with Google so that we can replace all uses of our custom RPC solution to use gRPC. We decided to move to gRPC because of its open support for multiple platforms, the demonstrated performance of the protocol, and the ability to customize and adapt it to our network. Developers at Square are looking forward to being able to take advantage of writing streaming APIs and in the future, push gRPC to the edges of the network for integration with mobile clients and third party APIs.
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="testimonialsection">
|
||||
<div class="testimonialimage">
|
||||
<a href="https://github.com/Netflix/ribbon"><img src="../img/netflix-logo.png" /></a>
|
||||
</div>
|
||||
<div>
|
||||
<span class="testimonialquote"> “ </span>
|
||||
In our initial use of gRPC we've been able to extend it easily to live within our opinionated ecosystem. Further, we've had great success making improvements directly to gRPC through pull requests and interactions with Google's team that manages the project. We expect to see many improvements to developer productivity, and the ability to allow development in non-JVM languages as a result of adopting gRPC.
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="testimonialsection">
|
||||
<div class="testimonialimage">
|
||||
<a href="https://blog.gopheracademy.com/advent-2015/etcd-distributed-key-value-store-with-grpc-http2/">
|
||||
<img src="../img/coreos-1.png" style="width:30%"/>
|
||||
</a>
|
||||
</div>
|
||||
<div>
|
||||
<span class="testimonialquote">“ </span>
|
||||
At CoreOS we are excited by the gRPC v1.0 release and the opportunities it opens up for people consuming and building what we like to call Google Infrastructure for Everyone Else. Today gRPC is in use in a number of our critical open source projects such as the etcd consensus database and the rkt container engine.
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="testimonialrow">
|
||||
<div class="testimonialsection">
|
||||
<div class="testimonialimage">
|
||||
<a href="https://github.com/cockroachdb/cockroach"><img src="../img/cockroach-1.png"/></a>
|
||||
</div>
|
||||
<div>
|
||||
<span class="testimonialquote">“ </span>
|
||||
Our switch from a home-grown RPC system to gRPC was seamless. We quickly took advantage of the per-stream flow control to provide better scheduling of large RPCs over the same connection as small ones.
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="testimonialsection">
|
||||
<div class="testimonialimage">
|
||||
<a href="https://github.com/CiscoDevNet/grpc-getting-started"><img src="../img/cisco.svg"/></a>
|
||||
</div>
|
||||
<div>
|
||||
<span class="testimonialquote">“ </span>
|
||||
With support for high performance bi-directional streaming, TLS based security, and a wide variety of programming languages, gRPC is an ideal unified transport protocol for model driven configuration and telemetry.
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="testimonialsection">
|
||||
<div class="testimonialimage">
|
||||
<a href="http://www.carbon3d.com"><img src="../img/carbon3d.svg"/></a>
|
||||
</div>
|
||||
<div>
|
||||
<span class="testimonialquote">“ </span>
|
||||
Carbon3D uses gRPC to implement distributed processes both within and outside our 3D printers. We actually switched from using Thrift early on for a number of reasons including but not limited to robust support for multiple languages like C++, Nodejs and Python. Features like bi-directional streaming are a huge win in keeping our systems implementations simpler and correct. Lastly the gRPC team/community is very active and responsive which is also a key factor for us in selecting an open source technology for mission critical projects.
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="testimonialrow">
|
||||
<div class="testimonialsection">
|
||||
<div class="testimonialimage"><a href="https://www.wisc.edu/"><img src="../img/wisc-mad.jpg"/></a></div>
|
||||
<div>
|
||||
<span class="testimonialquote">“ </span>
|
||||
We've been using gRPC for both classes and research at University of Wisconsin. Students in our distributed systems class (CS 739) utilized many of its powerful features when building their own distributed systems. In addition, gRPC is a key component of our OpenLambda research project (https://www.open-lambda.org/) which aims to provide an open-source, low-latency, serverless computational framework.
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="testimonialsection">
|
||||
<div class="testimonialimage"><a href="https://github.com/Juniper/open-nti"><img src="../img/juniperlogo.png"/></a></div>
|
||||
<div>
|
||||
<span class="testimonialquote">“ </span>
|
||||
<p>The fact that gRPC is built on HTTP/2 transport brings us native bi-directional streaming capabilities and flexible custom-metadata in request headers. The first point is important for large payloadexchange and network telemetry scenarios while the latter enables us to expand and include capabilities including but not limited to various network element authentication mechanisms.</p>
|
||||
<p>In addition, the wide language binding support that gRPC/proto3 bringsenables us to provide a flexible and rapid development environment for both internal and external consumers.</p>
|
||||
<p>Last but not least, while there are a number of network communicationprotocols for configuration, operational state retrieval and network telemetry, gRPC provides us with a unified flexible protocol and transport to ease client/server interaction.</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="testimonialsection">
|
||||
<div class="testimonialimage"><a href="http://www.pingcap.com"><img src="../img/pingcap5.png"/></a></div>
|
||||
<div>
|
||||
<span class="testimonialquote">“ </span>
|
||||
At PingCAP, we use gRPC in almost every project that involves interactions or communications through network. As has been proven, gRPC has well met our demands in terms of performance and usability. We also provide a production-ready gRPC library for Rust.
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="clearfix"></div>
|
||||
{{< testimonials >}}
|
||||
|
||||
## Officially supported platforms
|
||||
|
||||
<style>
|
||||
th:first-child { width: 20%; }
|
||||
</style>
|
||||
|
||||
| Language | Platform | Compiler |
|
||||
| -------- | -------- | -------- |
|
||||
| C/C++ | Linux/Mac | GCC 4.9+ <br> Clang 3.4+ |
|
||||
| C/C++ | Windows 7+ | Visual Studio 2015+ |
|
||||
| C# | Linux/Mac | .NET Core, Mono 4+ |
|
||||
| C# | Windows 7+ | .NET Core, .NET 4.5+ |
|
||||
| Dart | Windows/Linux/Mac | Dart 2.0+ |
|
||||
| Go | Windows/Linux/Mac | Go 1.6+ |
|
||||
| Java | Windows/Linux/Mac | JDK 8 recommended. Gingerbread+ for Android |
|
||||
| Node.js | Windows/Linux/Mac | Node v4+ |
|
||||
| Objective-C | Mac OS X 10.11+/iOS 7.0+ | Xcode 7.2+ |
|
||||
| PHP (beta) | Linux/Mac | PHP 5.5+ and PHP 7.0+ |
|
||||
| Python | Windows/Linux/Mac | Python 2.7 and Python 3.4+ |
|
||||
| Ruby | Windows/Linux/Mac | Ruby 2.3+ |
|
||||
{{< supported-platforms >}}
|
||||
|
||||
## The story behind gRPC
|
||||
|
||||
|
|
@ -162,5 +50,5 @@ the industry and collaborate with them to build the next version of Stubby both
|
|||
for microservices inside and outside Google but also for last mile of computing
|
||||
(mobile, web and IOT).
|
||||
|
||||
For more background on why we created gRPC, see [gRPC Motivation and Design
|
||||
Principles blog](/blog/principles).
|
||||
For more background on why we created gRPC, see the [gRPC Motivation and Design
|
||||
Principles](/blog/principles) on the [gRPC blog](/blog).
|
||||
|
|
|
|||
|
|
@ -1,27 +0,0 @@
|
|||
---
|
||||
attribution: Mugur Marculescu, gRPC
|
||||
date: "2015-10-26T00:00:00Z"
|
||||
published: true
|
||||
title: gRPC releases Beta, opening door for use in production environments.
|
||||
url: blog/beta_release
|
||||
---
|
||||
|
||||
<p>
|
||||
The gRPC team is excited to announce the immediate availability of gRPC Beta. This release marks an important point in API stability and going forward most API changes are expected to be additive in nature. This milestone opens the door for gRPC use in production environments.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
We’re also taking a big step forward in improving the installation process. Over the past few weeks we’ve rolled out gRPC packages to <a href="https://packages.debian.org/jessie-backports/libgrpc0">Debian Stable/Backports</a>. Installation in most cases is now a two line install using the Debian package and available language specific package managers (<a href="https://search.maven.org/#artifactdetails%7Cio.grpc%7Cgrpc-core%7C0.9.0%7Cjar">maven</a>, <a href="https://pypi.python.org/pypi/grpcio">pip</a>, <a href="https://rubygems.org/gems/grpc">gem</a>, <a href="https://packagist.org/packages/grpc/grpc">composer</a>, <a href="https://pecl.php.net/package/gRPC">pecl</a>, <a href="https://www.npmjs.com/package/grpc">npm</a>, <a href="https://www.nuget.org/packages/Grpc/">nuget</a>, <a href="https://cocoapods.org/pods/gRPC">pod</a>). In addition <a href="https://hub.docker.com/r/grpc/">gRPC docker images</a> are now available on Docker Hub.
|
||||
</p>
|
||||
<p>
|
||||
We’ve updated the <a href="/docs/">documentation</a> on grpc.io to reflect the latest changes and released additional language-specific <a href="/docs/reference/">reference docs</a>. See what’s changed with the Beta release in the release notes on GitHub for <a href="https://github.com/grpc/grpc-java/releases/tag/v0.9.0">Java</a>, <a href="https://godoc.org/google.golang.org/grpc">Go</a> and <a href="https://github.com/grpc/grpc/releases/tag/release-0_11_0">all other</a> languages.
|
||||
</p>
|
||||
<p>
|
||||
In keeping in line with our <a href="/blog/principles">principles</a> and goal to enable highly performant and scalable APIs and microservices on top of HTTP/2, in the coming months, the focus of the gRPC project will be to keep improving performance and stability and adding carefully chosen features for production use cases. Documentation will also be clarified and will continue to improve with new examples and guides.
|
||||
</p>
|
||||
<p>
|
||||
We’ve been very excited to see the community response to gRPC and the various projects starting to use it (<a href="https://coreos.com/blog/etcd-2.2/">etcd v3 experimental api</a>, <a href="https://github.com/gengo/grpc-gateway">grpc-gateway</a> for RESTful APIs and others).
|
||||
</p>
|
||||
<p>
|
||||
We really want to thank everyone who contributed code, gave presentations, adopted the technology and engaged in the community. With your help support we look forward to the 1.0!
|
||||
</p>
|
||||
|
|
@ -1,48 +0,0 @@
|
|||
---
|
||||
attribution: Originally written by Louis Ryan with help from others at Google.
|
||||
date: "2015-09-08T00:00:00Z"
|
||||
published: true
|
||||
title: gRPC Motivation and Design Principles.
|
||||
url: blog/principles
|
||||
---
|
||||
|
||||
<h2>Motivation</h2>
|
||||
|
||||
<p>Google has been using a single general-purpose RPC infrastructure called Stubby to connect the large number of microservices running within and across our data centers for over a decade. Our internal systems have long embraced the microservice architecture gaining popularity today. Having a uniform, cross-platform RPC infrastructure has allowed for the rollout of fleet-wide improvements in efficiency, security, reliability and behavioral analysis critical to supporting the incredible growth seen in that period.
|
||||
</p>
|
||||
|
||||
<p>Stubby has many great features - however, it's not based on any standard and is too tightly coupled to our internal infrastructure to be considered suitable for public release. With the advent of SPDY, HTTP/2, and QUIC, many of these same features have appeared in public standards, together with other features that Stubby does not provide. It became clear that it was time to rework Stubby to take advantage of this standardization, and to extend its applicability to mobile, IoT, and Cloud use-cases.</p>
|
||||
|
||||
<h2>Principles & Requirements</h2>
|
||||
|
||||
<p><strong>Services not Objects, Messages not References</strong> - Promote the microservices design philosophy of coarse-grained message exchange between systems while avoiding the <a href="https://martinfowler.com/articles/distributed-objects-microservices.html">pitfalls of distributed objects</a> and the <a href="https://en.wikipedia.org/wiki/Fallacies_of_distributed_computing">fallacies of ignoring the network</a>.</p>
|
||||
|
||||
<p><strong>Coverage & Simplicity</strong> - The stack should be available on every popular development platform and easy for someone to build for their platform of choice. It should be viable on CPU & memory limited devices. </p>
|
||||
|
||||
<p><strong>Free & Open</strong> - Make the fundamental features free for all to use. Release all artifacts as open-source efforts with licensing that should facilitate and not impede adoption.</p>
|
||||
|
||||
<p><strong>Interoperability & Reach</strong> - The wire-protocol must be capable of surviving traversal over common internet infrastructure.</p>
|
||||
|
||||
<p><strong>General Purpose & Performant</strong> - The stack should be applicable to a broad class of use-cases while sacrificing little in performance when compared to a use-case specific stack.</p>
|
||||
|
||||
<p><strong>Layered</strong> - Key facets of the stack must be able to evolve independently. A revision to the wire-format should not disrupt application layer bindings.</p>
|
||||
|
||||
<p><strong>Payload Agnostic</strong> - Different services need to use different message types and encodings such as protocol buffers, JSON, XML, and Thrift; the protocol and implementations must allow for this. Similarly the need for payload compression varies by use-case and payload type: the protocol should allow for pluggable compression mechanisms.</p>
|
||||
|
||||
<p><strong>Streaming</strong> - Storage systems rely on streaming and flow-control to express large data-sets. Other services, like voice-to-text or stock-tickers, rely on streaming to represent temporally related message sequences.</p>
|
||||
|
||||
<p><strong>Blocking & Non-Blocking</strong> - Support both asynchronous and synchronous processing of the sequence of messages exchanged by a client and server. This is critical for scaling and handling streams on certain platforms.</p>
|
||||
|
||||
<p><strong>Cancellation & Timeout</strong> - Operations can be expensive and long-lived - cancellation allows servers to reclaim resources when clients are well-behaved. When a causal-chain of work is tracked, cancellation can cascade. A client may indicate a timeout for a call, which allows services to tune their behavior to the needs of the client.</p>
|
||||
|
||||
<p><strong>Lameducking</strong> - Servers must be allowed to gracefully shut-down by rejecting new requests while continuing to process in-flight ones.</p>
|
||||
|
||||
<p><strong>Flow-Control</strong> - Computing power and network capacity are often unbalanced between client & server. Flow control allows for better buffer management as well as providing protection from DOS by an overly active peer.</p>
|
||||
|
||||
<p><strong>Pluggable</strong> - A wire protocol is only part of a functioning API infrastructure. Large distributed systems need security, health-checking, load-balancing and failover, monitoring, tracing, logging, and so on. Implementations should provide extensions points to allow for plugging in these features and, where useful, default implementations.</p>
|
||||
|
||||
<p><strong>Extensions as APIs</strong> - Extensions that require collaboration among services should favor using APIs rather than protocol extensions where possible. Extensions of this type could include health-checking, service introspection, load monitoring, and load-balancing assignment.</p>
|
||||
|
||||
<p><strong>Metadata Exchange</strong> - Common cross-cutting concerns like authentication or tracing rely on the exchange of data that is not part of the declared interface of a service. Deployments rely on their ability to evolve these features at a different rate to the individual APIs exposed by services.</p>
|
||||
|
||||
<p><strong>Standardized Status Codes</strong> - Clients typically respond to errors returned by API calls in a limited number of ways. The status code namespace should be constrained to make these error handling decisions clearer. If richer domain-specific status is needed the metadata exchange mechanism can be used to provide that.</p>
|
||||
|
|
@ -1,43 +0,0 @@
|
|||
---
|
||||
attribution: Originally written by Dale Hopkins with additional content by Lisa Carey
|
||||
and others at Google.
|
||||
author: Dale Hopkins
|
||||
company: Vendasta
|
||||
company-link: https://vendasta.com
|
||||
date: "2016-07-25T00:00:00Z"
|
||||
published: false
|
||||
thumbnail: ../img/vend-icon.png?raw=true
|
||||
title: Why we have decided to move our APIs to gRPC
|
||||
url: blog/vendasta
|
||||
---
|
||||
|
||||
Our guest post today comes from Dale Hopkins, CTO of [Vendasta](https://vendasta.com/). Vendasta started out 8 years ago as a point solution provider of products for small business. From the beginning we partnered with media companies and agencies who have armies of salespeople and existing relationships with those businesses to sell our software. It is estimated that over 30 million small businesses exist in the United States alone, so scalability of our SaaS solution was considered one of our top concerns from the beginning and it was the reason we started with Google App Engine (Python GAE) and Datastore. This solution worked really well for us as our system scaled from hundreds to hundreds of thousands of end users. We also scaled our offering from a point solution to an entire platform with multiple products and the tools for partners to manage their sales of those products during this time.
|
||||
|
||||
<!--more-->
|
||||
All throughout this journey Python GAE served our needs well. We exposed a number of APIs via HTTP + JSON for our partners to automate tasks and integrate their other systems with our products and platform. However, in 2016 we introduced the Vendasta Marketplace. This marked a major change to our offering, which depended heavily on having 3rd party vendors use our APIs to deliver their own products in our platform. This was a major change because our public APIs provide an upper-bound on 3rd-party applications, and made us realize that we really needed to make APIs that were amazing, not just good.
|
||||
|
||||
|
||||
# Three Optimizations to our architecture
|
||||
|
||||
* The first optimization that we started with was to use the Go programming language to build endpoints that handled higher throughput with lower latency than we could get with Python. On some APIs this made an incredible difference: we saw 50th percentile response times to drop from 1200 ms to 4 ms, and even more spectacularly 99th percentile response times drop from 30,000 ms to 12 ms! On other APIs we saw a much smaller, but still significant difference.
|
||||
|
||||
|
||||
* The second optimization we used was to replicate large portions of our Datastore data into ElasticSearch. ElasticSearch is a fundamentally different storage technology to Datastore, and is not a managed service, so it was a big leap for us. But this change allowed us to migrate almost all of our overnight batch-processing APIs to real-time APIs. So with these first two solutions in place, we had made meaningful changes to the performance of our APIs.
|
||||
|
||||
* The last optimization we made was to move our APIs to gRPC. This change was much more extensive than the others as it affected our clients. Like ElasticSearch, it represents a fundamentally different model with differing performance characteristics, but unlike ElasticSearch we found it to be a true superset: all of our usage scenarios were impacted positively by it.
|
||||
|
||||
|
||||
## Four Benefits from gRPC
|
||||
|
||||
* The first benefit we saw from gRPC was the ability to move from publishing APIs and asking developers to integrate with them, to releasing SDKs and asking developers to copy-paste example code written in their language. This represents a really big benefit for people looking to integrate with our products, while not requiring us to hand-roll entire SDKs in the 5+ languages our partners and vendors use. It is important to note that we still write light wrappers over the generated gRPC SDKs to make them package-manager friendly, and to provide wrappers over the generated protobuf structures.
|
||||
|
||||
|
||||
* The second benefit we saw from gRPC was the ability to break free from the call-and-response architecture necessitated by HTTP + JSON. gRPC is built on top of HTTP/2, which allows for client-side and/or server-side streaming. In our use cases, this means we can lower the time to first display by streaming results as they become ready on the server (server-side streaming), and by providing very flexible create endpoints that easily support bulk ingestion (bi-directional streaming). We feel that we are just starting to see the benefits from this feature as it opens up a totally new model for client-server interactions that just wasn't possible with HTTP.
|
||||
|
||||
* The third benefit was the switch from JSON to protocol buffers, which works very well with gRPC. This improves serialization and deserialization times; which is very significant to some of our APIs, but appreciated on all of them. The more important benefit comes from the explicit format specification of proto, meaning that clients receive typed objects rather than free-form JSON. Because of this, our clients can reap the benefits of auto-completion in their IDEs, type-safety if their language supports it, and enforced compatibility between clients and servers with differing versions.
|
||||
|
||||
* The final benefit of gRPC was our ability to quickly spec endpoints. The proto format for both data and service definition greatly simplifies defining new endpoints and finally allows the succinct definition of endpoint contracts. Combined with code generation, it allows us to truly develop clients and servers in parallel.
|
||||
|
||||
|
||||
Our experience with gRPC has been positive, even though it does not eliminate the difficulty of providing endpoints to partners and vendors, and address of our performance issues. However, it does make improvements to our endpoint performance, integration with those endpoints, and even in delivery of SDKs.
|
||||
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
---
|
||||
attribution: Mark Mandel, Sandeep Dinesh
|
||||
date: "2017-09-14T00:00:00Z"
|
||||
published: true
|
||||
title: The gRPC Meetup Kit
|
||||
url: blog/meetup-kit
|
||||
---
|
||||
|
||||
<p>If you have ever wanted to run an event around <a href="http://grpc.io">gRPC</a>, but didn’t know where to start, or wasn’t sure what content is available - we have released the <a href="https://github.com/grpc-ecosystem/meetup-kit">gRPC Meetup Kit</a>!</p>
|
||||
|
||||
<p>The meetup kit includes a 15 minute presentation on the basic concepts of gRPC, with accompanying <a href="https://docs.google.com/presentation/d/1dgI09a-_4dwBMLyqfwchvS6iXtbcISQPLAXL6gSYOcc/edit?usp=sharing">slides</a> and <a href="https://www.youtube.com/watch?v=UVsIfSfS6I4">video</a> for either reference or playback, as well as a <a href="https://codelabs.developers.google.com/codelabs/cloud-grpc/index.html">45 minute codelab</a> that takes you through the basics of gRPC in <a href="https://nodejs.org">Node.js</a> and <a href="https://golang.org/">Go</a>. At the end of the codelab participants will have a solid understanding of the fundamentals of gRPC.</p>
|
||||
<p>If you are thinking about running a gRPC event, make sure to contact us to receive <a href="https://goo.gl/forms/C3TCtFdobz4ippty2">gRPC stickers</a> and/or organise <a href="https://goo.gl/forms/pvxNwWExr5ApbNst2">office hours over Hangouts with the gRPC team</a>! </p>
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
---
|
||||
title: The gRPC Blog
|
||||
---
|
||||
|
|
@ -1,10 +1,8 @@
|
|||
---
|
||||
title: A short introduction to Channelz
|
||||
author: Yuxuan Li
|
||||
author-link: https://github.com/lyuxuan
|
||||
date: "2018-09-05T00:00:00Z"
|
||||
published: true
|
||||
title: A short introduction to Channelz
|
||||
url: blog/a_short_introduction_to_channelz
|
||||
date: 2018-09-05
|
||||
---
|
||||
|
||||
Channelz is a tool that provides comprehensive runtime info about connections at
|
||||
|
|
@ -1,13 +1,11 @@
|
|||
---
|
||||
title: Building gRPC services with bazel and rules_protobuf
|
||||
attribution: Originally written by Paul Johnston.
|
||||
author: Paul Cody Johnston
|
||||
company: PubRef.org
|
||||
company-link: https://pubref.org
|
||||
date: "2016-10-13T00:00:00Z"
|
||||
published: true
|
||||
date: 2016-10-13
|
||||
thumbnail: https://avatars3.githubusercontent.com/u/10408150?v=3&s=200
|
||||
title: Building gRPC services with bazel and rules_protobuf
|
||||
url: blog/bazel_rules_protobuf
|
||||
---
|
||||
|
||||
[gRPC](/) makes it easier to build high-performance
|
||||
|
|
@ -0,0 +1,20 @@
|
|||
---
|
||||
title: gRPC releases Beta, opening door for use in production environments
|
||||
attribution: Mugur Marculescu, gRPC
|
||||
date: 2015-10-26
|
||||
aliases: ["blog/beta_release"]
|
||||
---
|
||||
|
||||
The gRPC team is excited to announce the immediate availability of gRPC Beta. This release marks an important point in API stability and going forward most API changes are expected to be additive in nature. This milestone opens the door for gRPC use in production environments.
|
||||
|
||||
We’re also taking a big step forward in improving the installation process. Over the past few weeks we’ve rolled out gRPC packages to <a href="https://packages.debian.org/jessie-backports/libgrpc0">Debian Stable/Backports</a>. Installation in most cases is now a two line install using the Debian package and available language specific package managers (<a href="https://search.maven.org/#artifactdetails%7Cio.grpc%7Cgrpc-core%7C0.9.0%7Cjar">maven</a>, <a href="https://pypi.python.org/pypi/grpcio">pip</a>, <a href="https://rubygems.org/gems/grpc">gem</a>, <a href="https://packagist.org/packages/grpc/grpc">composer</a>, <a href="https://pecl.php.net/package/gRPC">pecl</a>, <a href="https://www.npmjs.com/package/grpc">npm</a>, <a href="https://www.nuget.org/packages/Grpc/">nuget</a>, [pod](https://cocoapods.org/pods/gRPC)). In addition [gRPC docker images](https://hub.docker.com/r/grpc) are now available on Docker Hub.
|
||||
|
||||
|
||||
We’ve updated the [documentation](/docs) on grpc.io to reflect the latest changes and released additional language-specific [reference docs](/docs/reference). See what’s changed with the Beta release in the release notes on GitHub for [Java](https://github.com/grpc/grpc-java/releases/tag/v0.9.0), [Go](https://godoc.org/google.golang.org/grpc), and [all other](https://github.com/grpc/grpc/releases/tag/release-0_11_0) languages.
|
||||
|
||||
In keeping in line with our [principles](../principles) and goal to enable highly performant and scalable APIs and microservices on top of HTTP/2, in the coming months, the focus of the gRPC project will be to keep improving performance and stability and adding carefully chosen features for production use cases. Documentation will also be clarified and will continue to improve with new examples and guides.
|
||||
|
||||
|
||||
We’ve been very excited to see the community response to gRPC and the various projects starting to use it ([etcd v3 experimental API](https://coreos.com/blog/etcd-2.2), [grpc-gateway](https://github.com/gengo/grpc-gateway) for RESTful APIs and others).
|
||||
|
||||
We really want to thank everyone who contributed code, gave presentations, adopted the technology and engaged in the community. With your help support we look forward to the 1.0!
|
||||
|
|
@ -1,10 +1,9 @@
|
|||
---
|
||||
title: 2017-08-17 Community Meeting Update
|
||||
author: Jaye Pitzeruse
|
||||
company: Indeed
|
||||
company-link: https://www.indeed.com
|
||||
date: "2017-08-17T00:00:00Z"
|
||||
published: true
|
||||
title: 2017-08-17 Community Meeting Update
|
||||
date: 2017-08-17
|
||||
---
|
||||
|
||||
**Next Community Meeting:** Thursday, August 31, 2017 11am Pacific Time (US and Canada)
|
||||
|
|
@ -1,14 +1,12 @@
|
|||
---
|
||||
title: gRPC with REST and Open APIs
|
||||
attribution: Originally written by Brandon Phillips with additional content by Lisa
|
||||
Carey and others at Google.
|
||||
Carey and others at Google
|
||||
author: Brandon Phillips
|
||||
company: CoreOS
|
||||
company-link: https://coreos.com
|
||||
date: "2016-05-09T00:00:00Z"
|
||||
published: true
|
||||
date: 2016-05-09
|
||||
thumbnail: https://avatars2.githubusercontent.com/u/3730757?v=3&s=200
|
||||
title: gRPC with REST and Open APIs
|
||||
url: blog/coreos
|
||||
---
|
||||
|
||||
Our guest post today comes from Brandon Phillips of [CoreOS](https://coreos.com/). CoreOS builds open source projects and products for Linux Containers. Their flagship product for consensus and discovery [etcd](https://coreos.com/etcd/) and their container engine [rkt](https://coreos.com/rkt/) are early adopters of gRPC.
|
||||
|
|
@ -1,14 +1,12 @@
|
|||
---
|
||||
title: gRPC and Deadlines
|
||||
author: Gráinne Sheerin, Google SRE
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2018-02-26T00:00:00Z"
|
||||
published: true
|
||||
title: gRPC and Deadlines
|
||||
url: blog/deadlines
|
||||
date: 2018-02-26
|
||||
---
|
||||
|
||||
**TL;DR Always set a deadline**. This post explains why we recommend being deliberate about setting deadlines, with useful code snippets to show you how.
|
||||
**TL;DR: Always set a deadline**. This post explains why we recommend being deliberate about setting deadlines, with useful code snippets to show you how.
|
||||
|
||||
<!--more-->
|
||||
|
||||
|
|
@ -1,14 +1,13 @@
|
|||
---
|
||||
title: gRPC Project is now 1.0 and ready for production deployments
|
||||
attribution: Originally written by Varun Talwar with additional content by Kailash
|
||||
Sethuraman and others at Google.
|
||||
author: Varun Talwar
|
||||
company: Google
|
||||
company-link: https://cloud.google.com
|
||||
date: "2016-08-23T00:00:00Z"
|
||||
published: true
|
||||
date: 2016-08-23
|
||||
thumbnail: ../img/gcp-icon.png?raw=true
|
||||
title: gRPC Project is now 1.0 and ready for production deployments
|
||||
url: blog/gablogpost
|
||||
aliases: ["blog/gablogpost"]
|
||||
---
|
||||
|
||||
Today, the gRPC project has reached a significant milestone with its [1.0 release](https://github.com/grpc/grpc/releases).
|
||||
|
|
@ -1,12 +1,10 @@
|
|||
---
|
||||
title: Gracefully clean up in gRPC JUnit tests
|
||||
author: Dapeng Zhang
|
||||
author-link: https://github.com/dapengzhang0
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2018-06-26T00:00:00Z"
|
||||
published: true
|
||||
title: Gracefully clean up in gRPC JUnit tests
|
||||
url: blog/gracefully_clean_up_in_grpc_junit_tests
|
||||
date: 2018-06-26
|
||||
---
|
||||
|
||||
It is best practice to always clean up gRPC resources such as client channels, servers, and previously attached Contexts whenever they are no longer needed.
|
||||
|
|
@ -112,5 +110,5 @@ public class MyTest {
|
|||
|
||||
Now with [`GrpcCleanupRule`][GrpcCleanupRule] you don't need to worry about graceful shutdown of gRPC servers and channels in JUnit test. So try it out and clean up in your tests!
|
||||
|
||||
[GrpcServerRule]:https://github.com/grpc/grpc-java/blob/v1.1.x/testing/src/main/java/io/grpc/testing/GrpcServerRule.java
|
||||
[GrpcCleanupRule]:https://github.com/grpc/grpc-java/blob/v1.13.x/testing/src/main/java/io/grpc/testing/GrpcCleanupRule.java
|
||||
[GrpcServerRule]: https://github.com/grpc/grpc-java/blob/v1.1.x/testing/src/main/java/io/grpc/testing/GrpcServerRule.java
|
||||
[GrpcCleanupRule]: https://github.com/grpc/grpc-java/blob/v1.13.x/testing/src/main/java/io/grpc/testing/GrpcCleanupRule.java
|
||||
|
|
@ -1,10 +1,8 @@
|
|||
---
|
||||
title: "gRPC Meets .NET SDK And Visual Studio: Automatic Codegen On Build"
|
||||
author: Kirill 'kkm' Katsnelson
|
||||
author-link: https://github.com/kkm000
|
||||
date: "2018-12-18T00:00:00Z"
|
||||
published: true
|
||||
title: "gRPC Meets .NET SDK And Visual Studio: Automatic Codegen On Build"
|
||||
url: blog/grpc-dotnet-build
|
||||
date: 2018-12-18
|
||||
---
|
||||
|
||||
As part of Microsoft's move towards its cross-platform .NET offering, they have
|
||||
|
|
@ -14,6 +12,8 @@ to introduce integrated compilation of Protocol Buffer and gRPC service
|
|||
`.proto` files in .NET C# projects starting with the version 1.17 of the
|
||||
Grpc.Tools NuGet package, now available from Nuget.org.
|
||||
|
||||
<!--more-->
|
||||
|
||||
You no longer need to use hand-written scripts to generate code from `.proto`
|
||||
files: The .NET build magic handles this for you. The integrated tools locate
|
||||
the proto compiler and gRPC plugin, standard Protocol Buffer imports, and track
|
||||
|
|
@ -22,8 +22,6 @@ source files are never out of date, at the same time keeping regeneration to
|
|||
the minimum required. In essence, `.proto` files are treated as first-class
|
||||
sources in a .NET C# project.
|
||||
|
||||
<!--more-->
|
||||
|
||||
## A Walkthrough
|
||||
|
||||
In this blog post, we'll walk through the simplest and probably the most common
|
||||
|
|
@ -1,12 +1,9 @@
|
|||
---
|
||||
title: Announcing out-of-the-box support for gRPC in the Flatbuffers serialization library
|
||||
author: Wouter van Oortmerssen
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2017-08-17T00:00:00Z"
|
||||
published: true
|
||||
title: Announcing out of the box support for gRPC in the Flatbuffers serialization
|
||||
library.
|
||||
url: blog/flatbuffers
|
||||
date: 2017-08-17
|
||||
---
|
||||
|
||||
The recent release of Flatbuffers [version 1.7](https://github.com/google/flatbuffers/releases) introduced truly zero-copy support for gRPC out of the box.
|
||||
|
|
@ -22,9 +19,11 @@ This is currently, fully supported in the C++ implementation of FlatBuffers, wit
|
|||
|
||||
|
||||
## Example Usage
|
||||
|
||||
Let's look at an example of how this works.
|
||||
|
||||
### Use Flatbuffers as an IDL
|
||||
|
||||
Start with an `.fbs` schema (similar to .proto, if you are familiar with protocol buffers) that declares an RPC service:
|
||||
|
||||
```proto
|
||||
|
|
@ -1,10 +1,9 @@
|
|||
---
|
||||
title: gRPC-Go Engineering Practices
|
||||
author: Doug Fawley, gRPC-Go TL
|
||||
company: Google
|
||||
company-link: google.com
|
||||
date: "2018-01-22T00:00:00Z"
|
||||
published: true
|
||||
title: 2018-01-19 gRPC-Go Engineering Practices
|
||||
date: 2018-01-22
|
||||
---
|
||||
|
||||
It's the start of the new year, and almost the end of my first full year on the
|
||||
|
|
@ -1,23 +1,20 @@
|
|||
---
|
||||
title: gRPC-Go performance Improvements
|
||||
author: Mahak Mukhi
|
||||
company: Google
|
||||
company-link: google.com
|
||||
date: "2017-08-22T00:00:00Z"
|
||||
published: true
|
||||
title: 2017-08-22 gRPC-Go performance Improvements
|
||||
date: 2017-08-22
|
||||
---
|
||||
<p>
|
||||
<span style="margin-bottom:5%">For past few months we've been working on improving gRPC-Go performance. This includes improving network utilization, optimizing CPU usage and memory allocations. Most of our recent effort has been focused around revamping gRPC-Go flow control. After several optimizations and new features we've been able to improve quite significantly, especially on high-latency networks. We expect users that are working with high-latency networks and large messages to see an order of magnitude performance gain.
|
||||
|
||||
For past few months we've been working on improving gRPC-Go performance. This includes improving network utilization, optimizing CPU usage and memory allocations. Most of our recent effort has been focused around revamping gRPC-Go flow control. After several optimizations and new features we've been able to improve quite significantly, especially on high-latency networks. We expect users that are working with high-latency networks and large messages to see an order of magnitude performance gain.
|
||||
Benchmark results at the end.
|
||||
|
||||
This blog summarizes the work we have done so far (in chronological order) to improve performance and lays out our near-future plans.</style>
|
||||
</p><br>
|
||||
This blog summarizes the work we have done so far (in chronological order) to improve performance and lays out our near-future plans.
|
||||
<!--more-->
|
||||
|
||||
### Recently Implemented Optimizations
|
||||
## Recently Implemented Optimizations
|
||||
|
||||
|
||||
###### Expanding stream window on receiving large messages
|
||||
### Expanding stream window on receiving large messages
|
||||
|
||||
[Code link](https://github.com/grpc/grpc-go/pull/1248)
|
||||
|
||||
|
|
@ -26,7 +23,7 @@ This is an optimization used by gRPC-C to achieve performance benefits for large
|
|||
This optimization alone provided a 10x improvement for large messages on high-latency networks.
|
||||
|
||||
|
||||
###### Decoupling application reads from connection flow control
|
||||
### Decoupling application reads from connection flow control
|
||||
|
||||
[Code link](https://github.com/grpc/grpc-go/pull/1265)
|
||||
|
||||
|
|
@ -45,14 +42,13 @@ The need for connection-level flow control:
|
|||
It is true that stream-level flow control is sufficient to throttle a sender from sending too much data. But not having connection-level flow control (or using an unlimited connection-level window) makes it so that when things get slower on a stream, opening a new one will appear to make things faster. This will only take one so far since the number of streams are limited. However, having a connection-level flow control window set to the Bandwidth Delay Product (BDP) of the network puts an upper-bound on how much performance can realistically be squeezed out of the network.
|
||||
|
||||
|
||||
###### Piggyback window updates
|
||||
### Piggyback window updates
|
||||
|
||||
[Code link](https://github.com/grpc/grpc-go/pull/1273)
|
||||
|
||||
Sending a window update itself has a cost associated to it; a flush operation is necessary, which results in a syscall. Syscalls are blocking and slow. Therefore, when sending out a stream-level window update, it makes sense to also check if a connection-level window update can be sent using the same flush syscall.
|
||||
|
||||
|
||||
###### BDP estimation and dynamic flow control window
|
||||
### BDP estimation and dynamic flow control window
|
||||
|
||||
[Code link](https://github.com/grpc/grpc-go/pull/1310)
|
||||
|
||||
|
|
@ -72,13 +68,11 @@ Given that we're always bound by the flow control of TCP which for most cases is
|
|||
|
||||
BDP estimation and dynamically adjusting window sizes is turned-on by default and can be turned off by setting values manually for connection and/or stream window sizes.
|
||||
|
||||
|
||||
###### Near-future efforts
|
||||
### Near-future efforts
|
||||
|
||||
We are now looking into improving our throughput by better CPU utilization, the following efforts are in-line with that.
|
||||
|
||||
|
||||
###### Reducing flush syscalls
|
||||
### Reducing flush syscalls
|
||||
|
||||
We noticed a bug in our transport layer which causes us to make a flush syscall for every data frame we write, even if the same goroutine has more data to send. We can batch a lot of these writes to use only one flush. This in fact will not be a big change to the code itself.
|
||||
|
||||
|
|
@ -86,15 +80,11 @@ In our efforts to get rid of unnecessary flushes we recently combined the header
|
|||
|
||||
Another related idea proposed by one of our users @petermattic in [this](https://github.com/grpc/grpc-go/pull/1373) PR was to combine a server response to a unary RPC into one flush. We are currently looking into that as well.
|
||||
|
||||
|
||||
###### Reducing memory allocation
|
||||
### Reducing memory allocation
|
||||
|
||||
For every data frame read from the wire a new memory allocation takes place. The same holds true at the gRPC layer for every new message for decompressing and decoding. These allocations result in excessive garbage collection cycles, which are expensive. Reusing memory buffers can reduce this GC pressure, and we are prototyping approaches to do so. As requests need buffers of differing sizes, one approach would be to maintain individual memory pools of fixed sizes (powers of two). So now when reading x bytes from the wire we can find the nearest power of 2 greater than x and reuse a buffer from our cache if available or allocate a new one if need be. We will be using golang sync Pools so we don't have to worry about garbage collection. However, we will need to run sufficient tests before committing to this.
|
||||
|
||||
|
||||
|
||||
###### Results:
|
||||
|
||||
### Results
|
||||
|
||||
* Benchmark on a real network:
|
||||
|
||||
|
|
@ -104,18 +94,14 @@ For every data frame read from the wire a new memory allocation takes place. The
|
|||
* [Code link](https://github.com/grpc/grpc-go/compare/master...MakMukhi:http_greeter)
|
||||
|
||||
|
||||
<table>
|
||||
<tr><th>Message Size </th><th>GRPC </th><th>HTTP 1.1</th></tr>
|
||||
|
||||
<tr><td>1 KB</td><td>~152 ms</td><td>~152 ms</td></tr>
|
||||
<tr><td>10 KB</td><td>~152 ms</td><td>~152 ms</td></tr>
|
||||
<tr><td>10 KB</td><td>~152 ms</td><td>~152 ms</td></tr>
|
||||
<tr><td>1 MB</td><td>~152 ms</td><td>~152 ms</td></tr>
|
||||
<tr><td>10 MB</td><td>~622 ms</td><td>~630 ms</td></tr>
|
||||
<tr><td>100 MB</td><td>~5 sec</td><td>~5 sec</td></tr>
|
||||
|
||||
|
||||
</table>
|
||||
Message size | gRPC | HTTP 1.1
|
||||
:------------|:-----|:--------
|
||||
1 KB | ~152 ms | ~152 ms
|
||||
10 KB | ~152 ms | ~152 ms
|
||||
10 KB | ~152 ms | ~152 ms
|
||||
1 MB | ~152 ms | ~152 ms
|
||||
10 MB | ~622 ms | ~630 ms
|
||||
100 MB | ~5 sec | ~5 sec
|
||||
|
||||
* Benchmark on simulated network:
|
||||
* Server and client were launched on the same machine and different network latencies were simulated.
|
||||
|
|
@ -124,9 +110,9 @@ For every data frame read from the wire a new memory allocation takes place. The
|
|||
* Following tables show time taken by first 10 RPCs.
|
||||
* [Code link](https://github.com/grpc/grpc-go/compare/master...MakMukhi:grpc_vs_http)
|
||||
|
||||
##### No Latency Network
|
||||
##### No-latency Network
|
||||
|
||||
| GRPC | HTTP 2.0 | HTTP 1.1 |
|
||||
| gRPC | HTTP 2.0 | HTTP 1.1 |
|
||||
| --------------|:-------------:|-----------:|
|
||||
|5.097809ms|16.107461ms|18.298959ms |
|
||||
|4.46083ms|4.301808ms|7.715456ms
|
||||
|
|
@ -141,7 +127,7 @@ For every data frame read from the wire a new memory allocation takes place. The
|
|||
|
||||
##### Network with RTT of 16ms
|
||||
|
||||
| GRPC | HTTP 2.0 | HTTP 1.1 |
|
||||
| gRPC | HTTP 2.0 | HTTP 1.1 |
|
||||
| --------------|:-------------:|-----------:|
|
||||
|118.837625ms|84.453913ms|58.858109ms
|
||||
|36.801006ms|22.476308ms|20.877585ms
|
||||
|
|
@ -1,11 +1,9 @@
|
|||
---
|
||||
title: gRPC Load Balancing
|
||||
author: makdharma
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2017-06-15T00:00:00Z"
|
||||
published: true
|
||||
title: gRPC Load Balancing
|
||||
url: blog/loadbalancing
|
||||
date: 2017-06-15
|
||||
---
|
||||
|
||||
This post describes various load balancing scenarios seen when deploying gRPC. If you use [gRPC](/) with multiple backends, this document is for you.
|
||||
|
|
@ -1,10 +1,8 @@
|
|||
---
|
||||
title: .NET Core ❤ gRPC
|
||||
author: Sourabh Shirhatti
|
||||
author-link: https://twitter.com/sshirhatti
|
||||
date: "2019-09-23T00:00:00Z"
|
||||
published: true
|
||||
title: .NET Core ❤ gRPC
|
||||
url: blog/grpc-on-dotnetcore
|
||||
date: 2019-09-23
|
||||
---
|
||||
|
||||
_This is a guest post by [Sourabh Shirhatti](https://twitter.com/sshirhatti), a Program Manager on the .NET team at Microsoft._
|
||||
|
|
@ -1,24 +1,23 @@
|
|||
---
|
||||
author: Jean de Klerk
|
||||
author-link: https://github.com/jadekler
|
||||
date: "2018-08-20T00:00:00Z"
|
||||
published: true
|
||||
title: gRPC on HTTP/2 Engineering a Robust, High Performance Protocol
|
||||
url: blog/grpc_on_http2
|
||||
author: Jean de Klerk
|
||||
author-link: https://github.com/jadekler
|
||||
date: 2018-08-20
|
||||
---
|
||||
|
||||
In a [previous article](/blog/http2_smarter_at_scale), we explored how HTTP/2 dramatically increases network efficiency and enables real-time communication by providing a framework for long-lived connections. In this article, we’ll look at how gRPC builds on HTTP/2’s long-lived connections to create a performant, robust platform for inter-service communication. We will explore the relationship between gRPC and HTTP/2, how gRPC manages HTTP/2 connections, and how gRPC uses HTTP/2 to keep connections alive, healthy, and utilized.
|
||||
|
||||
<!--more-->
|
||||
|
||||
## gRPC Semantics
|
||||
|
||||
To begin, let’s dive into how gRPC concepts relate to HTTP/2 concepts. gRPC introduces three new concepts: *channels* [1], *remote procedure calls* (RPCs), and *messages*. The relationship between the three is simple: each channel may have many RPCs while each RPC may have many messages.
|
||||
|
||||
<img src="/img/channels_mapping_2.png" title="Channel Mapping" alt="Channel Mapping" style="max-width: 800px">
|
||||

|
||||
|
||||
Let’s take a look at how gRPC semantics relate to HTTP/2:
|
||||
|
||||
<img src="/img/grpc_on_http2_mapping_2.png" title="gRPC on HTTP/2" alt="gRPC on HTTP/2" style="max-width: 800px">
|
||||

|
||||
|
||||
Channels are a key concept in gRPC. Streams in HTTP/2 enable multiple concurrent conversations on a single connection; channels extend this concept by enabling multiple streams over multiple concurrent connections. On the surface, channels provide an easy interface for users to send messages into; underneath the hood, though, an incredible amount of engineering goes into keeping these connections alive, healthy, and utilized.
|
||||
|
||||
|
|
@ -28,9 +27,9 @@ Channels represent virtual connections to an endpoint, which in reality may be b
|
|||
|
||||
In order to keep connections alive, healthy, and utilized, gRPC utilizes a number of components, foremost among them *name resolvers* and *load balancers*. The resolver turns names into addresses and then hands these addresses to the load balancer. The load balancer is in charge of creating connections from these addresses and load balancing RPCs between connections.
|
||||
|
||||
<img src="/img/dns_to_load_balancer_mapping_3.png" title="Resolvers and Load Balancers" alt="Resolvers and Load Balancers" style="max-width: 800px">
|
||||

|
||||
|
||||
<img src="/img/load_balance_round_robins_2.png" alt="Round Robin Load Balancer" style="max-width: 800px">
|
||||

|
||||
|
||||
A DNS resolver, for example, might resolve some host name to 13 IP addresses, and then a RoundRobin balancer might create 13 connections - one to each address - and round robin RPCs across each connection. A simpler balancer might simply create a connection to the first address. Alternatively, a user who wants multiple connections but knows that the host name will only resolve to one address might have their balancer create connections against each address 10 times to ensure that multiple connections are used.
|
||||
|
||||
|
|
@ -1,10 +1,8 @@
|
|||
---
|
||||
title: Visualizing gRPC Language Stacks
|
||||
author: Carl Mastrangelo
|
||||
author-link: https://carlmastrangelo.com/
|
||||
date: "2018-12-11T00:00:00Z"
|
||||
published: true
|
||||
title: Visualizing gRPC Language Stacks
|
||||
url: blog/grpc-stacks
|
||||
date: 2018-12-11
|
||||
---
|
||||
|
||||
Here is a high level overview of the gRPC Stacks. Each of the **10** default languages supported by gRPC has multiple layers, allowing you to customize what pieces you want in your application.
|
||||
|
|
@ -1,9 +1,7 @@
|
|||
---
|
||||
author: Luc Perkins - CNCF, Stanley Cheung - Google, Kailash Sethuraman - Google
|
||||
date: "2018-10-23T00:00:00Z"
|
||||
published: true
|
||||
title: gRPC-Web is Generally Available
|
||||
url: blog/grpc-web-ga
|
||||
author: Luc Perkins - CNCF, Stanley Cheung - Google, Kailash Sethuraman - Google
|
||||
date: 2018-10-23
|
||||
---
|
||||
|
||||
We are excited to announce the GA release of
|
||||
|
|
@ -35,7 +33,6 @@ From a broader architectural perspective, gRPC-Web enables end-to-end gRPC. The
|
|||
|
||||
<img src="/img/grpc-web-arch.png" style="max-width: 947px">
|
||||
|
||||
|
||||
<p style="text-align: center"> Figure 1.
|
||||
gRPC with gRPC-Web (left) and gRPC with REST (right)</p>
|
||||
|
||||
|
|
@ -1,12 +1,10 @@
|
|||
---
|
||||
title: gRPC + JSON
|
||||
author: Carl Mastrangelo
|
||||
author-link: https://carlmastrangelo.com
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2018-08-15T00:00:00Z"
|
||||
published: true
|
||||
title: gRPC + JSON
|
||||
url: blog/grpc-with-json
|
||||
date: 2018-08-15
|
||||
---
|
||||
|
||||
So you've bought into this whole RPC thing and want to try it out, but aren't quite sure about Protocol Buffers. Your existing code encodes your own objects, or perhaps you have code that needs a particular encoding. What to do?
|
||||
|
|
@ -227,4 +225,3 @@ Almost **10x** faster than before! We can still take advantage of gRPC's effici
|
|||
gRPC lets you use encoders other than Protobuf. It has no dependency on Protobuf and was specially made to work with a wide variety of environments. We can see that with a little extra boilerplate, we can use any encoder we want. While this post only covered JSON, gRPC is compatible with Thrift, Avro, Flatbuffers, Cap’n Proto, and even raw bytes! gRPC lets you be in control of how your data is handled. (We still recommend Protobuf though due to strong backwards compatibility, type checking, and performance it gives you.)
|
||||
|
||||
All the code is avaialable on [GitHub](https://github.com/carl-mastrangelo/kvstore/tree/04-gson-marshaller) if you would like to see a fully working implementation.
|
||||
|
||||
|
|
@ -1,10 +1,8 @@
|
|||
---
|
||||
title: Dear gRPC
|
||||
author: April Nassi
|
||||
author-link: https://www.thisisnotapril.com/
|
||||
date: "2019-03-08T00:00:00Z"
|
||||
published: true
|
||||
title: Dear gRPC
|
||||
url: blog/hello-pancakes
|
||||
date: 2019-03-08
|
||||
---
|
||||
|
||||
Dear gRPC,
|
||||
|
|
@ -15,7 +13,7 @@ You're 4 now and that's a big milestone! You're part of so much amazing technolo
|
|||
|
||||
We're proud of you, gRPC, and we're going to make this up to you. For starters - we got you a puppy! He's an adorable **G**olden **R**etriever and his name is **P**an**C**akes. He loves to run back and forth with toys, packets, or messages. He's super active and no matter how much we train him, we just can't get him to REST. PanCakes is going to be your best friend, and ambassador.
|
||||
|
||||
<img src="https://raw.githubusercontent.com/grpc/grpc-community/master/PanCakes/Pancakes_Birthday.png" alt="gRPC Mascot PanCakes" style="max-width: 547px">
|
||||

|
||||
|
||||
Even though it's a bit late, we still want to throw you a party, gRPC. Our friends at CNCF have planned a [big event](https://events.linuxfoundation.org/events/grpconf-2019/) for you on March 21, and there's going to be lots of people there! They'll be sharing stories about the cool things they've built, and meeting new people. It's an entire day all about you, and everyone there is going to learn so much. There will be other puppies who can play with PanCakes! Some of the amazing dogs from [Canine Companions for Independence](http://www.cci.org/) will be there to greet conference attendees and share how they help their humans live a more independent life.
|
||||
|
||||
|
|
@ -23,4 +21,4 @@ We are so excited to see what this year holds for you, gRPC!
|
|||
|
||||
~ gRPC Maintainers
|
||||
|
||||
<img src="https://raw.githubusercontent.com/grpc/grpc-community/master/PanCakes/Pancakes_Birthday_4.png" alt="gRPC Mascot PanCakes" style="max-width: 547px">
|
||||

|
||||
|
|
@ -1,12 +1,10 @@
|
|||
---
|
||||
title: gRPC in Helm
|
||||
author: Brian Hardock
|
||||
company: DEIS
|
||||
company-link: https://deis.com/
|
||||
date: "2017-05-15T00:00:00Z"
|
||||
published: true
|
||||
date: 2017-05-15
|
||||
thumbnail: https://gabrtv.github.io/deis-dockercon-2014/img/DeisLogo.png
|
||||
title: gRPC in Helm
|
||||
url: blog/helmgrpc
|
||||
---
|
||||
|
||||
*Our guest post today comes from Brian Hardock, a software engineer from Deis working on the [Helm](https://helm.sh/) project.*
|
||||
|
|
@ -1,15 +1,14 @@
|
|||
---
|
||||
title: HTTP/2 Smarter At Scale
|
||||
author: Jean de Klerk
|
||||
author-link: https://github.com/jadekler
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2018-07-13T00:00:00Z"
|
||||
published: true
|
||||
title: HTTP/2 Smarter At Scale
|
||||
url: blog/http2_smarter_at_scale
|
||||
date: 2018-07-13
|
||||
---
|
||||
|
||||
Much of the web today runs on HTTP/1.1. The spec for HTTP/1.1 was published in June of 1999, just shy of 20 years ago. A lot has changed since then, which makes it all the more remarkable that HTTP/1.1 has persisted and flourished for so long. But in some areas it’s beginning to show its age; for the most part, in that the designers weren’t building for the scale at which HTTP/1.1 would be used and the astonishing amount of traffic that it would come to handle. A not-so-bad case is that subsequent tests can't pass because of a leaked resource from the previous test. The worst case is that some subsequent tests pass that wouldn't have passed at all if the previously passed test had not leaked a resource.
|
||||
|
||||
<!--more-->
|
||||
|
||||
HTTP/2, whose specification was published in May of 2015, seeks to address some of the scalability concerns of its predecessor while still providing a similar experience to users. HTTP/2 improves upon HTTP/1.1’s design in a number of ways, perhaps most significantly in providing a semantic mapping over connections. In this post we’ll explore the concept of streams and how they can be of substantial benefit to software engineers.
|
||||
|
|
@ -20,7 +19,7 @@ There’s significant overhead to creating HTTP connections. You must establish
|
|||
|
||||
HTTP/2 takes the concept of persistent connections further by providing a semantic layer above connections: streams. Streams can be thought of as a series of semantically connected messages, called frames. A stream may be short-lived, such as a unary stream that requests the status of a user (in HTTP/1.1, this might equate to `GET /users/1234/status`). With increasing frequency it’s long-lived. To use the last example, instead of making individual requests to the /users/1234/status endpoint, a receiver might establish a long-lived stream and thereby continuously receive user status messages in real time.
|
||||
|
||||
<img src="/img/conn_stream_frame_mapping.png" alt="Kotlin Android app example" style="max-width: 800px">
|
||||

|
||||
|
||||
## Streams Provide Concurrency
|
||||
|
||||
|
|
@ -30,13 +29,13 @@ To illustrate this point, consider the case of some service A sending HTTP/1.1 r
|
|||
|
||||
In some snapshot in time, service A has a single idle connection to service B and wants to use it to send some data. Service A wants to send a product order (request 1), a profile update (request 2), and two “new user” requests (requests 3 and 4). Since the product order arrives first, it dominates the single idle connection. The latter three smaller requests must either wait for the large product order to be sent, or some number of new HTTP/1.1 connection must be spun up for the small requests.
|
||||
|
||||
<img src="/img/http2_queue_3.png" alt="Kotlin Android app example" style="max-width: 800px">
|
||||

|
||||
|
||||
Meanwhile, with HTTP/2, streaming allows messages to be sent concurrently on the same connection. Let’s imagine that service A creates a connection to service B with three streams: a “new users” stream, a “profile updates” stream, and a “product order” stream. Now, the latter requests don’t have to wait for the first-to-arrive large product order request; all requests are sent concurrently.
|
||||
|
||||
Concurrency does not mean parallelism, though; we can only send one packet at a time on the connection. So, the sender might round robin sending packets between streams (see below). Alternatively, senders might prioritize certain streams over others; perhaps getting new users signed up is more important to the service!
|
||||
|
||||
<img src="/img/http2_round_robin.png" alt="Kotlin Android app example" style="max-width: 800px">
|
||||

|
||||
|
||||
## Flow Control
|
||||
|
||||
|
|
@ -1,20 +1,19 @@
|
|||
---
|
||||
title: gRPC - now with easy installation
|
||||
attribution: Originally written by Lisa Carey with help from others at Google.
|
||||
date: "2016-04-04T00:00:00Z"
|
||||
title: gRPC - now with easy installation.
|
||||
url: blog/installation
|
||||
date: 2016-04-04
|
||||
---
|
||||
|
||||
Today we are happy to provide an update that significantly simplifies the getting started experience for gRPC.
|
||||
|
||||
* For most languages, **the gRPC runtime can now be installed in a single step via native package managers** such as `npm` for Node.js, `gem` for Ruby and `pip` for Python. Even though our Node, Ruby and Python runtimes are wrapped on gRPC's C core, users now don't need to explicitly pre-install the C core library as a package in most Linux distributions. We autofetch it for you :-).
|
||||
|
||||
* **For Java, we have simplified the steps needed to add gRPC support to your build tools** by providing plugins for Maven and Gradle. These let you easily depend on the core runtime to deploy or ship generated libraries into production environments.
|
||||
|
||||
* You can also use our Dockerfiles to use these updated packages - deploying microservices built on gRPC should now be a very simple experience.
|
||||
|
||||
<!--more-->
|
||||
|
||||
* For most languages, **the gRPC runtime can now be installed in a single step via native package managers** such as `npm` for Node.js, `gem` for Ruby and `pip` for Python. Even though our Node, Ruby and Python runtimes are wrapped on gRPC's C core, users now don't need to explicitly pre-install the C core library as a package in most Linux distributions. We autofetch it for you :-).
|
||||
|
||||
* **For Java, we have simplified the steps needed to add gRPC support to your build tools** by providing plugins for Maven and Gradle. These let you easily depend on the core runtime to deploy or ship generated libraries into production environments.
|
||||
|
||||
* You can also use our Dockerfiles to use these updated packages - deploying microservices built on gRPC should now be a very simple experience.
|
||||
|
||||
The installation story is not yet complete: we are now focused on improving your development experience by packaging our protocol buffer plugins in the same way as the gRPC runtime. This will simplify code generation and setting up your development environment.
|
||||
|
||||
### Want to try it?
|
||||
|
|
@ -1,16 +1,16 @@
|
|||
---
|
||||
title: gRPC ❤ Kotlin
|
||||
author: Spencer Fang
|
||||
author-link: https://github.com/zpencer
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2018-06-19T00:00:00Z"
|
||||
published: true
|
||||
title: gRPC ❤ Kotlin
|
||||
url: blog/kotlin-gradle-projects
|
||||
date: 2018-06-19
|
||||
---
|
||||
|
||||
Did you know that gRPC Java now has out of box support for Kotlin projects built with Gradle? [Kotlin](https://kotlinlang.org/) is a modern, statically typed language developed by JetBrains that targets the JVM and Android. It is generally easy for Kotlin programs to interoperate with existing Java libraries. To improve this experience further, we have added support to the [protobuf-gradle-plugin](https://github.com/google/protobuf-gradle-plugin/releases) so that the generated Java libraries are automatically picked up by Kotlin. You can now add the protobuf-gradle-plugin to your Kotlin project, and use gRPC just like you would with a typical Java project.
|
||||
|
||||
<!--more-->
|
||||
|
||||
The following examples show you how to configure a project for a JVM application and an Android application using Kotlin.
|
||||
|
||||
### Kotlin gRPC client and server
|
||||
|
|
@ -20,6 +20,7 @@ The full example can be found [here](https://github.com/grpc/grpc-java/tree/mast
|
|||
Configuring gRPC for a Kotlin project is the same as configuring it for a Java project.
|
||||
|
||||
Below is a snippet of the example project's `build.gradle` highlighting some Kotlin related sections:
|
||||
|
||||
```groovy
|
||||
apply plugin: 'kotlin'
|
||||
apply plugin: 'com.google.protobuf'
|
||||
|
|
@ -127,6 +128,6 @@ Just like the non-Android project, run `./gradlew generateProto generateProto` t
|
|||
|
||||
Finally, test out the Android app by opening the project in Android Studio and selecting `Run > Run 'app'`.
|
||||
|
||||
<img src="/img/kotlin-project-android-app.png" alt="Kotlin Android app example" style="max-width: 404px">
|
||||

|
||||
|
||||
We are excited about improving the gRPC experience for Kotlin developers. Please add enhancement ideas or bugs to the [protobuf-gradle-plugin issue tracker](https://github.com/google/protobuf-gradle-plugin/issues) or the [grpc-java issue tracker](https://github.com/grpc/grpc-java/issues).
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
---
|
||||
title: The gRPC Meetup Kit
|
||||
date: 2017-09-14
|
||||
attribution: Mark Mandel, Sandeep Dinesh
|
||||
---
|
||||
|
||||
If you have ever wanted to run an event around [gRPC](/), but didn't know where to start, or weren't sure what content is available - we have released the [gRPC Meetup Kit](https://github.com/grpc-ecosystem/meetup-kit)!
|
||||
|
||||
The meetup kit includes a 15 minute presentation on the basic concepts of gRPC, with accompanying [slides](https://docs.google.com/presentation/d/1dgI09a-_4dwBMLyqfwchvS6iXtbcISQPLAXL6gSYOcc/edit?usp=sharing) and [video](https://www.youtube.com/watch?v=UVsIfSfS6I4) for either reference or playback, as well as a [45-minute codelab](https://codelabs.developers.google.com/codelabs/cloud-grpc/index.html) that takes you through the basics of gRPC in [Node.js](https://nodejs.org) and [Go](https://golang.org). At the end of the codelab participants will have a solid understanding of the fundamentals of gRPC.
|
||||
|
||||
If you are thinking about running a gRPC event, make sure to contact us to receive [gRPC stickers](https://goo.gl/forms/C3TCtFdobz4ippty2) and/or organise [office hours over Hangouts with the gRPC team](https://goo.gl/forms/pvxNwWExr5ApbNst2)!
|
||||
|
|
@ -1,28 +1,25 @@
|
|||
---
|
||||
title: Mobile Benchmarks
|
||||
attribution: Originally written by David Cao with additional content by Makarand and
|
||||
others at Google.
|
||||
author: David Cao
|
||||
company: Google
|
||||
company-link: https://cloud.google.com
|
||||
date: "2016-07-26T00:00:00Z"
|
||||
published: false
|
||||
date: 2016-07-26
|
||||
thumbnail: ../img/gcp-icon.png?raw=true
|
||||
title: Mobile Benchmarks
|
||||
url: blog/mobile-benchmarks
|
||||
---
|
||||
|
||||
As gRPC has become a better and faster RPC framework, we've consistently gotten the question, "How _much_ faster is gRPC?" We already have comprehensive server-side benchmarks, but we don't have mobile benchmarks. Benchmarking a client is a bit different than benchmarking a server. We care more about things such as latency and request size and less about things like queries per second (QPS) and number of concurrent threads. Thus we built an Android app in order to quantify these factors and provide solid numbers behind them.
|
||||
|
||||
Specifically what we want to benchmark is client side protobuf vs. JSON serialization/deserialization and gRPC vs. a RESTful HTTP JSON service. For the serialization benchmarks, we want to measure the size of messages and speed at which we serialize and deserialize. For the RPC benchmarks, we want to measure the latency of end-to-end requests and packet size.
|
||||
|
||||
|
||||
Protobuf vs. JSON
|
||||
## Protobuf vs. JSON
|
||||
|
||||
In order to benchmark protobuf and JSON, we ran serializations and deserializations over and over on randomly generated protos, which can be seen [here](https://github.com/david-cao/gRPCBenchmarks/tree/master/protolite_app/app/src/main/proto). These protos varied quite a bit in size and complexity, from just a few bytes to over 100kb. JSON equivalents were created and then also benchmarked. For the protobuf messages, we had three main methods of serializing and deserializing: simply using a byte array, `CodedOutputStream`/`CodedInputStream` which is protobuf's own implementation of input and output streams, and Java's `ByteArrayOutputStream` and `ByteArrayInputStream`. For JSON we used `org.json`'s [`JSONObject`](https://developer.android.com/reference/org/json/JSONObject.html). This only had one method to serialize and deserialize, `toString()` and `new JSONObject()`, respectively.
|
||||
|
||||
In order to keep benchmarks as accurate as possible, we wrapped the code to be benchmarked in an interface and simply looped it for a set number of iterations. This way we discounted any time spent checking the system time.
|
||||
|
||||
``` Java
|
||||
```java
|
||||
interface Action {
|
||||
void execute();
|
||||
}
|
||||
|
|
@ -39,6 +36,7 @@ for (int i = 0; i < 100; ++i) {
|
|||
a.execute();
|
||||
}
|
||||
```
|
||||
|
||||
Before running a benchmark, we ran a warmup in order to clean out any erratic behaviour by the JVM, and then calculated the number of iterations needed to run for a set time (10 seconds in the protobuf vs. JSON case). To do this, we started with 1 iteration, measured the time it took for that run, and compared it to a minimum sample time (2 seconds in our case). If the number of iterations took long enough, we estimated the number of iterations needed to run for 10 seconds by doing some math. Otherwise, we multiplied the number of iterations by 2 and repeated.
|
||||
|
||||
```Java
|
||||
|
|
@ -54,22 +52,19 @@ while (elapsed < MIN_SAMPLE_TIME_MS) {
|
|||
iterations = (int) ((TARGET_TIME_MS / (double) elapsed) * iterations);
|
||||
```
|
||||
|
||||
Results
|
||||
## Results
|
||||
|
||||
Benchmarks were run on protobuf, JSON, and gzipped JSON.
|
||||
|
||||
We found that regardless of the serialization/deserialization method used for protobuf, it was consistently about 3x faster for serializing than JSON. For deserialization, JSON is actually a bit faster for small messages (<1kb), around 1.5x, but for larger messages (>15kb) protobuf is 2x faster. For gzipped JSON, protobuf is well over 5x faster in serialization, regardless of size. For deserialization, both are about the same at small messages, but protobuf is about 3x faster for larger messages. Results can be explored in more depth and replicated [here](/github_readme).
|
||||
|
||||
|
||||
gRPC vs. HTTP JSON
|
||||
We found that regardless of the serialization/deserialization method used for protobuf, it was consistently about 3x faster for serializing than JSON. For deserialization, JSON is actually a bit faster for small messages (<1kb), around 1.5x, but for larger messages (>15kb) protobuf is 2x faster. For gzipped JSON, protobuf is well over 5x faster in serialization, regardless of size. For deserialization, both are about the same at small messages, but protobuf is about 3x faster for larger messages. Results can be explored in more depth and replicated [in the README](https://github.com/david-cao/gRPCBenchmarks).
|
||||
|
||||
## gRPC vs. HTTP JSON
|
||||
|
||||
To benchmark RPC calls, we want to measure end-to-end latency and bandwidth. To do this, we ping pong with a server for 60 seconds, using the same message each time, and measure the latency and message size. The message consists of some fields for the server to read, and a payload of bytes. We compared gRPC's unary call to a simple RESTful HTTP JSON service. The gRPC benchmark creates a channel, and starts a unary call that repeats when it recieves a response until 60 seconds have passed. The response contains a proto with the same payload sent.
|
||||
|
||||
Similarly for the HTTP JSON benchmarks, it sends a POST request to the server with an equivalent JSON object, and the server sends back a JSON object with the same payload.
|
||||
|
||||
```Java
|
||||
|
||||
```java
|
||||
// This can be found in AsyncClient.java doUnaryCalls()
|
||||
// Make stub to send unary call
|
||||
final BenchmarkServiceStub stub = BenchmarkServiceGrpc.newStub(channel);
|
||||
|
|
@ -109,11 +104,11 @@ stub.unaryCall(request, new StreamObserver<SimpleResponse>() {
|
|||
}
|
||||
});
|
||||
```
|
||||
|
||||
Both `HttpUrlConnection` and the [OkHttp library](https://square.github.io/okhttp/) were used.
|
||||
|
||||
Only gRPC's unary calls were benchmarked against HTTP, since streaming calls were over 2x faster than the unary calls. Moreover, HTTP has no equivalent of streaming, which is an HTTP/2 specific feature.
|
||||
|
||||
## Results
|
||||
|
||||
Results
|
||||
|
||||
In terms of latency, gRPC is **5x-10x** faster up to the 95th percentile, with averages of around 2 milliseconds for an end-to-end request. For bandwidth, gRPC is about 3x faster for small requests (100-1000 byte payload), and consistently 2x faster for large requests (10kb-100kb payload). To replicate these results or explore in more depth, check out our [repository](/github_readme).
|
||||
In terms of latency, gRPC is **5x-10x** faster up to the 95th percentile, with averages of around 2 milliseconds for an end-to-end request. For bandwidth, gRPC is about 3x faster for small requests (100-1000 byte payload), and consistently 2x faster for large requests (10kb-100kb payload). To replicate these results or explore in more depth, check out our [repository](https://github.com/david-cao/gRPCBenchmarks).
|
||||
|
|
@ -1,12 +1,10 @@
|
|||
---
|
||||
title: So You Want to Optimize gRPC - Part 1
|
||||
author: Carl Mastrangelo
|
||||
author-link: https://github.com/carl-mastrangelo
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2018-03-06T00:00:00Z"
|
||||
published: true
|
||||
title: So You Want to Optimize gRPC - Part 1
|
||||
url: blog/optimizing-grpc-part-1
|
||||
date: 2018-03-06
|
||||
---
|
||||
|
||||
A common question with gRPC is how to make it fast. The gRPC library offers users access to high
|
||||
|
|
@ -61,26 +59,26 @@ As mentioned above, the client makes random RPCs. For example, here is the code
|
|||
request:
|
||||
|
||||
```java
|
||||
private void doCreate(KeyValueServiceBlockingStub stub) {
|
||||
ByteString key = createRandomKey();
|
||||
try {
|
||||
CreateResponse res = stub.create(
|
||||
CreateRequest.newBuilder()
|
||||
.setKey(key)
|
||||
.setValue(randomBytes(MEAN_VALUE_SIZE))
|
||||
.build());
|
||||
if (!res.equals(CreateResponse.getDefaultInstance())) {
|
||||
throw new RuntimeException("Invalid response");
|
||||
}
|
||||
} catch (StatusRuntimeException e) {
|
||||
if (e.getStatus().getCode() == Code.ALREADY_EXISTS) {
|
||||
knownKeys.remove(key);
|
||||
logger.log(Level.INFO, "Key already existed", e);
|
||||
} else {
|
||||
throw e;
|
||||
}
|
||||
private void doCreate(KeyValueServiceBlockingStub stub) {
|
||||
ByteString key = createRandomKey();
|
||||
try {
|
||||
CreateResponse res = stub.create(
|
||||
CreateRequest.newBuilder()
|
||||
.setKey(key)
|
||||
.setValue(randomBytes(MEAN_VALUE_SIZE))
|
||||
.build());
|
||||
if (!res.equals(CreateResponse.getDefaultInstance())) {
|
||||
throw new RuntimeException("Invalid response");
|
||||
}
|
||||
} catch (StatusRuntimeException e) {
|
||||
if (e.getStatus().getCode() == Code.ALREADY_EXISTS) {
|
||||
knownKeys.remove(key);
|
||||
logger.log(Level.INFO, "Key already existed", e);
|
||||
} else {
|
||||
throw e;
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
A random key is created, along with a random value. The request is sent to the server, and the
|
||||
|
|
@ -101,21 +99,21 @@ On the server side, the request is received by the
|
|||
[service handler](https://github.com/carl-mastrangelo/kvstore/blob/f422b1b6e7c69f8c07f96ed4ddba64757242352c/src/main/java/io/grpc/examples/KvService.java#L34):
|
||||
|
||||
```java
|
||||
private final Map<ByteBuffer, ByteBuffer> store = new HashMap<>();
|
||||
private final Map<ByteBuffer, ByteBuffer> store = new HashMap<>();
|
||||
|
||||
@Override
|
||||
public synchronized void create(
|
||||
CreateRequest request, StreamObserver<CreateResponse> responseObserver) {
|
||||
ByteBuffer key = request.getKey().asReadOnlyByteBuffer();
|
||||
ByteBuffer value = request.getValue().asReadOnlyByteBuffer();
|
||||
simulateWork(WRITE_DELAY_MILLIS);
|
||||
if (store.putIfAbsent(key, value) == null) {
|
||||
responseObserver.onNext(CreateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
return;
|
||||
}
|
||||
responseObserver.onError(Status.ALREADY_EXISTS.asRuntimeException());
|
||||
@Override
|
||||
public synchronized void create(
|
||||
CreateRequest request, StreamObserver<CreateResponse> responseObserver) {
|
||||
ByteBuffer key = request.getKey().asReadOnlyByteBuffer();
|
||||
ByteBuffer value = request.getValue().asReadOnlyByteBuffer();
|
||||
simulateWork(WRITE_DELAY_MILLIS);
|
||||
if (store.putIfAbsent(key, value) == null) {
|
||||
responseObserver.onNext(CreateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
return;
|
||||
}
|
||||
responseObserver.onError(Status.ALREADY_EXISTS.asRuntimeException());
|
||||
}
|
||||
```
|
||||
|
||||
The service extracts the key and value as `ByteBuffer`s from the request. It acquires the lock
|
||||
|
|
@ -164,21 +162,21 @@ decides](https://github.com/carl-mastrangelo/kvstore/blob/f422b1b6e7c69f8c07f96e
|
|||
what operation to do:
|
||||
|
||||
```java
|
||||
void doClientWork(AtomicBoolean done) {
|
||||
Random random = new Random();
|
||||
KeyValueServiceBlockingStub stub = KeyValueServiceGrpc.newBlockingStub(channel);
|
||||
void doClientWork(AtomicBoolean done) {
|
||||
Random random = new Random();
|
||||
KeyValueServiceBlockingStub stub = KeyValueServiceGrpc.newBlockingStub(channel);
|
||||
|
||||
while (!done.get()) {
|
||||
// Pick a random CRUD action to take.
|
||||
int command = random.nextInt(4);
|
||||
if (command == 0) {
|
||||
doCreate(stub);
|
||||
continue;
|
||||
}
|
||||
/* ... */
|
||||
rpcCount++;
|
||||
while (!done.get()) {
|
||||
// Pick a random CRUD action to take.
|
||||
int command = random.nextInt(4);
|
||||
if (command == 0) {
|
||||
doCreate(stub);
|
||||
continue;
|
||||
}
|
||||
/* ... */
|
||||
rpcCount++;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
This means that **at most one RPC can be active at any time**. Each RPC has to wait for the
|
||||
|
|
@ -192,7 +190,7 @@ Our code can do about 16 queries in a second, so that seems about right. We can
|
|||
assumption by looking at the output of the `time` command used to run the code. The server goes
|
||||
to sleep when running queries in the
|
||||
[`simulateWork`](https://github.com/carl-mastrangelo/kvstore/blob/f422b1b6e7c69f8c07f96ed4ddba64757242352c/src/main/java/io/grpc/examples/KvService.java#L88)
|
||||
method. This implies that the program should be mostly idle while waiting for the RPCs to
|
||||
method. This implies that the program should be mostly idle while waiting for the RPCs to
|
||||
complete.
|
||||
|
||||
We can confirm this is the case by looking at the `real` and `user` times of the command above.
|
||||
|
|
@ -228,39 +226,39 @@ is still roughly from top to bottom in the function. Here is the
|
|||
method revised:
|
||||
|
||||
```java
|
||||
private void doCreate(KeyValueServiceFutureStub stub, AtomicReference<Throwable> error) {
|
||||
ByteString key = createRandomKey();
|
||||
ListenableFuture<CreateResponse> res = stub.create(
|
||||
CreateRequest.newBuilder()
|
||||
.setKey(key)
|
||||
.setValue(randomBytes(MEAN_VALUE_SIZE))
|
||||
.build());
|
||||
res.addListener(() -> rpcCount.incrementAndGet(), MoreExecutors.directExecutor());
|
||||
Futures.addCallback(res, new FutureCallback<CreateResponse>() {
|
||||
@Override
|
||||
public void onSuccess(CreateResponse result) {
|
||||
if (!result.equals(CreateResponse.getDefaultInstance())) {
|
||||
error.compareAndSet(null, new RuntimeException("Invalid response"));
|
||||
}
|
||||
synchronized (knownKeys) {
|
||||
knownKeys.add(key);
|
||||
}
|
||||
private void doCreate(KeyValueServiceFutureStub stub, AtomicReference<Throwable> error) {
|
||||
ByteString key = createRandomKey();
|
||||
ListenableFuture<CreateResponse> res = stub.create(
|
||||
CreateRequest.newBuilder()
|
||||
.setKey(key)
|
||||
.setValue(randomBytes(MEAN_VALUE_SIZE))
|
||||
.build());
|
||||
res.addListener(() -> rpcCount.incrementAndGet(), MoreExecutors.directExecutor());
|
||||
Futures.addCallback(res, new FutureCallback<CreateResponse>() {
|
||||
@Override
|
||||
public void onSuccess(CreateResponse result) {
|
||||
if (!result.equals(CreateResponse.getDefaultInstance())) {
|
||||
error.compareAndSet(null, new RuntimeException("Invalid response"));
|
||||
}
|
||||
synchronized (knownKeys) {
|
||||
knownKeys.add(key);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailure(Throwable t) {
|
||||
Status status = Status.fromThrowable(t);
|
||||
if (status.getCode() == Code.ALREADY_EXISTS) {
|
||||
synchronized (knownKeys) {
|
||||
knownKeys.remove(key);
|
||||
}
|
||||
logger.log(Level.INFO, "Key already existed", t);
|
||||
} else {
|
||||
error.compareAndSet(null, t);
|
||||
@Override
|
||||
public void onFailure(Throwable t) {
|
||||
Status status = Status.fromThrowable(t);
|
||||
if (status.getCode() == Code.ALREADY_EXISTS) {
|
||||
synchronized (knownKeys) {
|
||||
knownKeys.remove(key);
|
||||
}
|
||||
logger.log(Level.INFO, "Key already existed", t);
|
||||
} else {
|
||||
error.compareAndSet(null, t);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
```
|
||||
|
||||
The stub has been modified to be a `KeyValueServiceFutureStub`, which produces a `Future` when
|
||||
|
|
@ -323,23 +321,23 @@ permit. To [accomplish](https://github.com/carl-mastrangelo/kvstore/blob/02-fut
|
|||
this, we will using a `Semaphore`:
|
||||
|
||||
```java
|
||||
private final Semaphore limiter = new Semaphore(100);
|
||||
private final Semaphore limiter = new Semaphore(100);
|
||||
|
||||
private void doCreate(KeyValueServiceFutureStub stub, AtomicReference<Throwable> error)
|
||||
throws InterruptedException {
|
||||
limiter.acquire();
|
||||
ByteString key = createRandomKey();
|
||||
ListenableFuture<CreateResponse> res = stub.create(
|
||||
CreateRequest.newBuilder()
|
||||
.setKey(key)
|
||||
.setValue(randomBytes(MEAN_VALUE_SIZE))
|
||||
.build());
|
||||
res.addListener(() -> {
|
||||
rpcCount.incrementAndGet();
|
||||
limiter.release();
|
||||
}, MoreExecutors.directExecutor());
|
||||
/* ... */
|
||||
}
|
||||
private void doCreate(KeyValueServiceFutureStub stub, AtomicReference<Throwable> error)
|
||||
throws InterruptedException {
|
||||
limiter.acquire();
|
||||
ByteString key = createRandomKey();
|
||||
ListenableFuture<CreateResponse> res = stub.create(
|
||||
CreateRequest.newBuilder()
|
||||
.setKey(key)
|
||||
.setValue(randomBytes(MEAN_VALUE_SIZE))
|
||||
.build());
|
||||
res.addListener(() -> {
|
||||
rpcCount.incrementAndGet();
|
||||
limiter.release();
|
||||
}, MoreExecutors.directExecutor());
|
||||
/* ... */
|
||||
}
|
||||
```
|
||||
|
||||
Now the code runs successfully, and doesn't run out of memory.
|
||||
|
|
@ -396,4 +394,3 @@ the very basics of how to approach and think about optimization. Always make su
|
|||
before and after your changes, and use these measurements to guide your optimizations.
|
||||
|
||||
In [Part 2](/blog/optimizing-grpc-part-2), we will continue optimizing the server part of the code.
|
||||
|
||||
|
|
@ -1,12 +1,10 @@
|
|||
---
|
||||
title: So You Want to Optimize gRPC - Part 2
|
||||
author: Carl Mastrangelo
|
||||
author-link: https://carlmastrangelo.com/
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2018-04-16T00:00:00Z"
|
||||
published: true
|
||||
title: So You Want to Optimize gRPC - Part 2
|
||||
url: blog/optimizing-grpc-part-2
|
||||
date: 2018-04-16
|
||||
---
|
||||
|
||||
How fast is gRPC? Pretty fast if you understand how modern clients and servers are built. In
|
||||
|
|
@ -32,21 +30,21 @@ accidentally corrupt the state of storage. To ensure this, the service uses the
|
|||
keyword to ensure only one RPC is active at a time:
|
||||
|
||||
```java
|
||||
private final Map<ByteBuffer, ByteBuffer> store = new HashMap<>();
|
||||
private final Map<ByteBuffer, ByteBuffer> store = new HashMap<>();
|
||||
|
||||
@Override
|
||||
public synchronized void create(
|
||||
CreateRequest request, StreamObserver<CreateResponse> responseObserver) {
|
||||
ByteBuffer key = request.getKey().asReadOnlyByteBuffer();
|
||||
ByteBuffer value = request.getValue().asReadOnlyByteBuffer();
|
||||
simulateWork(WRITE_DELAY_MILLIS);
|
||||
if (store.putIfAbsent(key, value) == null) {
|
||||
responseObserver.onNext(CreateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
return;
|
||||
}
|
||||
responseObserver.onError(Status.ALREADY_EXISTS.asRuntimeException());
|
||||
@Override
|
||||
public synchronized void create(
|
||||
CreateRequest request, StreamObserver<CreateResponse> responseObserver) {
|
||||
ByteBuffer key = request.getKey().asReadOnlyByteBuffer();
|
||||
ByteBuffer value = request.getValue().asReadOnlyByteBuffer();
|
||||
simulateWork(WRITE_DELAY_MILLIS);
|
||||
if (store.putIfAbsent(key, value) == null) {
|
||||
responseObserver.onNext(CreateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
return;
|
||||
}
|
||||
responseObserver.onError(Status.ALREADY_EXISTS.asRuntimeException());
|
||||
}
|
||||
```
|
||||
|
||||
While this code is thread safe, it comes at a high price: only one RPC can ever be active! We
|
||||
|
|
@ -81,21 +79,21 @@ Concurrent maps provide stronger guarantees about the safety of `putIfAbsent`, s
|
|||
`HashMap` to a `ConcurrentHashMap` and remove `synchronized`:
|
||||
|
||||
```java
|
||||
private final ConcurrentMap<ByteBuffer, ByteBuffer> store = new ConcurrentHashMap<>();
|
||||
|
||||
@Override
|
||||
public void create(
|
||||
CreateRequest request, StreamObserver<CreateResponse> responseObserver) {
|
||||
ByteBuffer key = request.getKey().asReadOnlyByteBuffer();
|
||||
ByteBuffer value = request.getValue().asReadOnlyByteBuffer();
|
||||
simulateWork(WRITE_DELAY_MILLIS);
|
||||
if (store.putIfAbsent(key, value) == null) {
|
||||
responseObserver.onNext(CreateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
return;
|
||||
}
|
||||
responseObserver.onError(Status.ALREADY_EXISTS.asRuntimeException());
|
||||
private final ConcurrentMap<ByteBuffer, ByteBuffer> store = new ConcurrentHashMap<>();
|
||||
|
||||
@Override
|
||||
public void create(
|
||||
CreateRequest request, StreamObserver<CreateResponse> responseObserver) {
|
||||
ByteBuffer key = request.getKey().asReadOnlyByteBuffer();
|
||||
ByteBuffer value = request.getValue().asReadOnlyByteBuffer();
|
||||
simulateWork(WRITE_DELAY_MILLIS);
|
||||
if (store.putIfAbsent(key, value) == null) {
|
||||
responseObserver.onNext(CreateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
return;
|
||||
}
|
||||
responseObserver.onError(Status.ALREADY_EXISTS.asRuntimeException());
|
||||
}
|
||||
```
|
||||
|
||||
### If at First You Don't Succeed
|
||||
|
|
@ -104,21 +102,21 @@ Updating `create` was pretty easy. Doing the same for `retrieve` and `delete` i
|
|||
However, the `update` method is a little trickier. Let's take a look at what it's doing:
|
||||
|
||||
```java
|
||||
@Override
|
||||
public synchronized void update(
|
||||
UpdateRequest request, StreamObserver<UpdateResponse> responseObserver) {
|
||||
ByteBuffer key = request.getKey().asReadOnlyByteBuffer();
|
||||
ByteBuffer newValue = request.getValue().asReadOnlyByteBuffer();
|
||||
simulateWork(WRITE_DELAY_MILLIS);
|
||||
ByteBuffer oldValue = store.get(key);
|
||||
if (oldValue == null) {
|
||||
responseObserver.onError(Status.NOT_FOUND.asRuntimeException());
|
||||
return;
|
||||
}
|
||||
store.replace(key, oldValue, newValue);
|
||||
responseObserver.onNext(UpdateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
@Override
|
||||
public synchronized void update(
|
||||
UpdateRequest request, StreamObserver<UpdateResponse> responseObserver) {
|
||||
ByteBuffer key = request.getKey().asReadOnlyByteBuffer();
|
||||
ByteBuffer newValue = request.getValue().asReadOnlyByteBuffer();
|
||||
simulateWork(WRITE_DELAY_MILLIS);
|
||||
ByteBuffer oldValue = store.get(key);
|
||||
if (oldValue == null) {
|
||||
responseObserver.onError(Status.NOT_FOUND.asRuntimeException());
|
||||
return;
|
||||
}
|
||||
store.replace(key, oldValue, newValue);
|
||||
responseObserver.onNext(UpdateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
}
|
||||
```
|
||||
|
||||
Updating a key to a new value needs two interactions with the `store`:
|
||||
|
|
@ -135,21 +133,21 @@ was successful. (`ConcurrentMap` asserts that the operations will not corrupt t
|
|||
structure, but doesn't say that they will succeed!) We will use a do-while loop:
|
||||
|
||||
```java
|
||||
@Override
|
||||
public void update(
|
||||
UpdateRequest request, StreamObserver<UpdateResponse> responseObserver) {
|
||||
// ...
|
||||
ByteBuffer oldValue;
|
||||
do {
|
||||
oldValue = store.get(key);
|
||||
if (oldValue == null) {
|
||||
responseObserver.onError(Status.NOT_FOUND.asRuntimeException());
|
||||
return;
|
||||
}
|
||||
} while (!store.replace(key, oldValue, newValue));
|
||||
responseObserver.onNext(UpdateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
}
|
||||
@Override
|
||||
public void update(
|
||||
UpdateRequest request, StreamObserver<UpdateResponse> responseObserver) {
|
||||
// ...
|
||||
ByteBuffer oldValue;
|
||||
do {
|
||||
oldValue = store.get(key);
|
||||
if (oldValue == null) {
|
||||
responseObserver.onError(Status.NOT_FOUND.asRuntimeException());
|
||||
return;
|
||||
}
|
||||
} while (!store.replace(key, oldValue, newValue));
|
||||
responseObserver.onNext(UpdateResponse.getDefaultInstance());
|
||||
responseObserver.onCompleted();
|
||||
}
|
||||
```
|
||||
|
||||
The code wants to fail if it ever sees null, but never if there is a non-null previous value. One
|
||||
|
|
@ -229,4 +227,3 @@ need to understand what your code is doing. This post shows how to convert a lo
|
|||
a low-contention, lock-free service. Always make sure to measure before and after your changes.
|
||||
|
||||
In Part 3, we will optimize the code even further. 2,400 RPC/s is just the beginning!
|
||||
|
||||
|
|
@ -0,0 +1,77 @@
|
|||
---
|
||||
title: gRPC Motivation and Design Principles
|
||||
date: 2015-09-08
|
||||
attribution: Originally written by Louis Ryan with help from others at Google
|
||||
---
|
||||
|
||||
## Motivation
|
||||
|
||||
Google has been using a single general-purpose RPC infrastructure called Stubby to connect the large number of microservices running within and across our data centers for over a decade. Our internal systems have long embraced the microservice architecture gaining popularity today. Having a uniform, cross-platform RPC infrastructure has allowed for the rollout of fleet-wide improvements in efficiency, security, reliability and behavioral analysis critical to supporting the incredible growth seen in that period.
|
||||
|
||||
Stubby has many great features - however, it's not based on any standard and is too tightly coupled to our internal infrastructure to be considered suitable for public release. With the advent of SPDY, HTTP/2, and QUIC, many of these same features have appeared in public standards, together with other features that Stubby does not provide. It became clear that it was time to rework Stubby to take advantage of this standardization, and to extend its applicability to mobile, IoT, and Cloud use-cases.</p>
|
||||
|
||||
## Principles & Requirements
|
||||
|
||||
### Services not Objects, Messages not References
|
||||
|
||||
Promote the microservices design philosophy of coarse-grained message exchange between systems while avoiding the [pitfalls of distributed objects](https://martinfowler.com/articles/distributed-objects-microservices.html) and the [fallacies of ignoring the network](https://en.wikipedia.org/wiki/Fallacies_of_distributed_computing).
|
||||
|
||||
### Coverage & Simplicity
|
||||
|
||||
The stack should be available on every popular development platform and easy for someone to build for their platform of choice. It should be viable on CPU and memory-limited devices.
|
||||
|
||||
### Free & Open
|
||||
|
||||
Make the fundamental features free for all to use. Release all artifacts as open-source efforts with licensing that should facilitate and not impede adoption.
|
||||
|
||||
### Interoperability & Reach
|
||||
|
||||
The wire protocol must be capable of surviving traversal over common internet infrastructure.
|
||||
|
||||
### General Purpose & Performant
|
||||
|
||||
The stack should be applicable to a broad class of use-cases while sacrificing little in performance when compared to a use-case specific stack.
|
||||
|
||||
### Layered
|
||||
|
||||
Key facets of the stack must be able to evolve independently. A revision to the wire-format should not disrupt application layer bindings.
|
||||
|
||||
### Payload Agnostic
|
||||
|
||||
Different services need to use different message types and encodings such as protocol buffers, JSON, XML, and Thrift; the protocol and implementations must allow for this. Similarly the need for payload compression varies by use-case and payload type: the protocol should allow for pluggable compression mechanisms.
|
||||
|
||||
### Streaming
|
||||
|
||||
Storage systems rely on streaming and flow-control to express large data-sets. Other services, like voice-to-text or stock-tickers, rely on streaming to represent temporally related message sequences.
|
||||
|
||||
### Blocking & Non-Blocking
|
||||
|
||||
Support both asynchronous and synchronous processing of the sequence of messages exchanged by a client and server. This is critical for scaling and handling streams on certain platforms.
|
||||
|
||||
### Cancellation & Timeout
|
||||
|
||||
Operations can be expensive and long-lived - cancellation allows servers to reclaim resources when clients are well-behaved. When a causal-chain of work is tracked, cancellation can cascade. A client may indicate a timeout for a call, which allows services to tune their behavior to the needs of the client.
|
||||
|
||||
### Lameducking
|
||||
|
||||
Servers must be allowed to gracefully shut-down by rejecting new requests while continuing to process in-flight ones.
|
||||
|
||||
### Flow Control
|
||||
|
||||
Computing power and network capacity are often unbalanced between client ands server. Flow control allows for better buffer management as well as providing protection from DOS by an overly active peer.
|
||||
|
||||
### Pluggable
|
||||
|
||||
A wire protocol is only part of a functioning API infrastructure. Large distributed systems need security, health-checking, load-balancing and failover, monitoring, tracing, logging, and so on. Implementations should provide extensions points to allow for plugging in these features and, where useful, default implementations.
|
||||
|
||||
### Extensions as APIs
|
||||
|
||||
Extensions that require collaboration among services should favor using APIs rather than protocol extensions where possible. Extensions of this type could include health-checking, service introspection, load monitoring, and load-balancing assignment.
|
||||
|
||||
### Metadata Exchange
|
||||
|
||||
Common cross-cutting concerns like authentication or tracing rely on the exchange of data that is not part of the declared interface of a service. Deployments rely on their ability to evolve these features at a different rate to the individual APIs exposed by services.
|
||||
|
||||
### Standardized Status Codes
|
||||
|
||||
Clients typically respond to errors returned by API calls in a limited number of ways. The status code namespace should be constrained to make these error handling decisions clearer. If richer domain-specific status is needed the metadata exchange mechanism can be used to provide that.
|
||||
|
|
@ -1,9 +1,7 @@
|
|||
---
|
||||
attribution: Originally written by Lisa Carey with help from others at Google.
|
||||
date: "2016-03-24T00:00:00Z"
|
||||
published: true
|
||||
title: Google Cloud PubSub - with the power of gRPC!
|
||||
url: blog/pubsub
|
||||
attribution: Originally written by Lisa Carey with help from others at Google.
|
||||
date: 2016-03-24
|
||||
---
|
||||
|
||||
[Google Cloud PubSub](https://cloud.google.com/pubsub/) is Google's scalable real-time messaging service that lets users send and receive messages between independent applications. It's an important part of Google Cloud Platform's big data offering, and is used by customers worldwide to build their own robust, global services. However, until now, the only way to use the Cloud PubSub API was via JSON over HTTP. That's all changed with the release of [PubSub gRPC alpha](https://cloud.google.com/blog/big-data/2016/03/announcing-grpc-alpha-for-google-cloud-pubsub). Now **users can access PubSub via gRPC** and benefit from all the advantages it brings.
|
||||
|
|
@ -1,10 +1,8 @@
|
|||
---
|
||||
title: The state of gRPC in the browser
|
||||
author: Johan Brandhorst
|
||||
author-link: https://jbrandhorst.com/
|
||||
date: "2019-01-08T00:00:00Z"
|
||||
published: true
|
||||
title: The state of gRPC in the browser
|
||||
url: blog/state-of-grpc-web
|
||||
date: 2019-01-08
|
||||
---
|
||||
|
||||
_This is a guest post by_
|
||||
|
|
@ -18,6 +16,8 @@ Its support for polyglot environments, focus on performance, type safety, and
|
|||
developer productivity has transformed the way developers design their
|
||||
architectures.
|
||||
|
||||
<!--more-->
|
||||
|
||||
So far the benefits have largely only been available to mobile
|
||||
app and backend developers, whilst frontend developers have had to continue to
|
||||
rely on JSON REST interfaces as their primary means of information exchange.
|
||||
|
|
@ -27,8 +27,6 @@ addition in the toolbox of frontend developers.
|
|||
In this post, I'll describe some of the history of gRPC in the browser, explore
|
||||
the state of the world today, and share some thoughts on the future.
|
||||
|
||||
<!--more-->
|
||||
|
||||
# Beginnings
|
||||
|
||||
In the summer of 2016, both a team at Google and
|
||||
|
|
@ -1,20 +1,20 @@
|
|||
---
|
||||
title: Take the gRPC Survey!
|
||||
author: Kailash Sethuraman
|
||||
author-link: https://github.com/hsaliak
|
||||
company: Google
|
||||
company-link: https://www.google.com
|
||||
date: "2018-08-14T00:00:00Z"
|
||||
published: true
|
||||
title: Take the gRPC Survey!
|
||||
url: blog/take-the-grpc-survey
|
||||
date: 2018-08-14
|
||||
---
|
||||
|
||||
## The gRPC Project wants your feedback!
|
||||
|
||||
The gRPC project is looking for feedback to improve the gRPC experience. To do this, we are running a [gRPC user survey](http://bit.ly/gRPC18survey). We invite you to participate and provide input that will help us better plan and prioritize.
|
||||
|
||||
<!--more-->
|
||||
|
||||
## gRPC User Survey
|
||||
|
||||
**Who** : If you currently use gRPC, have used gRPC in the past, or have any interest in it, we would love to hear from you.
|
||||
|
||||
**Where**: Please take this 15 minute survey by Friday, 24th August.
|
||||
|
|
@ -23,7 +23,7 @@ The gRPC project is looking for feedback to improve the gRPC experience. To do t
|
|||
|
||||
|
||||
## Spread the word!
|
||||
|
||||
Please help us spread the word on this survey by posting it on your social networks and sharing with your friends. Every single feedback is precious, and we would like as much of it as possible!
|
||||
|
||||
Survey Short link: [http://bit.ly/gRPC18survey
|
||||
](http://bit.ly/gRPC18survey)
|
||||
Survey Short link: [http://bit.ly/gRPC18survey](http://bit.ly/gRPC18survey)
|
||||
|
|
@ -1,14 +1,13 @@
|
|||
---
|
||||
title: Why we have decided to move our APIs to gRPC
|
||||
attribution: Originally written by Dale Hopkins with additional content by Lisa Carey
|
||||
and others at Google.
|
||||
author: Dale Hopkins
|
||||
company: Vendasta
|
||||
company-link: https://vendasta.com
|
||||
date: "2016-08-29T00:00:00Z"
|
||||
published: true
|
||||
date: 2016-08-29
|
||||
thumbnail: ../img/vend-icon.png?raw=true
|
||||
title: Why we have decided to move our APIs to gRPC
|
||||
url: blog/vendastagrpc
|
||||
aliases: ["blog/vendastagrpc"]
|
||||
---
|
||||
|
||||
Our guest post today comes from Dale Hopkins, CTO of [Vendasta](https://vendasta.com/).
|
||||
|
|
@ -1,14 +1,13 @@
|
|||
---
|
||||
title: gRPC at VSCO
|
||||
attribution: Thanks to the VSCO engineers that worked on this migration.Steven Tang,
|
||||
Sam Bobra, Daniel Song, Lucas Kacher, and many others.
|
||||
author: Robert Sayre and Melinda Lu
|
||||
company: VSCO
|
||||
company-link: https://vsco.co
|
||||
date: "2016-09-06T00:00:00Z"
|
||||
published: true
|
||||
date: 2016-09-06
|
||||
thumbnail: ../img/vsco-logo.png?raw=true
|
||||
title: gRPC at VSCO
|
||||
url: blog/vscogrpc
|
||||
aliases: ["blog/vscogrpc"]
|
||||
---
|
||||
|
||||
Our guest post today comes from Robert Sayre and Melinda Lu of VSCO.
|
||||
|
|
@ -1,12 +1,10 @@
|
|||
---
|
||||
title: Migration to Google Cloud Platform — gRPC & grpc-gateway
|
||||
author: Miguel Mendez
|
||||
company: Yik Yak
|
||||
company-link: https://yikyakapp.com
|
||||
date: "2017-04-12T00:00:00Z"
|
||||
published: true
|
||||
date: 2017-04-12
|
||||
thumbnail: https://cdn-images-1.medium.com/max/1600/0*qYehJ2DvPgFcG_nX.
|
||||
title: Migration to Google Cloud Platform — gRPC & grpc-gateway
|
||||
url: blog/yygrpc
|
||||
---
|
||||
|
||||
Our guest post today comes from [Miguel Mendez](https://www.linkedin.com/in/miguel-mendez-008231/) of Yik Yak.
|
||||
|
|
@ -36,18 +34,17 @@ Third, it is great that I can use curl from the command line to hit an API, but
|
|||
The fourth problem with a REST APIs is that, at least until [Swagger](https://swagger.io/) arrived on the scene, there was no declarative way to define a REST API and include type information. It may sound pedantic, but there are legitimate reasons to want a proper definition that includes type information in general. To reinforce the point, look at the lines of PHP server code below, which were extracted from various files, that set the “hidePin” field on “yak” which was then returned to the client. The actual line of code that executed on the server was a function of multiple parameters, so imagine that the one which was run was basically chosen at random:
|
||||
|
||||
```php
|
||||
// Code omitted…
|
||||
$yak->hidePin=false;
|
||||
|
||||
// Code omitted…
|
||||
$yak->hidePin=true;
|
||||
|
||||
// Code omitted…
|
||||
$yak->hidePin=0;
|
||||
|
||||
// Code omitted…
|
||||
$yak->hidePin=1;
|
||||
// Code omitted…
|
||||
$yak->hidePin=false;
|
||||
|
||||
// Code omitted…
|
||||
$yak->hidePin=true;
|
||||
|
||||
// Code omitted…
|
||||
$yak->hidePin=0;
|
||||
|
||||
// Code omitted…
|
||||
$yak->hidePin=1;
|
||||
```
|
||||
|
||||
What is the type of the field hidePin? You cannot say for certain. It could be a boolean or an integer or whatever happens to have been written there by the server, but in any case now your clients have to be able to deal with these possibilities which makes them more complicated.
|
||||
|
|
@ -55,51 +52,59 @@ What is the type of the field hidePin? You cannot say for certain. It could be a
|
|||
Problems can also arise when the client’s definition of a type varies from that which the server expects. Have a look at the server code below which processed a JSON payload sent up by a client:
|
||||
|
||||
```php
|
||||
// Code omitted…
|
||||
switch ($fieldName) {
|
||||
// Code omitted…
|
||||
case “recipientID”:
|
||||
// This is being added because iOS is passing the recipientID
|
||||
// incorrectly and we still want to capture these events
|
||||
// … expected fall through …
|
||||
|
||||
case “Recipientid”:
|
||||
$this->yakkerEvent->recipientID = $value;
|
||||
break;
|
||||
// Code omitted…
|
||||
}
|
||||
// Code omitted…
|
||||
// Code omitted...
|
||||
switch ($fieldName) {
|
||||
// Code omitted...
|
||||
case “recipientID”:
|
||||
// This is being added because iOS is passing the recipientID
|
||||
// incorrectly and we still want to capture these events
|
||||
// … expected fall through …
|
||||
|
||||
case “Recipientid”:
|
||||
$this->yakkerEvent->recipientID = $value;
|
||||
break;
|
||||
// Code omitted...
|
||||
}
|
||||
// Code omitted...
|
||||
```
|
||||
|
||||
In this case, the server had to deal with an iOS client that sent a JSON object whose field name used unexpected casing. Again, not insurmountable but all of these little disconnects compound and work together to steal time away from the problems that really move the ball down the field.
|
||||
|
||||
## gRPC can address the issues with REST…
|
||||
## gRPC can address the issues with REST
|
||||
|
||||
If you’re not familiar with gRPC, it’s a “high performance, open-source universal remote procedure call (RPC) framework” that uses Google Protocol Buffers as the Interface Description Language (IDL) for describing a service interface as well as the structure of the messages exchanged. This IDL can then be compiled to produce language-specific client and server stubs. In case that seemed a little obtuse, I’ll zoom into the aspects that are important.
|
||||
|
||||
### gRPC is Declarative, Strongly-Typed, and Language Independent
|
||||
|
||||
gRPC descriptions are written using an Interface Description Language that is independent of any specific programming language, yet its concepts map onto the supported languages. This means that you can describe your ideal service API, the messages that it supports, and then use “protoc”, the protocol compiler, to generate client and server stubs for your API. Out of the box, you can produce client and server stubs in C/C++, C#, Node.js, PHP, Ruby, Python, Go and Java. You can also get additional protoc plugins which can create stubs for Objective-C and Swift.
|
||||
|
||||
Those issues that we had with “hidePin” and “recipientID” vs.”Recipientid” fields above go away because we have a single, canonical declaration that establishes the types used, and the language-specific code generation ensures that we don’t have typos in the client or server code regardless of their implementation language.
|
||||
|
||||
### gRPC Means No hand-rolling of RPC Code is Required
|
||||
|
||||
This is a very powerful aspect of the gRPC ecosystem. Often times developers will hand roll their RPC code because it just seems more straightforward. However, as the number of types of clients that you need to support increases, the carrying costs of this approach also increase non-linearly.
|
||||
Imagine that you start off with a service that is called from a web browser. At some point down the road, the requirements are updated and now you have to support Android and iOS clients. Your server is likely fine, but the clients now need to be able to speak the same RPC dialect and often times there are differences that creep in. Things can get even worse if the server has to compensate for the differences amongst the clients.
|
||||
On the other hand, using gRPC you just add the protocol compiler plugins and they generate the Android and iOS client stubs. This cuts out a whole class of problems. As a bonus, if you don’t modify the generated code — and you should not have to — then any performance improvements in the generated code will be picked up.
|
||||
|
||||
### gRPC has Compact Serialization
|
||||
|
||||
gRPC uses Google protocol buffers to serialize messages. This serialization format is very compact because, among other things, field names are not included in the serialized form. Compare this to a JSON object where each instance of an object carries a full copy of its field names, includes extra curly braces, etc. For a low-volume application this may not be an issue, but it can add up quickly.
|
||||
|
||||
### gRPC Tooling is Extensible
|
||||
|
||||
Another very useful feature of the gRPC framework is that it is extensible. If you need support for a language that is not currently supported, there is a way to create plugins for the protocol compiler that allows you to add what you need.
|
||||
|
||||
### gRPC Supports Contract Updates
|
||||
|
||||
An often overlooked aspect of service APIs is how they may evolve over time. At best, this is often a secondary consideration. If you are using gRPC, and you adhered to a few basic rules, your messages can be forward and backward compatible.
|
||||
|
||||
## Grpc-gateway — because REST will be with us for a while…
|
||||
|
||||
You’re probably thinking: gRPC is great but I have a ton of REST clients to deal with. Well, there is another tool in this ecosystem and it is called grpc-gateway. Grpc-gateway “generates a reverse-proxy server which translates a RESTful JSON API into gRPC”. So if you want to support REST clients you can, and it doesn’t cost you any real extra effort.
|
||||
If your existing REST clients are pretty far from the normal REST APIs, you can use custom marshallers with grpc-gateway to compensate.
|
||||
|
||||
## Migration and gRPC + grpc-gateway
|
||||
|
||||
As mentioned previously, we had a lot of PHP code and REST endpoints which we wanted to rework as part of the migration. By using the combination of gRPC and grpc-gateway, we were able to define gRPC versions of the legacy REST APIs and then use grpc-gateway to expose the exact REST endpoints that clients were used to. With these alternative implementations in place we were able to move traffic between the old and new systems using combinations of DNS updates as well as our [Experimentation and Configuration System](https://medium.com/yik-yak-eng/yik-yak-configuration-and-experiment-system-16a5c15ee77c#.7s11d3kqh) without causing any disruption to the existing clients. We were even able to leverage the existing test suites to verify functionality and establish parity between the old and new systems.
|
||||
Lets walk through the pieces and how they fit together.
|
||||
|
||||
|
|
@ -0,0 +1,31 @@
|
|||
---
|
||||
title: Contributing to gRPC
|
||||
---
|
||||
|
||||
To contribute to gRPC documentation, please fork the [gRPC repository on GitHub](https://github.com/grpc/grpc.io) and start submitting pull requests.
|
||||
|
||||
## Contribute guidelines for gRPC
|
||||
|
||||
We welcome contributions to any of our three core repositories:
|
||||
|
||||
* [gRPC](https://github.com/grpc/grpc)
|
||||
* [gRPC Java](https://github.com/grpc/grpc-java)
|
||||
* [gRPC Go](https://github.com/grpc/grpc-go)
|
||||
|
||||
{{< button text="View guidelines" url="https://github.com/grpc/grpc/blob/master/CONTRIBUTING.md" >}}
|
||||
|
||||
## Contribution guidelines for the gRPC Ecosystem
|
||||
|
||||
The [gRPC Ecosystem](https://github.com/grpc-ecosystem/) is a different organization where we collect and curate valuable integrations of other projects with gRPC. You can propose a new project for it by filling out the **Propose new project** form.
|
||||
|
||||
{{< button text="View guidelines" url="https://github.com/grpc/grpc-contrib/blob/master/CONTRIBUTING.md" >}}
|
||||
|
||||
## Edit our site on GitHub
|
||||
|
||||
Click the below button to visit the repo for our site. You can then click the "Fork" button in the upper-right area of the screen to create a copy of our site on your GitHub account called a "fork." Make any changes you want in your fork, and when you are ready to send those changes to us, go to the index page for your fork and click **New Pull Request** to let us know about it.
|
||||
|
||||
{{< button text="Browse this site's source code" url="https://github.com/grpc/grpc.io" >}}
|
||||
|
||||
## Being a member of the gRPC organization on github
|
||||
|
||||
Being an organization member is not required for the vast majority of the contributions. Membership is required for certain administrative tasks such as accepting a pull request, or closing issues. If you wish to be part of the gRPC organization on github, please [get in touch with us](/community). Please note that in order to be part of the organization, your GitHub account needs to have [two-factor authentication enabled](https://help.github.com/articles/securing-your-account-with-two-factor-authentication-2fa/).
|
||||
|
|
@ -1,46 +0,0 @@
|
|||
---
|
||||
title: Contribute
|
||||
---
|
||||
<div class="container markdown">
|
||||
<div class="row">
|
||||
|
||||
To contribute to gRPC documentation, please fork the <a href="https://github.com/grpc/grpc.io">GitHub gRPC repository</a> and start submitting pull requests.
|
||||
|
||||
<div id="MainRepoInstructions">
|
||||
<h2>Contribution guidelines for gRPC</h2>
|
||||
|
||||
<p>We welcome contributions to either of our three core repositories. <a href="https://github.com/grpc/grpc">gRPC</a>, <a href="https://github.com/grpc/grpc-java">gRPC Java</a> and <a href="https://github.com/grpc/grpc-go">gRPC Go</a>. </p>
|
||||
|
||||
<button class="btn btn-grpc waves-effect waves-light"><a href="https://github.com/grpc/grpc/blob/master/CONTRIBUTING.md">View Guidelines</a></button>
|
||||
|
||||
</div>
|
||||
|
||||
<div id="EcosystemInstructions">
|
||||
<h2>Contribution guidelines for gRPC Ecosystem</h2>
|
||||
|
||||
<p><a href="https://github.com/grpc-ecosystem/">gRPC Ecosystem</a> is a different organization where we collect and curate valuable integrations of other projects with gRPC. You can propose a new project for it by filling up the <a hre="https://docs.google.com/a/google.com/forms/d/119zb79XRovQYafE9XKjz9sstwynCWcMpoJwHgZJvK74/edit">Propose new project form</a>.</p>
|
||||
|
||||
<button class="btn btn-grpc waves-effect waves-light"><a href="https://github.com/grpc/grpc-contrib/blob/master/CONTRIBUTING.md">View Guidelines</a></button>
|
||||
|
||||
|
||||
<div id="generalInstructions">
|
||||
<h2>Edit our site on github</h2>
|
||||
|
||||
<p>Click the below button to visit the repo for our site. You can then click the "Fork" button in the upper-right area of the screen to create a copy of our site on your GitHub account called a "fork." Make any changes you want in your fork, and when you are ready to send those changes to us, go to the index page for your fork and click "New Pull Request" to let us know about it.</p>
|
||||
|
||||
<button class="btn btn-grpc waves-effect waves-light"><a href="https://github.com/grpc/grpc.io">Browse this site's source code</a></button>
|
||||
</div>
|
||||
|
||||
<div id="githubOrganization">
|
||||
<h2>Being a member of the gRPC organization on github</h2>
|
||||
|
||||
<p>Being an organization member is not required for the vast majority of the contributions. Membership is required for certain administrative tasks such as accepting a pull request, or closing issues. If you wish to be part of the gRPC organization on github, please <a href="https://grpc.io/community/">get in touch with us</a>. Please note that in order to be part of the organization, your github account needs to have <a href="https://help.github.com/articles/securing-your-account-with-two-factor-authentication-2fa/">two factor security enabled</a>.</p>
|
||||
|
||||
</div>
|
||||
<p></p>
|
||||
<p></p>
|
||||
<p></p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -1,171 +0,0 @@
|
|||
---
|
||||
title: "Documentation"
|
||||
date: 2018-09-11T15:45:50+07:00
|
||||
draft: false
|
||||
---
|
||||
|
||||
<div class="docssection2">
|
||||
Welcome to the developer documentation for gRPC.
|
||||
Here you can learn about key gRPC concepts, find quick starts, reference
|
||||
material, and tutorials for all our supported languages, and more. If you’re new to gRPC we recommend that you read <a href="guides/"><b>What is
|
||||
gRPC?</b></a> to find out more about our system and how it works. Or, if you want to see gRPC in action first, visit the <a href="quickstart/">QuickStart</a> for your favourite language.
|
||||
</div>
|
||||
|
||||
|
||||
<div class="doclangsection">
|
||||
<h4 style="text-align:center;"> gRPC by Language</h4>
|
||||
<div class="doccols">
|
||||
<div class="docscol1">
|
||||
|
||||
<h3>C++</h3>
|
||||
<a href="/docs/quickstart/cpp/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/cpp/">gRPC Basics Tutorial</a><br>
|
||||
<a href="https://grpc.io/grpc/cpp/index.html">API Reference</a>
|
||||
<br>
|
||||
<h3 style="margin-top:3%;">Go</h3>
|
||||
|
||||
<a href="/docs/quickstart/go/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/go/">gRPC Basics Tutorial</a><br>
|
||||
<a href="https://godoc.org/google.golang.org/grpc">API Reference</a><br>
|
||||
<a href="/docs/reference/go/generated-code/">Generated Code Reference</a>
|
||||
<br>
|
||||
<h3 style="margin-top:3%;">Node.js</h3>
|
||||
|
||||
<a href="/docs/quickstart/node/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/node/">gRPC Basics Tutorial</a><br>
|
||||
<a href="https://grpc.io/grpc/node/">API Reference</a>
|
||||
<br>
|
||||
<h3 style="margin-top:3%;">PHP</h3>
|
||||
|
||||
<a href="/docs/quickstart/php/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/php/">gRPC Basics Tutorial</a><br>
|
||||
<a href="https://grpc.io/grpc/php/namespace-Grpc.html">API Reference</a>
|
||||
|
||||
</div>
|
||||
|
||||
<div class="docscol2">
|
||||
|
||||
<h3>Java</h3>
|
||||
|
||||
<a href="/docs/quickstart/java/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/java/">gRPC Basics Tutorial</a><br>
|
||||
<a href="https://grpc.io/grpc-java/javadoc/index.html">API Reference</a><br>
|
||||
<a href="/docs/reference/java/generated-code/">Generated Code Reference</a>
|
||||
<br>
|
||||
<h3 style="margin-top:3%;">Ruby</h3>
|
||||
|
||||
<a href="/docs/quickstart/ruby/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/ruby/">gRPC Basics Tutorial</a><br>
|
||||
<a href="https://www.rubydoc.info/gems/grpc">API Reference</a>
|
||||
<br>
|
||||
<h3 style="margin-top:3%;">Android Java</h3>
|
||||
|
||||
<a href="/docs/quickstart/android/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/android/">gRPC Basics Tutorial</a><br>
|
||||
<a href="https://grpc.io/grpc-java/javadoc/index.html">API Reference</a><br>
|
||||
<a href="/docs/reference/java/generated-code/">Generated Code Reference</a>
|
||||
<br>
|
||||
<h3 style="margin-top:3%;">Dart</h3>
|
||||
|
||||
<a href="/docs/quickstart/dart/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/dart/">gRPC Basics Tutorial</a><br>
|
||||
|
||||
</div>
|
||||
|
||||
<div class="docscol3">
|
||||
|
||||
<h3>Python</h3>
|
||||
|
||||
<a href="/docs/quickstart/python/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/python/">gRPC Basics Tutorial</a><br>
|
||||
<a href="https://grpc.io/grpc/python/">API Reference</a><br>
|
||||
<a href="/docs/reference/python/generated-code/">Generated Code Reference</a>
|
||||
|
||||
<br>
|
||||
<h3 style="margin-top:3%;">C#</h3>
|
||||
|
||||
<a href="/docs/quickstart/csharp/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/csharp/">gRPC Basics Tutorial</a><br>
|
||||
<a href="https://grpc.io/grpc/csharp/api/Grpc.Core.html">API Reference</a><br>
|
||||
<br>
|
||||
<a href="/docs/quickstart/csharp-dotnet/">Quick Start Guide (the "grpc-dotnet" version)</a>
|
||||
|
||||
<br>
|
||||
<h3 style="margin-top:3%;">Objective-C</h3>
|
||||
|
||||
<a href="/docs/quickstart/objective-c/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/objective-c/">gRPC Basics Tutorial</a><br>
|
||||
<a href="http://cocoadocs.org/docsets/gRPC/">API Reference</a>
|
||||
<br>
|
||||
<h3 style="margin-top:3%;">Web</h3>
|
||||
|
||||
<a href="/docs/quickstart/web/">Quick Start Guide</a><br>
|
||||
<a href="/docs/tutorials/basic/web/">gRPC Basics Tutorial</a><br>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="docusecasesection">
|
||||
<h4 style="text-align:center;">gRPC by Use Cases</h4>
|
||||
<div class="doccols" style="background-color:white;margin-top:0px"">
|
||||
<div class="docstext">
|
||||
gRPC is used in last mile of computing in mobile and web client since it can generate libraries for iOS and Android and uses standards based HTTP/2 as transport allowing it to easily traverse proxies and firewalls. There is also work underway to develop a JS library for use in browsers. Beyond that, it is ideal as a microservices interconnect, not just because the core protocol is very efficient but also because the framework has pluggable authentication, load balancing etc. Google itself is also transitioning to use it to connect microservices.
|
||||
</div>
|
||||
<div class="docscol1">
|
||||
|
||||
<h3 style="padding-bottom:5%;">Last Mile of Computing</h3>
|
||||
|
||||
<p><a href="/docs/tutorials/basic/android/">Mobile: Example RouteGuide Client on Android</a></p>
|
||||
<p><a href="https://github.com/grpc/grpc-web">Web: Browser Client</a></p>
|
||||
<br>
|
||||
</div>
|
||||
|
||||
<div class="docscol2" >
|
||||
|
||||
<h3 style="padding-bottom:5%;">APIs</h3>
|
||||
<p>
|
||||
<a href="https://github.com/GoogleCloudPlatform/cloud-bigtable-client">Google Cloud BigTable Client APIs</a></p>
|
||||
<p><a href="https://cloud.google.com/blog/big-data/2016/03/announcing-grpc-alpha-for-google-cloud-pubsub">Google Cloud PubSub APIs</a></p>
|
||||
<p><a href="https://cloud.google.com/speech/reference/rpc/">Google Cloud Speech APIs</a></p>
|
||||
<br>
|
||||
</div>
|
||||
|
||||
<div class="docscol3">
|
||||
|
||||
<h3 style="padding-bottom:5%;">Microservices</h3>
|
||||
|
||||
<p><a href="https://github.com/dinowernli/java-grpc-prometheus">Monitoring gRPC services using Prometheus in Java</a></p>
|
||||
<p><a href="https://github.com/mwitkow/go-grpc-prometheus">Tracing gRPC services using Zipkin in Java</a></p>
|
||||
<p><a href="https://github.com/grpc/grpc/blob/master/doc/load-balancing.md">Load Balancing in gRPC</a></p>
|
||||
<br>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="docprojectsection">
|
||||
<h4 style="text-align:center;">gRPC in Other Projects</h4>
|
||||
<div class="doccols">
|
||||
<div class="docstext">
|
||||
gRPC now has a vibrant community of companies, projects, developers who are extending and building around it. Here are some popular projects.
|
||||
</div>
|
||||
<div class="docscol1">
|
||||
|
||||
<h3 style="padding-bottom:5%;">Popular Projects</h3>
|
||||
|
||||
<a href="https://github.com/grpc-ecosystem/grpc-gateway" style="display:block">gRPC Gateway</a>
|
||||
<a href="https://github.com/grpc-ecosystem/polyglot" style="display:block">Polyglot: gRPC command line client</a>
|
||||
<a href="https://github.com/google/flatbuffers/tree/master/grpc" style="display:block">FlatBuffer for gRPC</a>
|
||||
<a href="https://github.com/go-kit/kit/tree/master/transport/grpc" style="display:block">Go kit with gRPC transport</a>
|
||||
<a href="https://github.com/etcd-io/etcd" style="display:block">etcd</a>
|
||||
<a href="https://github.com/cockroachdb/cockroach" style="display:block">cockroachdb</a>
|
||||
<a href="https://github.com/openzipkin/brave/tree/master/archive/brave-grpc" style="display:block">Zipkin for gRPC</a>
|
||||
<a href="https://github.com/pingcap/tidb" style="display:block">TiDB</a>
|
||||
<a href="https://github.com/apache/bookkeeper" style="display:block">Apache BookKeeper</a>
|
||||
<br>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -0,0 +1,12 @@
|
|||
---
|
||||
title: Overview
|
||||
---
|
||||
|
||||
Welcome to the developer documentation for gRPC. Here you can learn about key gRPC concepts, find quick starts, reference material, and tutorials for all our supported languages, and more. If you’re new to gRPC we recommend that you read [What is gRPC?](guides) to find out more about our system and how it works. Or if you want to see gRPC in action first, visit the [Quick Start](quickstart) for your favourite language.
|
||||
|
||||
<!-- generated using the shortcode at layouts/shortcodes/language-block.html -->
|
||||
{{< language-block >}}
|
||||
|
||||
## gRPC by Use Cases
|
||||
|
||||
gRPC is used in last mile of computing in mobile and web client since it can generate libraries for iOS and Android and uses standards based HTTP/2 as transport allowing it to easily traverse proxies and firewalls. There is also work underway to develop a JS library for use in browsers. Beyond that, it is ideal as a microservices interconnect, not just because the core protocol is very efficient but also because the framework has pluggable authentication, load balancing, etc. Google itself is also transitioning to use it to connect microservices.
|
||||
|
|
@ -0,0 +1,14 @@
|
|||
---
|
||||
title: Example
|
||||
draft: true
|
||||
---
|
||||
|
||||
Example doc!
|
||||
|
||||
{{< success >}}
|
||||
Ea sunt quis cillum elit ipsum et sint nostrud sit sit ad ullamco minim aliqua. Exercitation excepteur ut tempor elit id. Officia eiusmod fugiat tempor ipsum anim incididunt. Irure incididunt esse do ad in magna eiusmod aliqua excepteur sunt.
|
||||
|
||||
Cupidatat duis est consequat qui tempor elit. Amet aliquip voluptate Lorem ipsum fugiat non amet elit sunt pariatur reprehenderit tempor excepteur nostrud. Consequat tempor ea occaecat quis fugiat officia culpa tempor cillum do. Irure adipisicing enim ipsum consectetur elit.
|
||||
|
||||
Ex Lorem ut consequat est enim aliqua aute incididunt labore aliqua. Consectetur occaecat esse Lorem amet fugiat consectetur commodo ea et aliquip dolore consequat cupidatat ut. Magna nisi labore nostrud proident nulla tempor sit occaecat labore commodo anim voluptate tempor anim.
|
||||
{{< /success >}}
|
||||
|
|
@ -1,19 +1,16 @@
|
|||
---
|
||||
layout: guides
|
||||
title: Guides
|
||||
description: Task-oriented walkthroughs of common use cases
|
||||
weight: 2
|
||||
---
|
||||
|
||||
This document introduces you to gRPC and protocol buffers. gRPC can use
|
||||
protocol buffers as both its Interface Definition Language (IDL) and as its underlying message
|
||||
protocol buffers as both its Interface Definition Language (**IDL**) and as its underlying message
|
||||
interchange format. If you’re new to gRPC and/or protocol buffers, read this!
|
||||
If you just want to dive in and see gRPC in action first,
|
||||
see our [Quick Starts](../quickstart).
|
||||
|
||||
|
||||
<div id="toc" class="toc mobile-toc"></div>
|
||||
|
||||
### Overview
|
||||
## Overview
|
||||
|
||||
In gRPC, a client application can directly call a method on a server application
|
||||
on a different machine as if it were a local object, making it easier for you to
|
||||
|
|
@ -24,13 +21,13 @@ server implements this interface and runs a gRPC server to handle client calls.
|
|||
On the client side, the client has a stub (referred to as just a client in some
|
||||
languages) that provides the same methods as the server.
|
||||
|
||||

|
||||

|
||||
|
||||
gRPC clients and servers can run and talk to each other in a variety of environments - from servers inside Google to your own desktop - and can be written in any of gRPC's supported languages. So, for example, you can easily create a gRPC server in Java with clients in Go, Python, or Ruby. In addition, the latest Google APIs will have gRPC versions of their interfaces, letting you easily build Google functionality into your applications.
|
||||
|
||||
### Working with Protocol Buffers
|
||||
|
||||
By default, gRPC uses [Protocol Buffers][PB docs], Google’s
|
||||
By default, gRPC uses [Protocol Buffers][], Google’s
|
||||
mature open source mechanism for serializing structured data (although it
|
||||
can be used with other data formats such as JSON). Here's a quick intro to how
|
||||
it works. If you're already familiar with protocol buffers, feel free to skip
|
||||
|
|
@ -89,11 +86,11 @@ code for populating, serializing, and retrieving your message types. You'll
|
|||
see an example of this below.
|
||||
|
||||
To learn more about protocol buffers, including how to install `protoc` with the
|
||||
gRPC plugin in your chosen language, see the [protocol buffers documentation][PB docs].
|
||||
gRPC plugin in your chosen language, see the [protocol buffers documentation][protocol buffers].
|
||||
|
||||
#### Protocol buffer versions
|
||||
## Protocol buffer versions
|
||||
|
||||
While protocol buffers have been available to open source users for some time,
|
||||
While [protocol buffers][] have been available to open source users for some time,
|
||||
most examples from this site use protocol buffers version 3 (proto3), which has
|
||||
a slightly simplified syntax, some useful new features, and supports more
|
||||
languages. Proto3 is currently available in Java, C++, Dart, Python,
|
||||
|
|
@ -113,6 +110,5 @@ issues with proto2 clients talking to proto3 servers and vice versa.
|
|||
[golang/protobuf GitHub repo]: https://github.com/golang/protobuf
|
||||
[proto3 language guide]: https://developers.google.com/protocol-buffers/docs/proto3
|
||||
[protocol buffers GitHub repo]: https://github.com/google/protobuf/releases
|
||||
[PB docs]: https://developers.google.com/protocol-buffers/docs/overview
|
||||
|
||||
[protocol buffers]: https://developers.google.com/protocol-buffers/docs/overview
|
||||
[reference documentation]: https://developers.google.com/protocol-buffers/docs/reference/overview
|
||||
|
|
|
|||
|
|
@ -2,11 +2,9 @@
|
|||
layout: guides
|
||||
title: Authentication
|
||||
description: |
|
||||
This document provides an overview of gRPC authentication, including our built-in supported auth mechanisms, how to plug in your own authentication systems, and examples of how to use gRPC auth in our supported languages.
|
||||
This document provides an overview of gRPC authentication, including our built-in supported auth mechanisms, how to plug in your own authentication systems, and examples of how to use gRPC auth in our supported languages.
|
||||
---
|
||||
|
||||
<div id="toc" class="toc mobile-toc"></div>
|
||||
|
||||
### Overview
|
||||
|
||||
gRPC is designed to work with a variety of authentication mechanisms, making it
|
||||
|
|
@ -36,10 +34,9 @@ on the channel - Google will not allow connections without SSL/TLS, and
|
|||
most gRPC language implementations will not let you send credentials on an
|
||||
unencrypted channel.
|
||||
|
||||
<p class="note"> <strong>WARNING</strong>: Google credentials should only
|
||||
be used to connect to Google services. Sending a Google issued OAuth2 token
|
||||
to a non-Google service could result in this token being stolen and used to
|
||||
impersonate the client to Google services.</p>
|
||||
{{< warning >}}
|
||||
Google credentials should only be used to connect to Google services. Sending a Google issued OAuth2 token to a non-Google service could result in this token being stolen and used to impersonate the client to Google services.
|
||||
{{< /warning >}}
|
||||
|
||||
### Authentication API
|
||||
|
||||
|
|
@ -539,7 +536,6 @@ var scope = 'https://www.googleapis.com/auth/grpc-testing';
|
|||
$client = new helloworld\GreeterClient('localhost:50051', [
|
||||
'credentials' => Grpc\ChannelCredentials::createInsecure(),
|
||||
]);
|
||||
...
|
||||
```
|
||||
|
||||
##### Authenticate with Google
|
||||
|
|
|
|||
|
|
@ -5,10 +5,6 @@ description: |
|
|||
gRPC is designed to support high-performance open-source RPCs in many languages. This document describes the performance benchmarking tools, the scenarios considered by the tests, and the testing infrastructure.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
<a name="Overview"></a>
|
||||
|
||||
### Overview
|
||||
|
||||
gRPC is designed for both high-performance and high-productivity
|
||||
|
|
@ -42,9 +38,6 @@ These workers are controlled by a
|
|||
that takes as input a scenario description (in JSON format) and an
|
||||
environment variable specifying the host:port of each worker process.
|
||||
|
||||
|
||||
<a name="Languages under test"></a>
|
||||
|
||||
### Languages under test
|
||||
|
||||
The following languages have continuous performance testing as both
|
||||
|
|
@ -73,8 +66,6 @@ performance can be benchmarked using a proxy WorkerService written in
|
|||
another language. This code is implemented for PHP but is not yet in
|
||||
continuous testing mode.
|
||||
|
||||
<a name="Scenarios under test"></a>
|
||||
|
||||
### Scenarios under test
|
||||
|
||||
There are several important scenarios under test and displayed in the dashboards
|
||||
|
|
@ -89,8 +80,6 @@ protobufs. Some C++ tests additionally use insecure communication and
|
|||
the generic (non-protobuf) API to display peak performance. Additional
|
||||
scenarios may be added in the future.
|
||||
|
||||
<a name="Testing infrastructure"></a>
|
||||
|
||||
### Testing infrastructure
|
||||
|
||||
All performance benchmarks are run as instances in GCE through our
|
||||
|
|
|
|||
|
|
@ -10,8 +10,6 @@ language-specific details, see the Quick Start, tutorial, and reference
|
|||
documentation for your chosen language(s), where available (complete reference
|
||||
docs are coming soon).
|
||||
|
||||
<div id="toc" class="toc mobile-toc"></div>
|
||||
|
||||
### Overview
|
||||
|
||||
#### Service definition
|
||||
|
|
@ -170,9 +168,7 @@ before writing its responses, or the server and client could "ping-pong": the
|
|||
server gets a request, then sends back a response, then the client sends another
|
||||
request based on the response, and so on.
|
||||
|
||||
<a name="deadlines"></a>
|
||||
|
||||
#### Deadlines/Timeouts
|
||||
#### Deadlines/Timeouts {#deadlines}
|
||||
|
||||
gRPC allows clients to specify how long they are willing to wait for an RPC to
|
||||
complete before the RPC is terminated with the error `DEADLINE_EXCEEDED`. On
|
||||
|
|
@ -199,8 +195,6 @@ Either the client or the server can cancel an RPC at any time. A cancellation
|
|||
terminates the RPC immediately so that no further work is done. It is *not* an
|
||||
"undo": changes made before the cancellation will not be rolled back.
|
||||
|
||||
<a name="metadata"></a>
|
||||
|
||||
#### Metadata
|
||||
|
||||
Metadata is information about a particular RPC call (such as [authentication
|
||||
|
|
|
|||
|
|
@ -3,6 +3,4 @@ layout: guides
|
|||
title: Contribution Guidelines
|
||||
---
|
||||
|
||||
# Contribution Guidelines
|
||||
|
||||
Coming soon!
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ description: |
|
|||
This page describes how gRPC deals with errors, including gRPC's built-in error codes. Example code in different languages can be found [here](https://github.com/avinassh/grpc-errors).
|
||||
---
|
||||
|
||||
<div id="toc" class="toc mobile-toc"></div>
|
||||
|
||||
### Standard error model
|
||||
|
||||
As you'll have seen in our concepts document and examples, when a gRPC call
|
||||
|
|
|
|||
|
|
@ -1,17 +1,14 @@
|
|||
---
|
||||
title: Quick Start
|
||||
layout: quickstart
|
||||
description: Get started with gRPC
|
||||
weight: 1
|
||||
---
|
||||
|
||||
<div id="toc" class="toc mobile-toc"></div>
|
||||
|
||||
These pages show you how to get up and running as quickly as possible in gRPC,
|
||||
including installing all the tools you’ll need.
|
||||
|
||||
There is a Quick Start for each gRPC supported language with accompanying sample
|
||||
code for a simple ```Hello World``` example for you to explore and update.
|
||||
code for a simple "Hello World" example for you to explore and update.
|
||||
|
||||
For an overview of some of the core concepts in gRPC, see [gRPC Concepts](/docs/guides/concepts/).
|
||||
For more tutorials and examples, see our [Tutorials](/docs/tutorials).
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: Android
|
|||
description: This guide gets you started with gRPC in Android Java with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
- JDK version 7 or higher
|
||||
|
|
@ -17,9 +15,9 @@ description: This guide gets you started with gRPC in Android Java with a simple
|
|||
[Android Virtual Device]: https://developer.android.com/studio/run/managing-avds.html
|
||||
[USB debugging]: https://developer.android.com/studio/command-line/adb.html#Enabling
|
||||
|
||||
> **Note**: gRPC Java does not support running a server on an Android device.
|
||||
> For this quick start, the Android client app will connect to a server running
|
||||
> on your local (non-Android) computer.
|
||||
{{< note >}}
|
||||
gRPC Java does not support running a server on an Android device. For this quick start, the Android client app will connect to a server running on your local (non-Android) computer.
|
||||
{{< /note >}}
|
||||
|
||||
### Download the example
|
||||
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: C++
|
|||
description: This guide gets you started with gRPC in C++ with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
#### gRPC
|
||||
|
|
|
|||
|
|
@ -5,11 +5,9 @@ short: C# with grpc-dotnet
|
|||
description: This guide gets you started with gRPC for .NET with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
> **Note**: This is a quick start guide for the "grpc-dotnet" implementation of
|
||||
> gRPC C#s. See [gRPC C# Quick Start](/docs/quickstart/csharp) for how to start
|
||||
> with the gRPC C# implementation based on native Core library.
|
||||
{{< note >}}
|
||||
This is a quick start guide for the "grpc-dotnet" implementation of gRPC C#s. See [gRPC C# Quick Start](../csharp) for how to start with the gRPC C# implementation based on native Core library.
|
||||
{{< /note >}}
|
||||
|
||||
### General project info
|
||||
|
||||
|
|
@ -21,4 +19,4 @@ The best way to start is the [gRPC ASP.NET Core Tutorial](https://docs.microsoft
|
|||
|
||||
### More Examples
|
||||
|
||||
More code examples for grpc-dotnet are at https://github.com/grpc/grpc-dotnet/tree/master/examples
|
||||
More code examples for grpc-dotnet are at [https://github.com/grpc/grpc-dotnet/tree/master/examples](https://github.com/grpc/grpc-dotnet/tree/master/examples).
|
||||
|
|
|
|||
|
|
@ -5,12 +5,9 @@ short: C#
|
|||
description: This guide gets you started with gRPC in C# with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
> **Note**: This is a quick start guide for the gRPC C# implementation based on
|
||||
> Core native library. See [gRPC for .NET Quick
|
||||
> Start](/docs/quickstart/csharp-dotnet/) for how to start with the
|
||||
> "grpc-dotnet" implementation.
|
||||
{{< note >}}
|
||||
This is a quick start guide for the gRPC C# implementation based on Core native library. See [gRPC for .NET Quick Start](..//csharp-dotnet/) for how to start with the "grpc-dotnet" implementation.
|
||||
{{< /note >}}
|
||||
|
||||
### Prerequisites
|
||||
|
||||
|
|
@ -44,18 +41,22 @@ dependencies for you (`Grpc`, `Grpc.Tools` and `Google.Protobuf` NuGet packages)
|
|||
### Build the example
|
||||
|
||||
#### Using Visual Studio (or Visual Studio for Mac)
|
||||
|
||||
* Open the solution `Greeter.sln` with Visual Studio
|
||||
* Build the solution
|
||||
|
||||
#### Using .NET Core SDK from the command line
|
||||
|
||||
From the `examples/csharp/Helloworld` directory:
|
||||
|
||||
```sh
|
||||
> dotnet build Greeter.sln
|
||||
```
|
||||
|
||||
*NOTE: If you want to use gRPC C# from a project that uses the "classic" .csproj files (supported by Visual Studio 2013, 2015 and older versions of Mono), please refer to the
|
||||
[Greeter using "classic" .csproj](https://github.com/grpc/grpc/blob/{{< param grpc_release_tag >}}/examples/csharp/HelloworldLegacyCsproj/README.md) example.*
|
||||
{{< note >}}
|
||||
If you want to use gRPC C# from a project that uses the "classic" .csproj files (supported by Visual Studio 2013, 2015 and older versions of Mono), please refer to the
|
||||
[Greeter using "classic" .csproj](https://github.com/grpc/grpc/blob/{{< param grpc_release_tag >}}/examples/csharp/HelloworldLegacyCsproj/README.md) example.
|
||||
{{< /note >}}
|
||||
|
||||
### Run a gRPC application
|
||||
|
||||
|
|
@ -63,17 +64,17 @@ From the `examples/csharp/Helloworld` directory:
|
|||
|
||||
* Run the server:
|
||||
|
||||
```sh
|
||||
> cd GreeterServer
|
||||
> dotnet run -f netcoreapp2.1
|
||||
```
|
||||
```sh
|
||||
> cd GreeterServer
|
||||
> dotnet run -f netcoreapp2.1
|
||||
```
|
||||
|
||||
* From another terminal, run the client:
|
||||
|
||||
```sh
|
||||
> cd GreeterClient
|
||||
> dotnet run -f netcoreapp2.1
|
||||
```
|
||||
```sh
|
||||
> cd GreeterClient
|
||||
> dotnet run -f netcoreapp2.1
|
||||
```
|
||||
|
||||
Congratulations! You've just run a client-server application with gRPC.
|
||||
|
||||
|
|
@ -88,7 +89,7 @@ server and the client "stub" have a `SayHello` RPC method that takes a
|
|||
server, and that this method is defined like this:
|
||||
|
||||
|
||||
```C#
|
||||
```proto
|
||||
// The greeting service definition.
|
||||
service Greeter {
|
||||
// Sends a greeting
|
||||
|
|
@ -110,7 +111,7 @@ Let's update this so that the `Greeter` service has two methods. Edit
|
|||
`examples/protos/helloworld.proto` and update it with a new `SayHelloAgain`
|
||||
method, with the same request and response types:
|
||||
|
||||
```C#
|
||||
```proto
|
||||
// The greeting service definition.
|
||||
service Greeter {
|
||||
// Sends a greeting
|
||||
|
|
@ -220,14 +221,14 @@ example by running `dotnet build Greeter.sln` or by clicking "Build" in Visual S
|
|||
|
||||
Just like we did before, from the `examples/csharp/Helloworld` directory:
|
||||
|
||||
1. Run the server:
|
||||
1. Run the server:
|
||||
|
||||
```sh
|
||||
> cd GreeterServer
|
||||
> dotnet run -f netcoreapp2.1
|
||||
```
|
||||
|
||||
2. From another terminal, run the client:
|
||||
2. From another terminal, run the client:
|
||||
|
||||
```sh
|
||||
> cd GreeterClient
|
||||
|
|
|
|||
|
|
@ -5,15 +5,15 @@ short: Dart
|
|||
description: This guide gets you started with gRPC in Dart with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
- Dart SDK version 2.0 or higher.
|
||||
|
||||
For installation instructions, see [Install Dart](https://dart.dev/install).
|
||||
|
||||
> Note: Dart gRPC supports the Flutter and Server platforms.
|
||||
{{< note >}}
|
||||
Dart gRPC supports the Flutter and Server platforms.
|
||||
{{< /note >}}
|
||||
|
||||
#### Protocol Buffers v3
|
||||
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: Go
|
|||
description: This guide gets you started with gRPC in Go with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
- Go version 1.6 or higher.
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: Java
|
|||
description: This guide gets you started with gRPC in Java with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
- JDK version 7 or higher
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: Node
|
|||
description: This guide gets you started with gRPC in Node with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
- Node version 4.0.0 or higher
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: Objective-C
|
|||
description: This guide gets you started with gRPC on the iOS platform in Objective-C with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Before you begin
|
||||
|
||||
#### System requirements
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: PHP
|
|||
description: This guide gets you started with gRPC in PHP with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
- PHP 5.5 or higher, 7.0 or higher
|
||||
|
|
@ -82,8 +80,9 @@ or specific version
|
|||
sudo pecl install grpc-1.7.0
|
||||
```
|
||||
|
||||
Note: for users on CentOS/RHEL 6, unfortunately this step won’t work.
|
||||
Please follow the instructions below to compile the PECL extension from source.
|
||||
{{< warning >}}
|
||||
This step unfortunately won’t work on CentOS/RHEL 6. Please follow the instructions below to compile the PECL extension from source.
|
||||
{{< /warning >}}
|
||||
|
||||
##### Install on Windows
|
||||
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: Python
|
|||
description: This guide gets you started with gRPC in Python with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
- Python 2.7, or Python 3.4 or higher
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: Ruby
|
|||
description: This guide gets you started with gRPC in Ruby with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
- Ruby version 2 or higher
|
||||
|
|
|
|||
|
|
@ -5,8 +5,6 @@ short: Web
|
|||
description: This guide gets you started with gRPC-Web with a simple working example.
|
||||
---
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Prerequisites
|
||||
|
||||
- `docker`
|
||||
|
|
|
|||
|
|
@ -1,24 +0,0 @@
|
|||
---
|
||||
bodyclass: docs
|
||||
headline: 'Language Specific API Reference'
|
||||
layout: docs
|
||||
title: Reference
|
||||
type: markdown
|
||||
weight: 4
|
||||
---
|
||||
<p class="lead">Links to the language specific automatically generated API reference documentation.</p>
|
||||
|
||||
<ul>
|
||||
<li><a target="_blank" href="/grpc/cpp/index.html">C++ API</a></li>
|
||||
<li><a target="_blank" href="https://pub.dev/documentation/grpc">Dart API</a></li>
|
||||
<li><a target="_blank" href="/grpc-java/javadoc/index.html">Java API</a></li>
|
||||
<li><a target="_blank" href="/grpc/python/">Python API</a></li>
|
||||
<li><a target="_blank" href="http://www.rubydoc.info/gems/grpc">Ruby API</a></li>
|
||||
<li><a target="_blank" href="/grpc/node/">Node.js API</a></li>
|
||||
<li><a target="_blank" href="/grpc/csharp/api/Grpc.Core.html">C# API ("gRPC C#" implementation)</a></li>
|
||||
<li><a target="_blank" href="/grpc/csharp-dotnet/api/Grpc.Core.html">C# API ("grpc-dotnet" implementation)</a></li>
|
||||
<li><a target="_blank" href="https://godoc.org/google.golang.org/grpc">Go API</a></li>
|
||||
<li><a target="_blank" href="/grpc/php/namespace-Grpc.html">PHP API</a></li>
|
||||
<li><a target="_blank" href="/grpc/objc/index.html">Objective-C API</a></li>
|
||||
<li><a target="_blank" href="/grpc/core/">gRPC Core Library (for wrapped languages)</a></ul></li>
|
||||
</ul>
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
---
|
||||
title: Reference
|
||||
weight: 4
|
||||
---
|
||||
|
||||
Language-specific, automatically generated API reference documentation is available for the following languages and platforms:
|
||||
|
||||
{{< api-links >}}
|
||||
|
|
@ -1,15 +0,0 @@
|
|||
---
|
||||
bodyclass: docs
|
||||
headline: C++ Client Reference
|
||||
layout: docs
|
||||
title: C++ Client Reference
|
||||
---
|
||||
|
||||
<p class="lead">Being familiar with these will go a long way.</p>
|
||||
|
||||
<p>Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod
|
||||
tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,
|
||||
quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo
|
||||
consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse
|
||||
cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non
|
||||
proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>
|
||||
|
|
@ -1,15 +0,0 @@
|
|||
---
|
||||
bodyclass: docs
|
||||
headline: C++ Server Reference
|
||||
layout: docs
|
||||
title: C++ Server Reference
|
||||
---
|
||||
|
||||
<p class="lead">Being familiar with these will go a long way.</p>
|
||||
|
||||
<p>Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod
|
||||
tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,
|
||||
quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo
|
||||
consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse
|
||||
cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non
|
||||
proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>
|
||||
|
|
@ -1,9 +1,6 @@
|
|||
---
|
||||
bodyclass: docs
|
||||
headline: Go Generated Code Reference
|
||||
layout: docs
|
||||
title: Go Generated Code Reference
|
||||
---
|
||||
# Go Generated Code Reference
|
||||
|
||||
This guide describes the code generated with the [grpc plugin](https://godoc.org/github.com/golang/protobuf/protoc-gen-go/grpc) to `protoc-gen-go`
|
||||
when compiling `.proto` files with `protoc`.
|
||||
|
|
|
|||
|
|
@ -1,15 +0,0 @@
|
|||
---
|
||||
bodyclass: docs
|
||||
layout: docs
|
||||
title: Java Client Reference
|
||||
---
|
||||
|
||||
<h2 class="page-header">Java Client Reference</h2>
|
||||
<p class="lead">Being familiar with these will go a long way.</p>
|
||||
|
||||
<p>Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod
|
||||
tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,
|
||||
quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo
|
||||
consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse
|
||||
cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non
|
||||
proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>
|
||||
|
|
@ -1,9 +1,6 @@
|
|||
---
|
||||
bodyclass: docs
|
||||
title: Java Generated Code Reference
|
||||
layout: docs
|
||||
---
|
||||
# Java Generated Code Reference
|
||||
|
||||
## Packages
|
||||
|
||||
|
|
|
|||
|
|
@ -1,14 +0,0 @@
|
|||
---
|
||||
bodyclass: docs
|
||||
layout: docs
|
||||
title: Java Server Reference
|
||||
headline : Java Server Reference
|
||||
---
|
||||
<p class="lead">Being familiar with these will go a long way.</p>
|
||||
|
||||
<p>Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod
|
||||
tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam,
|
||||
quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo
|
||||
consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse
|
||||
cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non
|
||||
proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>
|
||||
|
|
@ -1,11 +1,7 @@
|
|||
---
|
||||
bodyclass: docs
|
||||
layout: docs
|
||||
headline: Python Generated Code Reference
|
||||
title: Python Generated Code Reference
|
||||
---
|
||||
|
||||
# Python Generated Code Reference
|
||||
|
||||
## Introduction
|
||||
|
||||
gRPC Python relies on the protocol buffers compiler (`protoc`) to generate
|
||||
|
|
@ -121,7 +117,7 @@ generated:
|
|||
|
||||
### Stub
|
||||
|
||||
<a name="stub"></a>The generated `Stub` class is used by the gRPC clients. It
|
||||
The generated `Stub` class is used by the gRPC clients. It
|
||||
will have a constructor that takes a `grpc.Channel` object and initializes the
|
||||
stub. For each method in the service, the initializer adds a corresponding
|
||||
attribute to the stub object with the same name. Depending on the RPC type
|
||||
|
|
@ -135,7 +131,7 @@ or
|
|||
|
||||
### Servicer
|
||||
|
||||
<a name="servicer"></a>For each service, a `Servicer` class is generated. This
|
||||
For each service, a `Servicer` class is generated. This
|
||||
class is intended to serve as the superclass of a service implementation. For
|
||||
each method in the service, a corresponding function in the `Servicer` class
|
||||
will be synthesized which is intended to be overriden in the actual service
|
||||
|
|
@ -145,7 +141,7 @@ the generated python code.
|
|||
|
||||
### Registration Function
|
||||
|
||||
<a name="registration-function"></a>For each service, a function will be
|
||||
For each service, a function will be
|
||||
generated that registers a `Servicer` object implementing it on a `grpc.Server`
|
||||
object, so that the server would be able to appropriately route the queries to
|
||||
the respective servicer. This function takes an object that implements the
|
||||
|
|
|
|||
|
|
@ -14,8 +14,6 @@ from the basic [Greeter example](https://github.com/grpc/grpc/tree/{{< param grp
|
|||
instructions in
|
||||
[grpc/examples/cpp/helloworld](https://github.com/grpc/grpc/tree/{{< param grpc_release_tag >}}/examples/cpp/helloworld).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Overview
|
||||
|
||||
gRPC uses the
|
||||
|
|
@ -38,30 +36,30 @@ the following to make an asynchronous call:
|
|||
- Initiate the RPC and create a handle for it. Bind the RPC to a
|
||||
`CompletionQueue`.
|
||||
|
||||
```c
|
||||
```c
|
||||
CompletionQueue cq;
|
||||
std::unique_ptr<ClientAsyncResponseReader<HelloReply> > rpc(
|
||||
stub_->AsyncSayHello(&context, request, &cq));
|
||||
```
|
||||
```
|
||||
|
||||
- Ask for the reply and final status, with a unique tag
|
||||
|
||||
```c
|
||||
```c
|
||||
Status status;
|
||||
rpc->Finish(&reply, &status, (void*)1);
|
||||
```
|
||||
```
|
||||
|
||||
- Wait for the completion queue to return the next tag. The reply and status are
|
||||
ready once the tag passed into the corresponding `Finish()` call is returned.
|
||||
|
||||
```c
|
||||
```c
|
||||
void* got_tag;
|
||||
bool ok = false;
|
||||
cq.Next(&got_tag, &ok);
|
||||
if (ok && got_tag == (void*)1) {
|
||||
// check reply and status
|
||||
}
|
||||
```
|
||||
```
|
||||
|
||||
You can see the complete client example in
|
||||
[greeter_async_client.cc](https://github.com/grpc/grpc/blob/{{< param grpc_release_tag >}}/examples/cpp/helloworld/greeter_async_client.cc).
|
||||
|
|
@ -74,28 +72,28 @@ asynchronously is:
|
|||
|
||||
- Build a server exporting the async service
|
||||
|
||||
```c
|
||||
```c
|
||||
helloworld::Greeter::AsyncService service;
|
||||
ServerBuilder builder;
|
||||
builder.AddListeningPort("0.0.0.0:50051", InsecureServerCredentials());
|
||||
builder.RegisterAsyncService(&service);
|
||||
auto cq = builder.AddCompletionQueue();
|
||||
auto server = builder.BuildAndStart();
|
||||
```
|
||||
```
|
||||
|
||||
- Request one RPC, providing a unique tag
|
||||
|
||||
```c
|
||||
```c
|
||||
ServerContext context;
|
||||
HelloRequest request;
|
||||
ServerAsyncResponseWriter<HelloReply> responder;
|
||||
service.RequestSayHello(&context, &request, &responder, &cq, &cq, (void*)1);
|
||||
```
|
||||
```
|
||||
|
||||
- Wait for the completion queue to return the tag. The context, request and
|
||||
responder are ready once the tag is retrieved.
|
||||
|
||||
```c
|
||||
```c
|
||||
HelloReply reply;
|
||||
Status status;
|
||||
void* got_tag;
|
||||
|
|
@ -105,19 +103,19 @@ asynchronously is:
|
|||
// set reply and status
|
||||
responder.Finish(reply, status, (void*)2);
|
||||
}
|
||||
```
|
||||
```
|
||||
|
||||
- Wait for the completion queue to return the tag. The RPC is finished when the
|
||||
tag is back.
|
||||
|
||||
```c
|
||||
```c
|
||||
void* got_tag;
|
||||
bool ok = false;
|
||||
cq.Next(&got_tag, &ok);
|
||||
if (ok && got_tag == (void*)2) {
|
||||
// clean up
|
||||
}
|
||||
```
|
||||
```
|
||||
|
||||
This basic flow, however, doesn't take into account the server handling multiple
|
||||
requests concurrently. To deal with this, our complete async server example uses
|
||||
|
|
@ -125,73 +123,74 @@ a `CallData` object to maintain the state of each RPC, and uses the address of
|
|||
this object as the unique tag for the call.
|
||||
|
||||
```c
|
||||
class CallData {
|
||||
public:
|
||||
// Take in the "service" instance (in this case representing an asynchronous
|
||||
// server) and the completion queue "cq" used for asynchronous communication
|
||||
// with the gRPC runtime.
|
||||
CallData(Greeter::AsyncService* service, ServerCompletionQueue* cq)
|
||||
: service_(service), cq_(cq), responder_(&ctx_), status_(CREATE) {
|
||||
// Invoke the serving logic right away.
|
||||
Proceed();
|
||||
}
|
||||
class CallData {
|
||||
public:
|
||||
// Take in the "service" instance (in this case representing an asynchronous
|
||||
// server) and the completion queue "cq" used for asynchronous communication
|
||||
// with the gRPC runtime.
|
||||
CallData(Greeter::AsyncService* service, ServerCompletionQueue* cq)
|
||||
: service_(service), cq_(cq), responder_(&ctx_), status_(CREATE) {
|
||||
// Invoke the serving logic right away.
|
||||
Proceed();
|
||||
}
|
||||
|
||||
void Proceed() {
|
||||
if (status_ == CREATE) {
|
||||
// As part of the initial CREATE state, we *request* that the system
|
||||
// start processing SayHello requests. In this request, "this" acts are
|
||||
// the tag uniquely identifying the request (so that different CallData
|
||||
// instances can serve different requests concurrently), in this case
|
||||
// the memory address of this CallData instance.
|
||||
service_->RequestSayHello(&ctx_, &request_, &responder_, cq_, cq_,
|
||||
this);
|
||||
// Make this instance progress to the PROCESS state.
|
||||
status_ = PROCESS;
|
||||
} else if (status_ == PROCESS) {
|
||||
// Spawn a new CallData instance to serve new clients while we process
|
||||
// the one for this CallData. The instance will deallocate itself as
|
||||
// part of its FINISH state.
|
||||
new CallData(service_, cq_);
|
||||
void Proceed() {
|
||||
if (status_ == CREATE) {
|
||||
// As part of the initial CREATE state, we *request* that the system
|
||||
// start processing SayHello requests. In this request, "this" acts are
|
||||
// the tag uniquely identifying the request (so that different CallData
|
||||
// instances can serve different requests concurrently), in this case
|
||||
// the memory address of this CallData instance.
|
||||
service_->RequestSayHello(&ctx_, &request_, &responder_, cq_, cq_,
|
||||
this);
|
||||
// Make this instance progress to the PROCESS state.
|
||||
status_ = PROCESS;
|
||||
} else if (status_ == PROCESS) {
|
||||
// Spawn a new CallData instance to serve new clients while we process
|
||||
// the one for this CallData. The instance will deallocate itself as
|
||||
// part of its FINISH state.
|
||||
new CallData(service_, cq_);
|
||||
|
||||
// The actual processing.
|
||||
std::string prefix("Hello ");
|
||||
reply_.set_message(prefix + request_.name());
|
||||
// The actual processing.
|
||||
std::string prefix("Hello ");
|
||||
reply_.set_message(prefix + request_.name());
|
||||
|
||||
// And we are done! Let the gRPC runtime know we've finished, using the
|
||||
// memory address of this instance as the uniquely identifying tag for
|
||||
// the event.
|
||||
responder_.Finish(reply_, Status::OK, this);
|
||||
status_ = FINISH;
|
||||
} else {
|
||||
GPR_ASSERT(status_ == FINISH);
|
||||
// Once in the FINISH state, deallocate ourselves (CallData).
|
||||
delete this;
|
||||
}
|
||||
// And we are done! Let the gRPC runtime know we've finished, using the
|
||||
// memory address of this instance as the uniquely identifying tag for
|
||||
// the event.
|
||||
responder_.Finish(reply_, Status::OK, this);
|
||||
status_ = FINISH;
|
||||
} else {
|
||||
GPR_ASSERT(status_ == FINISH);
|
||||
// Once in the FINISH state, deallocate ourselves (CallData).
|
||||
delete this;
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
For simplicity the server only uses one completion queue for all events, and
|
||||
runs a main loop in `HandleRpcs` to query the queue:
|
||||
|
||||
```c
|
||||
void HandleRpcs() {
|
||||
// Spawn a new CallData instance to serve new clients.
|
||||
new CallData(&service_, cq_.get());
|
||||
void* tag; // uniquely identifies a request.
|
||||
bool ok;
|
||||
while (true) {
|
||||
// Block waiting to read the next event from the completion queue. The
|
||||
// event is uniquely identified by its tag, which in this case is the
|
||||
// memory address of a CallData instance.
|
||||
cq_->Next(&tag, &ok);
|
||||
GPR_ASSERT(ok);
|
||||
static_cast<CallData*>(tag)->Proceed();
|
||||
}
|
||||
void HandleRpcs() {
|
||||
// Spawn a new CallData instance to serve new clients.
|
||||
new CallData(&service_, cq_.get());
|
||||
void* tag; // uniquely identifies a request.
|
||||
bool ok;
|
||||
while (true) {
|
||||
// Block waiting to read the next event from the completion queue. The
|
||||
// event is uniquely identified by its tag, which in this case is the
|
||||
// memory address of a CallData instance.
|
||||
cq_->Next(&tag, &ok);
|
||||
GPR_ASSERT(ok);
|
||||
static_cast<CallData*>(tag)->Proceed();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### Shutting Down the Server
|
||||
|
||||
We've been using a completion queue to get the async notifications. Care must be
|
||||
taken to shut it down *after* the server has also been shut down.
|
||||
|
||||
|
|
@ -206,11 +205,11 @@ Refer to `ServerBuilder::AddCompletionQueue`'s full docstring for more details.
|
|||
What this means in our example is that `ServerImpl's` destructor looks like:
|
||||
|
||||
```c
|
||||
~ServerImpl() {
|
||||
server_->Shutdown();
|
||||
// Always shutdown the completion queue after the server.
|
||||
cq_->Shutdown();
|
||||
}
|
||||
~ServerImpl() {
|
||||
server_->Shutdown();
|
||||
// Always shutdown the completion queue after the server.
|
||||
cq_->Shutdown();
|
||||
}
|
||||
```
|
||||
|
||||
You can see our complete server example in
|
||||
|
|
|
|||
|
|
@ -22,11 +22,7 @@ Objective-C](/docs/tutorials/basic/objective-c/) and the
|
|||
[overview](/docs/), and are familiar with OAuth2 concepts like _access
|
||||
token_.
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
<a name="setup"></a>
|
||||
|
||||
### Example code and setup
|
||||
### Example code and setup {#setup}
|
||||
|
||||
The example code for our tutorial is in
|
||||
[gprc/examples/objective-c/auth_sample](https://github.com/grpc/grpc/tree/
|
||||
|
|
@ -53,23 +49,22 @@ expects Google account credentials, but neither gRPC nor the Objective-C client
|
|||
library is tied to any specific OAuth2 provider). The second view makes a gRPC
|
||||
request to the test server, using the access token obtained by the first view.
|
||||
|
||||
Note: OAuth2 libraries need the application to register and obtain an ID from
|
||||
{{< note >}}
|
||||
OAuth2 libraries need the application to register and obtain an ID from
|
||||
the identity provider (in the case of this example app, Google). The app's XCode
|
||||
project is configured using that ID, so you shouldn't copy this project "as is"
|
||||
for your own app: it would result in your app being identified in the consent
|
||||
screen as "gRPC-AuthSample", and not having access to real Google services.
|
||||
Instead, configure your own XCode project following the [instructions
|
||||
here](https://developers.google.com/identity/sign-in/ios/).
|
||||
{{< /note >}}
|
||||
|
||||
As with the other Objective-C examples, you also should have
|
||||
[Cocoapods](https://cocoapods.org/#install) installed, as well as the relevant
|
||||
tools to generate the client library code. You can obtain the latter by
|
||||
following [these setup instructions](https://github.com/grpc/homebrew-grpc).
|
||||
|
||||
|
||||
<a name="try"></a>
|
||||
|
||||
### Try it out!
|
||||
### Try it out! {#try}
|
||||
|
||||
To try the sample app, first have Cocoapods generate and install the client library for our .proto
|
||||
files:
|
||||
|
|
@ -105,9 +100,7 @@ The next sections guide you step-by-step through how the gRPC call in
|
|||
`MakeRPCViewController` is performed. You can see the complete code in
|
||||
[MakeRPCViewController.m](https://github.com/grpc/grpc/blob/{{< param grpc_release_tag >}}/examples/objective-c/auth_sample/MakeRPCViewController.m).
|
||||
|
||||
<a name="rpc-call"></a>
|
||||
|
||||
### Create a call with access token
|
||||
### Create a call with access token {#rpc-call}
|
||||
|
||||
To make an authenticated call, first you need to initialize a `GRPCCallOptions` object and configure
|
||||
it with the access token.
|
||||
|
|
@ -151,9 +144,8 @@ You can then start the RPC represented by this object at any later time like thi
|
|||
[rpc start];
|
||||
```
|
||||
|
||||
<a name="authorization-protocol">
|
||||
### An alternative way to provide access token {#authorization-protocol}
|
||||
|
||||
### An alternative way to provide access token
|
||||
Rather than setting `oauth2AccessToken` option in `GRPCCallOptions` before the RPC object is
|
||||
created, an alternative approach allows users providing access token at call start time.
|
||||
|
||||
|
|
|
|||
|
|
@ -16,8 +16,6 @@ By walking through this example you'll learn how to:
|
|||
It assumes that you have read the [Overview](/docs/) and are familiar with [protocol buffers](https://developers.google.com/protocol-buffers/docs/overview).
|
||||
This guide also does not cover anything on the server side. You can check the [Java guide](/docs/tutorials/basic/java/) for more information.
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Why use gRPC?
|
||||
|
||||
Our example is a simple route mapping application that lets clients get information about features on their route, create a summary of their route, and exchange route information such as traffic updates with the server and other clients.
|
||||
|
|
|
|||
|
|
@ -23,8 +23,6 @@ guide](https://developers.google.com/protocol-buffers/docs/proto3) and [C++
|
|||
generated code
|
||||
guide](https://developers.google.com/protocol-buffers/docs/reference/cpp-generated).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Why use gRPC?
|
||||
|
||||
Our example is a simple route mapping application that lets clients get
|
||||
|
|
@ -193,9 +191,7 @@ These contain:
|
|||
defined in the `RouteGuide` service.
|
||||
|
||||
|
||||
<a name="server"></a>
|
||||
|
||||
### Creating the server
|
||||
### Creating the server {#server}
|
||||
|
||||
First let's look at how we create a `RouteGuide` server. If you're only
|
||||
interested in creating gRPC clients, you can skip this section and go straight
|
||||
|
|
@ -361,9 +357,7 @@ As you can see, we build and start our server using a `ServerBuilder`. To do thi
|
|||
6. Call `Wait()` on the server to do a blocking wait until process is killed or
|
||||
`Shutdown()` is called.
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
### Creating the client
|
||||
### Creating the client {#client}
|
||||
|
||||
In this section, we'll look at creating a C++ client for our `RouteGuide`
|
||||
service. You can see our complete example client code in
|
||||
|
|
@ -380,7 +374,10 @@ address and port we want to connect to - in our case we'll use no SSL:
|
|||
```cpp
|
||||
grpc::CreateChannel("localhost:50051", grpc::InsecureChannelCredentials());
|
||||
```
|
||||
Note: In order to set additional options for the *channel*, use the `grpc::CreateCustomChannel()` api with any special channel arguments - `grpc::ChannelArguments`
|
||||
|
||||
{{< note >}}
|
||||
In order to set additional options for the *channel*, use the `grpc::CreateCustomChannel()` api with any special channel arguments - `grpc::ChannelArguments`.
|
||||
{{< /note >}}
|
||||
|
||||
Now we can use the channel to create our stub using the `NewStub` method provided in the `RouteGuide` class we generated from our .proto.
|
||||
|
||||
|
|
|
|||
|
|
@ -20,8 +20,6 @@ language: you can find out more in the
|
|||
[proto3 language guide](https://developers.google.com/protocol-buffers/docs/proto3) and
|
||||
[C# generated code reference](https://developers.google.com/protocol-buffers/docs/reference/csharp-generated).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Why use gRPC?
|
||||
|
||||
Our example is a simple route mapping application that lets clients get
|
||||
|
|
@ -170,10 +168,7 @@ under the `RouteGuide/obj/Debug/TARGET_FRAMEWORK` directory:
|
|||
- a class `RouteGuide.RouteGuideClient` that can be used to access remote
|
||||
RouteGuide instances
|
||||
|
||||
|
||||
<a name="server"></a>
|
||||
|
||||
### Creating the server
|
||||
### Creating the server {#server}
|
||||
|
||||
First let's look at how we create a `RouteGuide` server. If you're only
|
||||
interested in creating gRPC clients, you can skip this section and go straight
|
||||
|
|
@ -353,9 +348,7 @@ do this, we:
|
|||
This is done by adding `ServerPort` to the `Ports` collection.
|
||||
1. Call `Start` on the server instance to start an RPC server for our service.
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
### Creating the client
|
||||
### Creating the client {#client}
|
||||
|
||||
In this section, we'll look at creating a C# client for our `RouteGuide`
|
||||
service. You can see our complete example client code in
|
||||
|
|
|
|||
|
|
@ -20,8 +20,6 @@ language: you can find out more in the
|
|||
[proto3 language
|
||||
guide](https://developers.google.com/protocol-buffers/docs/proto3).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Why use gRPC?
|
||||
|
||||
Our example is a simple route mapping application that lets clients get
|
||||
|
|
@ -170,10 +168,7 @@ This contains:
|
|||
- An interface type for servers to implement, also with the methods defined in
|
||||
the `RouteGuide` service.
|
||||
|
||||
|
||||
<a name="server"></a>
|
||||
|
||||
### Creating the server
|
||||
### Creating the server {#server}
|
||||
|
||||
First let's look at how we create a `RouteGuide` server. If you're only
|
||||
interested in creating gRPC clients, you can skip this section and go straight
|
||||
|
|
@ -380,9 +375,7 @@ To build and start a server, we:
|
|||
in the address and port to listen on. The server will continue to serve requests
|
||||
asynchronously until `shutdown()` is called on it.
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
### Creating the client
|
||||
### Creating the client {#client}
|
||||
|
||||
In this section, we'll look at creating a Dart client for our `RouteGuide`
|
||||
service. You can see our complete example client code in
|
||||
|
|
|
|||
|
|
@ -22,8 +22,6 @@ guide](https://developers.google.com/protocol-buffers/docs/proto3) and the [Go
|
|||
generated code
|
||||
guide](https://developers.google.com/protocol-buffers/docs/reference/go-generated).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Why use gRPC?
|
||||
|
||||
Our example is a simple route mapping application that lets clients get
|
||||
|
|
@ -170,10 +168,7 @@ This contains:
|
|||
- An interface type for servers to implement, also with the methods defined in
|
||||
the `RouteGuide` service.
|
||||
|
||||
|
||||
<a name="server"></a>
|
||||
|
||||
### Creating the server
|
||||
### Creating the server {#server}
|
||||
|
||||
First let's look at how we create a `RouteGuide` server. If you're only
|
||||
interested in creating gRPC clients, you can skip this section and go straight
|
||||
|
|
@ -392,9 +387,7 @@ To build and start a server, we:
|
|||
4. Call `Serve()` on the server with our port details to do a blocking wait
|
||||
until the process is killed or `Stop()` is called.
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
### Creating the client
|
||||
### Creating the client {#client}
|
||||
|
||||
In this section, we'll look at creating a Go client for our `RouteGuide`
|
||||
service. You can see our complete example client code in
|
||||
|
|
|
|||
|
|
@ -23,8 +23,6 @@ guide](https://developers.google.com/protocol-buffers/docs/proto3) and [Java
|
|||
generated code
|
||||
guide](https://developers.google.com/protocol-buffers/docs/reference/java-generated).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Why use gRPC?
|
||||
|
||||
Our example is a simple route mapping application that lets clients get
|
||||
|
|
@ -179,9 +177,7 @@ The following classes are generated from our service definition:
|
|||
`RouteGuide` service.
|
||||
- *stub* classes that clients can use to talk to a `RouteGuide` server.
|
||||
|
||||
<a name="server"></a>
|
||||
|
||||
### Creating the server
|
||||
### Creating the server {#server}
|
||||
|
||||
First let's look at how we create a `RouteGuide` server. If you're only
|
||||
interested in creating gRPC clients, you can skip this section and go straight
|
||||
|
|
@ -434,9 +430,7 @@ To do this, we:
|
|||
1. Call `build()` and `start()` on the builder to create and start an RPC server
|
||||
for our service.
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
## Creating the client
|
||||
## Creating the client {#client}
|
||||
|
||||
In this section, we'll look at creating a Java client for our `RouteGuide`
|
||||
service. You can see our complete example client code in
|
||||
|
|
|
|||
|
|
@ -20,8 +20,6 @@ that the example in this tutorial uses the
|
|||
buffers language. You can find out more in the
|
||||
[proto3 language guide](https://developers.google.com/protocol-buffers/docs/proto3).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Why use gRPC?
|
||||
|
||||
Our example is a simple route mapping application that lets clients get
|
||||
|
|
@ -191,9 +189,7 @@ Once you've done this, the stub constructor is in the `routeguide` namespace
|
|||
used to create a server) is a property of the stub
|
||||
(`protoDescriptor.routeguide.RouteGuide.service`);
|
||||
|
||||
<a name="server"></a>
|
||||
|
||||
### Creating the server
|
||||
### Creating the server {#server}
|
||||
|
||||
First let's look at how we create a `RouteGuide` server. If you're only
|
||||
interested in creating gRPC clients, you can skip this section and go straight
|
||||
|
|
@ -368,9 +364,7 @@ As you can see, we build and start our server with the following steps:
|
|||
using the instance's `bind()` method.
|
||||
1. Call `start()` on the instance to start the RPC server.
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
### Creating the client
|
||||
### Creating the client {#client}
|
||||
|
||||
In this section, we'll look at creating a Node.js client for our `RouteGuide`
|
||||
service. You can see our complete example client code in
|
||||
|
|
|
|||
|
|
@ -22,11 +22,7 @@ guide](https://developers.google.com/protocol-buffers/docs/proto3) and the
|
|||
[Objective-C generated code
|
||||
guide](https://developers.google.com/protocol-buffers/docs/reference/objective-c-generated).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
<a name="why-grpc"></a>
|
||||
|
||||
### Why use gRPC?
|
||||
### Why use gRPC? {#why-grpc}
|
||||
|
||||
With gRPC you can define your service once in a .proto file and implement
|
||||
clients and servers in any of gRPC's supported languages, which in turn can be
|
||||
|
|
@ -44,10 +40,7 @@ that has been optimized over the years at Google to keep code size to a minimum.
|
|||
The latter is important in Objective-C, because the ability of the compiler to
|
||||
strip unused code is limited by the dynamic nature of the language.
|
||||
|
||||
|
||||
<a name="setup"></a>
|
||||
|
||||
### Example code and setup
|
||||
### Example code and setup {#setup}
|
||||
|
||||
The example code for our tutorial is in
|
||||
[grpc/grpc/examples/objective-c/route_guide](https://github.com/grpc/grpc/tree/{{< param grpc_release_tag >}}/examples/objective-c/route_guide).
|
||||
|
|
@ -76,10 +69,7 @@ well as the relevant tools to generate the client library code (and a server in
|
|||
another language, for testing). You can obtain the latter by following [these
|
||||
setup instructions](https://github.com/grpc/homebrew-grpc).
|
||||
|
||||
|
||||
<a name="try"></a>
|
||||
|
||||
## Try it out!
|
||||
## Try it out! {#try}
|
||||
|
||||
To try the sample app, we need a gRPC server running locally. Let's compile and
|
||||
run, for example, the C++ server in this repository:
|
||||
|
|
@ -108,10 +98,7 @@ The next sections guide you step-by-step through how this proto service is
|
|||
defined, how to generate a client library from it, and how to create an app that
|
||||
uses that library.
|
||||
|
||||
|
||||
<a name="proto"></a>
|
||||
|
||||
### Defining the service
|
||||
### Defining the service {#proto}
|
||||
|
||||
First let's look at how the service we're using is defined. A gRPC *service* and
|
||||
its method *request* and *response* types using [protocol
|
||||
|
|
@ -200,9 +187,7 @@ You can specify a prefix to be used for your generated classes by adding the
|
|||
option objc_class_prefix = "RTG";
|
||||
```
|
||||
|
||||
<a name="protoc"></a>
|
||||
|
||||
### Generating client code
|
||||
### Generating client code {#protoc}
|
||||
|
||||
Next we need to generate the gRPC client interfaces from our .proto service
|
||||
definition. We do this using the protocol buffer compiler (`protoc`) with a
|
||||
|
|
@ -246,17 +231,17 @@ You can also use the provided Podspec file to generate client code from any
|
|||
other proto service definition; just replace the name (matching the file name),
|
||||
version, and other metadata.
|
||||
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
### Creating the client application
|
||||
### Creating the client application {#client}
|
||||
|
||||
In this section, we'll look at creating an Objective-C client for our
|
||||
`RouteGuide` service. You can see our complete example client code in
|
||||
[examples/objective-c/route_guide/ViewControllers.m](https://github.com/grpc/grpc/blob/{{< param grpc_release_tag >}}/examples/objective-c/route_guide/ViewControllers.m).
|
||||
(Note: In your apps, for maintainability and readability reasons, you shouldn't
|
||||
|
||||
{{< note >}}
|
||||
In your apps, for maintainability and readability reasons, you shouldn't
|
||||
put all of your view controllers in a single file; it's done here only to
|
||||
simplify the learning process).
|
||||
{{< /note >}}
|
||||
|
||||
#### Constructing a service object
|
||||
|
||||
|
|
|
|||
|
|
@ -22,11 +22,7 @@ Also note that currently you can only create clients in PHP for gRPC services -
|
|||
you can find out how to create gRPC servers in our other tutorials, e.g.
|
||||
[Node.js](/docs/tutorials/basic/node/).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
<a name="why-grpc"></a>
|
||||
|
||||
### Why use gRPC?
|
||||
### Why use gRPC? {#why-grpcc}
|
||||
|
||||
With gRPC you can define your service once in a .proto file and implement
|
||||
clients and servers in any of gRPC's supported languages, which in turn can be
|
||||
|
|
@ -36,10 +32,7 @@ handled for you by gRPC. You also get all the advantages of working with
|
|||
protocol buffers, including efficient serialization, a simple IDL, and easy
|
||||
interface updating.
|
||||
|
||||
|
||||
<a name="setup"></a>
|
||||
|
||||
### Example code and setup
|
||||
### Example code and setup {#setup}
|
||||
|
||||
The example code for our tutorial is in
|
||||
[grpc/grpc/examples/php/route_guide](https://github.com/grpc/grpc/tree/{{< param grpc_release_tag >}}/examples/php/route_guide).
|
||||
|
|
@ -73,10 +66,7 @@ interface code (and a server in another language, for testing). You can obtain
|
|||
the latter by following [these setup
|
||||
instructions](/docs/tutorials/basic/node/).
|
||||
|
||||
|
||||
<a name="try"></a>
|
||||
|
||||
### Try it out!
|
||||
### Try it out! {#try}
|
||||
|
||||
To try the sample app, we need a gRPC server running locally. Let's compile and
|
||||
run, for example, the Node.js server in this repository:
|
||||
|
|
@ -98,10 +88,7 @@ The next sections guide you step-by-step through how this proto service is
|
|||
defined, how to generate a client library from it, and how to create a client
|
||||
stub that uses that library.
|
||||
|
||||
|
||||
<a name="proto"></a>
|
||||
|
||||
### Defining the service
|
||||
### Defining the service {#proto}
|
||||
|
||||
First let's look at how the service we're using is defined. A gRPC *service* and
|
||||
its method *request* and *response* types using [protocol
|
||||
|
|
@ -183,10 +170,7 @@ message Point {
|
|||
}
|
||||
```
|
||||
|
||||
|
||||
<a name="protoc"></a>
|
||||
|
||||
### Generating client code
|
||||
### Generating client code {#protoc}
|
||||
|
||||
The PHP client stub implementation of the proto files can be generated by the
|
||||
gRPC PHP Protoc Plugin. To compile the plugin:
|
||||
|
|
@ -234,10 +218,7 @@ The file contains:
|
|||
- A class called `Routeguide\RouteGuideClient` that lets clients call the methods
|
||||
defined in the `RouteGuide` service.
|
||||
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
### Creating the client
|
||||
### Creating the client {#client}
|
||||
|
||||
In this section, we'll look at creating a PHP client for our `RouteGuide`
|
||||
service. You can see our complete example client code in
|
||||
|
|
|
|||
|
|
@ -21,8 +21,6 @@ guide](https://developers.google.com/protocol-buffers/docs/proto3) and [Python
|
|||
generated code
|
||||
guide](https://developers.google.com/protocol-buffers/docs/reference/python-generated).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Why use gRPC?
|
||||
|
||||
This example is a simple route mapping application that lets clients get
|
||||
|
|
@ -175,11 +173,11 @@ than creates a new one. The generated code files are called
|
|||
- `add_RouteGuideServicer_to_server`, which adds a RouteGuideServicer to
|
||||
a `grpc.Server`
|
||||
|
||||
Note: The `2` in pb2 indicates that the generated code is following Protocol Buffers Python API version 2. Version 1 is obsolete. It has no relation to the Protocol Buffers Language version, which is the one indicated by `syntax = "proto3"` or `syntax = "proto2"` in a .proto file.
|
||||
{{< note >}}
|
||||
The `2` in pb2 indicates that the generated code is following Protocol Buffers Python API version 2. Version 1 is obsolete. It has no relation to the Protocol Buffers Language version, which is the one indicated by `syntax = "proto3"` or `syntax = "proto2"` in a .proto file.
|
||||
{{< /note >}}
|
||||
|
||||
<a name="server"></a>
|
||||
|
||||
### Creating the server
|
||||
### Creating the server {#server}
|
||||
|
||||
First let's look at how you create a `RouteGuide` server. If you're only
|
||||
interested in creating gRPC clients, you can skip this section and go straight
|
||||
|
|
@ -313,9 +311,7 @@ def serve():
|
|||
Because `start()` does not block you may need to sleep-loop if there is nothing
|
||||
else for your code to do while serving.
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
### Creating the client
|
||||
### Creating the client {#client}
|
||||
|
||||
You can see the complete example client code in
|
||||
[examples/python/route_guide/route_guide_client.py](https://github.com/grpc/grpc/blob/{{< param grpc_release_tag >}}/examples/python/route_guide/route_guide_client.py).
|
||||
|
|
|
|||
|
|
@ -20,8 +20,6 @@ buffers language: you can find out more in
|
|||
the [proto3 language
|
||||
guide](https://developers.google.com/protocol-buffers/docs/proto3).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
### Why use gRPC?
|
||||
|
||||
Our example is a simple route mapping application that lets clients get
|
||||
|
|
@ -171,10 +169,7 @@ Running this command regenerates the following files in the lib directory:
|
|||
implementations
|
||||
- a class `Stub` that can be used to access remote RouteGuide instances
|
||||
|
||||
|
||||
<a name="server"></a>
|
||||
|
||||
### Creating the server
|
||||
### Creating the server {#server}
|
||||
|
||||
First let's look at how we create a `RouteGuide` server. If you're only
|
||||
interested in creating gRPC clients, you can skip this section and go straight
|
||||
|
|
@ -288,9 +283,7 @@ this, we:
|
|||
1. Call `run` on the`GRPC::RpcServer` to create and start an RPC server for our
|
||||
service.
|
||||
|
||||
<a name="client"></a>
|
||||
|
||||
### Creating the client
|
||||
### Creating the client {#client}
|
||||
|
||||
In this section, we'll look at creating a Ruby client for our `RouteGuide`
|
||||
service. You can see our complete example client code in
|
||||
|
|
@ -394,7 +387,9 @@ Run the server:
|
|||
$ bundle exec route_guide/route_guide_server.rb ../python/route_guide/route_guide_db.json
|
||||
```
|
||||
|
||||
> Note: The `route_guide_db.json` file is actually language-agnostic, it happens to be located in the `python` folder.
|
||||
{{< note >}}
|
||||
The `route_guide_db.json` file is actually language-agnostic, it happens to be located in the `python` folder.
|
||||
{{< /note >}}
|
||||
|
||||
From a different terminal, run the client:
|
||||
|
||||
|
|
|
|||
|
|
@ -17,11 +17,7 @@ By walking through this example you'll learn how to:
|
|||
It assumes a passing familiarity with [protocol
|
||||
buffers](https://developers.google.com/protocol-buffers/docs/overview).
|
||||
|
||||
<div id="toc"></div>
|
||||
|
||||
<a name="why-grpc"></a>
|
||||
|
||||
### Why use gRPC and gRPC-Web?
|
||||
### Why use gRPC and gRPC-Web? {#why-grpc}
|
||||
|
||||
With gRPC you can define your service once in a .proto file and implement
|
||||
clients and servers in any of gRPC's supported languages, which in turn can be
|
||||
|
|
@ -32,9 +28,7 @@ protocol buffers, including efficient serialization, a simple IDL, and easy
|
|||
interface updating. gRPC-Web lets you access gRPC services built in this manner
|
||||
from browsers using an idiomatic API.
|
||||
|
||||
<a name="setup"></a>
|
||||
|
||||
### Define the Service
|
||||
### Define the Service {#setup}
|
||||
|
||||
The first step when creating a gRPC service is to define the service methods
|
||||
and their request and response message types using protocol buffers. In this
|
||||
|
|
|
|||
|
|
@ -0,0 +1,24 @@
|
|||
- language: C++
|
||||
url: /grpc/cpp
|
||||
- language: Dart
|
||||
url: https://pub.dev/documentation/grpc
|
||||
- language: Java
|
||||
url: /grpc-java/javadoc
|
||||
- language: Python
|
||||
url: /grpc/python
|
||||
- language: Ruby
|
||||
url: https://www.rubydoc.info/gems/grpc
|
||||
- language: Node.js
|
||||
url: /grpc/node
|
||||
- language: C# API ("gRPC C#" implementation)
|
||||
url: /grpc/csharp/api/Grpc.Core
|
||||
- language: C# API ("grpc-dotnet" implementation)
|
||||
url: /grpc/csharp-dotnet/api/Grpc.Core
|
||||
- language: Go
|
||||
url: https://godoc.org/google.golang.org/grpc
|
||||
- language: Objective-C
|
||||
url: /grpc/objc
|
||||
- language: PHP
|
||||
url: /grpc/php/namespace-Grpc
|
||||
- language: gRPC Core Library (for wrapped languages)
|
||||
url: /grpc/core
|
||||
|
|
@ -0,0 +1,36 @@
|
|||
- language: "C/C++"
|
||||
platforms: ["Linux", "Mac"]
|
||||
compilers: ["GCC 4.9+", "Clang 3.4+"]
|
||||
- language: "C/C++"
|
||||
platforms: ["Windows 7+"]
|
||||
compilers: ["Visual Studio 2015+"]
|
||||
- language: "C#"
|
||||
platforms: ["Linux", "Mac"]
|
||||
compilers: [".NET Core", "Mono 4+"]
|
||||
- language: "C#"
|
||||
platforms: ["Windows 7+"]
|
||||
compilers: [".NET Core", "NET 4.5+"]
|
||||
- language: "Dart"
|
||||
platforms: ["Windows", "Linux", "Mac"]
|
||||
compilers: ["Dart 2.0+"]
|
||||
- language: "Go"
|
||||
platforms: ["Windows", "Linux", "Mac"]
|
||||
compilers: ["Go 1.6+"]
|
||||
- language: "Java"
|
||||
platforms: ["Windows", "Linux", "Mac"]
|
||||
compilers: ["JDK 8 recommended (Gingerbread+ for Android)"]
|
||||
- language: "Node.js"
|
||||
platforms: ["Windows", "Linux", "Mac"]
|
||||
compilers: ["Node v4+"]
|
||||
- language: "Objective-C"
|
||||
platforms: ["Mac OS X 10.11+", "iOS 7.0+"]
|
||||
compilers: ["Xcode 7.2+"]
|
||||
- language: "PHP (beta)"
|
||||
platforms: ["Linux", "Mac"]
|
||||
compilers: ["PHP 5.5+", "PHP 7.0+"]
|
||||
- language: "Python"
|
||||
platforms: ["Windows", "Linux", "Mac"]
|
||||
compilers: ["Python 2.7", "Python 3.4+"]
|
||||
- language: "Ruby"
|
||||
platforms: ["Windows", "Linux", "Mac"]
|
||||
compilers: ["Ruby 2.3+"]
|
||||
|
|
@ -0,0 +1,44 @@
|
|||
- name: Square
|
||||
link: https://www.youtube.com/watch?v=-2sWDr3Z0Wo
|
||||
image: square-icon.png
|
||||
quote: |
|
||||
At Square, we have been collaborating with Google so that we can replace all uses of our custom RPC solution to use gRPC. We decided to move to gRPC because of its open support for multiple platforms, the demonstrated performance of the protocol, and the ability to customize and adapt it to our network. Developers at Square are looking forward to being able to take advantage of writing streaming APIs and in the future, push gRPC to the edges of the network for integration with mobile clients and third party APIs.
|
||||
- name: Netflix
|
||||
link: https://github.com/Netflix/ribbon
|
||||
image: netflix-logo.png
|
||||
quote: |
|
||||
In our initial use of gRPC we've been able to extend it easily to live within our opinionated ecosystem. Further, we've had great success making improvements directly to gRPC through pull requests and interactions with Google's team that manages the project. We expect to see many improvements to developer productivity, and the ability to allow development in non-JVM languages as a result of adopting gRPC.
|
||||
- name: CoreOS
|
||||
link: https://blog.gopheracademy.com/advent-2015/etcd-distributed-key-value-store-with-grpc-http2
|
||||
image: coreos-1.png
|
||||
quote: |
|
||||
At CoreOS we are excited by the gRPC v1.0 release and the opportunities it opens up for people consuming and building what we like to call Google Infrastructure for Everyone Else. Today gRPC is in use in a number of our critical open source projects such as the etcd consensus database and the rkt container engine.
|
||||
- name: Cockroach Labs
|
||||
link: https://github.com/cockroachdb/cockroach
|
||||
image: cockroach-1.png
|
||||
quote: |
|
||||
Our switch from a home-grown RPC system to gRPC was seamless. We quickly took advantage of the per-stream flow control to provide better scheduling of large RPCs over the same connection as small ones.
|
||||
- name: Cisco
|
||||
link: https://github.com/CiscoDevNet/grpc-getting-started
|
||||
image: cisco.svg
|
||||
quote: |
|
||||
With support for high performance bi-directional streaming, TLS based security, and a wide variety of programming languages, gRPC is an ideal unified transport protocol for model driven configuration and telemetry.
|
||||
- name: Carbon3D
|
||||
link: https://www.carbon3d.com
|
||||
image: carbon3d.svg
|
||||
quote: |
|
||||
Carbon3D uses gRPC to implement distributed processes both within and outside our 3D printers. We actually switched from using Thrift early on for a number of reasons including but not limited to robust support for multiple languages like C++, Nodejs and Python. Features like bi-directional streaming are a huge win in keeping our systems implementations simpler and correct. Lastly the gRPC team/community is very active and responsive which is also a key factor for us in selecting an open source technology for mission critical projects.
|
||||
- name: University of Wisconsin
|
||||
link: https://www.wisc.edu
|
||||
image: wisc-mad.jpg
|
||||
quote: |
|
||||
We've been using gRPC for both classes and research at University of Wisconsin. Students in our distributed systems class (CS 739) utilized many of its powerful features when building their own distributed systems. In addition, gRPC is a key component of our OpenLambda research project (https://www.open-lambda.org/) which aims to provide an open-source, low-latency, serverless computational framework.
|
||||
- name: Juniper Networks
|
||||
link: https://github.com/Juniper/open-nti
|
||||
image: juniperlogo.png
|
||||
quote: |
|
||||
The fact that gRPC is built on HTTP/2 transport brings us native bi-directional streaming capabilities and flexible custom-metadata in request headers. The first point is important for large payloadexchange and network telemetry scenarios while the latter enables us to expand and include capabilities including but not limited to various network element authentication mechanisms.
|
||||
|
||||
In addition, the wide language binding support that gRPC/proto3 bringsenables us to provide a flexible and rapid development environment for both internal and external consumers.
|
||||
|
||||
Last but not least, while there are a number of network communicationprotocols for configuration, operational state retrieval and network telemetry, gRPC provides us with a unified flexible protocol and transport to ease client/server interaction.
|
||||
|
|
@ -0,0 +1,58 @@
|
|||
{{ define "main" }}
|
||||
<section class="hero is-medium has-background-image">
|
||||
<div class="hero-body">
|
||||
<div class="container has-text-centered">
|
||||
<p class="title is-size-1 is-size-2-mobile has-text-weight-bold is-spaced">
|
||||
<span class="has-text-white">
|
||||
404
|
||||
</span>
|
||||
<span class="has-text-secondary">
|
||||
!
|
||||
</span>
|
||||
</p>
|
||||
|
||||
<p class="subtitle is-size-3 is-size-4-mobile has-text-grey-lighter has-text-weight-medium">
|
||||
Page not found
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<section class="section">
|
||||
<div class="container has-text-centered">
|
||||
<div class="content has-bottom-padding is-medium">
|
||||
<p>
|
||||
Sorry, but that link wasn't found. Perhaps you were looking for one of the following:
|
||||
</p>
|
||||
|
||||
<a class="is-size-4 is-size-5-mobile" href="/">
|
||||
Main page
|
||||
</a>
|
||||
|
||||
<br />
|
||||
|
||||
<a class="is-size-4 is-size-5-mobile" href="/docs">
|
||||
Documentation
|
||||
</a>
|
||||
|
||||
<br />
|
||||
|
||||
<a class="is-size-4 is-size-5-mobile" href="/blog">
|
||||
Blog
|
||||
</a>
|
||||
|
||||
<br />
|
||||
|
||||
<a class="is-size-4 is-size-5-mobile" href="/community">
|
||||
Community
|
||||
</a>
|
||||
|
||||
<br />
|
||||
|
||||
<a class="is-size-4 is-size-5-mobile" href="/faq">
|
||||
FAQ
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
{{ end }}
|
||||
|
|
@ -0,0 +1,16 @@
|
|||
{{ $src := .Destination | safeURL }}
|
||||
{{ $id := index (last 1 (split .Destination "/")) 0 | replaceRE ".png" "" }}
|
||||
<figure x-data="{ open: false }">
|
||||
<img src="{{ $src }}"{{ with .Text }} alt="{{ . }}"{{ end }} id="{{ $id }}" @click="open = true">
|
||||
|
||||
<div class="modal" id="modal-{{ $id }}" :class="{ 'is-active': open }">
|
||||
<div class="modal-background"></div>
|
||||
<div class="modal-content">
|
||||
<p class="image">
|
||||
<img src="{{ $src }}"{{ with .Text }} alt="{{ . }}"{{ end }}>
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<button class="modal-close is-large" aria-label="close" @click="open = false"></button>
|
||||
</div>
|
||||
</figure>
|
||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue