Repository: badsyntax/grpc-js-typescript
Branch: master
Commit: 9daa97bbfd09
Files: 83
Total size: 92.9 KB
Directory structure:
gitextract_7hw2d8wn/
├── .github/
│ ├── CODEOWNERS
│ ├── dependabot.yml
│ └── workflows/
│ └── test.yml
├── README.md
└── examples/
├── gradle-ts-protoc-gen/
│ ├── .gitattributes
│ ├── .gitignore
│ ├── .npmrc
│ ├── .prettierignore
│ ├── .vscode/
│ │ ├── extensions.json
│ │ └── settings.json
│ ├── README.md
│ ├── build.gradle
│ ├── client.ts
│ ├── gradle/
│ │ └── wrapper/
│ │ ├── gradle-wrapper.jar
│ │ └── gradle-wrapper.properties
│ ├── gradlew
│ ├── gradlew.bat
│ ├── package.json
│ ├── proto/
│ │ ├── example.proto
│ │ ├── example_grpc_pb.d.ts
│ │ └── example_pb.d.ts
│ ├── server.ts
│ ├── settings.gradle
│ └── tsconfig.json
├── grpc-proto-loader/
│ ├── .gitignore
│ ├── .npmrc
│ ├── .nvmrc
│ ├── .prettierignore
│ ├── .vscode/
│ │ ├── extensions.json
│ │ └── settings.json
│ ├── README.md
│ ├── client.ts
│ ├── package.json
│ ├── proto/
│ │ ├── example.proto
│ │ ├── example.ts
│ │ └── example_package/
│ │ ├── ClientMessage.ts
│ │ ├── Example.ts
│ │ └── ServerMessage.ts
│ ├── server.ts
│ └── tsconfig.json
├── grpc-web/
│ ├── .gitignore
│ ├── .npmrc
│ ├── .prettierignore
│ ├── .vscode/
│ │ ├── extensions.json
│ │ └── settings.json
│ ├── README.md
│ ├── client.ts
│ ├── compile-proto.sh
│ ├── envoy.yaml
│ ├── index.html
│ ├── package.json
│ ├── proto/
│ │ └── chat.proto
│ ├── server.ts
│ ├── tsconfig.json
│ └── webpack.config.ts
├── grpc_tools_node_protoc_ts/
│ ├── .gitignore
│ ├── .npmrc
│ ├── .prettierignore
│ ├── .vscode/
│ │ ├── extensions.json
│ │ └── settings.json
│ ├── README.md
│ ├── client.ts
│ ├── compile-proto.sh
│ ├── package.json
│ ├── proto/
│ │ ├── example.proto
│ │ ├── example_grpc_pb.d.ts
│ │ └── example_pb.d.ts
│ ├── server.ts
│ └── tsconfig.json
└── ts-protoc-gen/
├── .gitignore
├── .npmrc
├── .prettierignore
├── .vscode/
│ ├── extensions.json
│ └── settings.json
├── README.md
├── client.ts
├── compile-proto.sh
├── package.json
├── proto/
│ ├── example.proto
│ ├── example_grpc_pb.d.ts
│ └── example_pb.d.ts
├── server.ts
└── tsconfig.json
================================================
FILE CONTENTS
================================================
================================================
FILE: .github/CODEOWNERS
================================================
* @badsyntax
================================================
FILE: .github/dependabot.yml
================================================
version: 2
updates:
- package-ecosystem: github-actions
directory: "/"
schedule:
interval: daily
open-pull-requests-limit: 10
================================================
FILE: .github/workflows/test.yml
================================================
name: Test
on:
push:
branches: [master]
pull_request:
branches: [master]
jobs:
test:
runs-on: ubuntu-20.04
name: Build examples
steps:
- uses: actions/checkout@v4.2.2
- uses: actions/setup-node@v3.4.1
with:
node-version: 16
- uses: actions/setup-java@v4.5.0
with:
java-version: 15
architecture: x64
distribution: zulu
- name: Build gradle-ts-protoc-gen
run: |
cd examples/gradle-ts-protoc-gen
npm i
npm run build
- name: Build grpc_tools_node_protoc_ts
run: |
cd examples/grpc_tools_node_protoc_ts
npm i
npm run build
- name: Build grpc-proto-loader
run: |
cd examples/grpc-proto-loader
npm i
npm run build
- name: Build grpc-web
run: |
cd examples/grpc-web
npm i
npm run build
- name: Build ts-protoc-gen
run: |
cd examples/ts-protoc-gen
npm i
npm run build
================================================
FILE: README.md
================================================
# gRPC TypeScript
[](https://github.com/badsyntax/grpc-js-typescript/actions/workflows/test.yml)
This repo shows how to use gRPC with TypeScript & Node.js.
In all cases, [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js) is used as [`grpc`](https://www.npmjs.com/package/grpc) is now [effectively deprecated](https://grpc.io/blog/grpc-js-1.0/).
TypeScript types are generated at build time from the proto files using different tools as demonstrated in this repo.
## Examples
Each example is a separate application. Refer to the README in each project for more information.
- [grpc-proto-loader](./examples/grpc-proto-loader)
- [ts-protoc-gen](./examples/ts-protoc-gen)
- [gradle-ts-protoc-gen](./examples/gradle-ts-protoc-gen)
- [grpc_tools_node_protoc_ts](./examples/grpc_tools_node_protoc_ts)
- [grpc-web](./examples/grpc-web)
## Type Parity
Thanks to [this issue](https://github.com/agreatfool/grpc_tools_node_protoc_ts/issues/79) being fixed, we now have type parity across the different type generator packages. 🎉
## Contributions
Contributions I made to help with gRPC & TypeScript support:
- https://github.com/grpc/grpc-node/pull/1368
- https://github.com/grpc/grpc-node/pull/1380
- https://github.com/grpc/grpc-node/pull/1387
- https://github.com/grpc/grpc-node/pull/1419
- https://github.com/grpc/grpc-node/pull/1454
- https://github.com/grpc/grpc-node/pull/1587
- https://github.com/grpc/grpc-node/pull/1590
- https://github.com/murgatroid99/grpc-node/pull/1
- https://github.com/murgatroid99/grpc-node/pull/2
- https://github.com/murgatroid99/grpc-node/pull/3
- https://github.com/improbable-eng/ts-protoc-gen/pull/236
- https://github.com/improbable-eng/ts-protoc-gen/pull/247
================================================
FILE: examples/gradle-ts-protoc-gen/.gitattributes
================================================
#
# https://help.github.com/articles/dealing-with-line-endings/
#
# These are explicitly windows files and should use crlf
*.bat text eol=crlf
================================================
FILE: examples/gradle-ts-protoc-gen/.gitignore
================================================
node_modules
**/*.js
!proto/*.js
# Ignore Gradle project-specific cache directory
.gradle
# Ignore Gradle build output directory
build
# Eclipse files
.settings
.classpath
.project
================================================
FILE: examples/gradle-ts-protoc-gen/.npmrc
================================================
registry=https://registry.npmjs.org/
================================================
FILE: examples/gradle-ts-protoc-gen/.prettierignore
================================================
package-lock.json
proto/*.ts
================================================
FILE: examples/gradle-ts-protoc-gen/.vscode/extensions.json
================================================
{
"recommendations": [
"dbaeumer.vscode-eslint",
"EditorConfig.EditorConfig",
"esbenp.prettier-vscode",
"streetsidesoftware.code-spell-checker",
"zxh404.vscode-proto3"
]
}
================================================
FILE: examples/gradle-ts-protoc-gen/.vscode/settings.json
================================================
{
"typescript.tsc.autoDetect": "off",
"typescript.updateImportsOnFileMove.enabled": "always",
"files.insertFinalNewline": true,
"files.trimTrailingWhitespace": true,
"eslint.validate": ["javascript", "typescript"],
"editor.formatOnSave": false,
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true,
"source.organizeImports": false
},
"[markdown]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[json]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[yaml]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"cSpell.language": "en-GB",
"cSpell.words": [
"grpc"
],
"java.configuration.updateBuildConfiguration": "automatic"
}
================================================
FILE: examples/gradle-ts-protoc-gen/README.md
================================================
# gradle-ts-protoc-gen example
This examples shows how to uses [Gradle](https://gradle.org/), the [proto compiler](https://www.npmjs.com/package/grpc-tools), [`ts-protoc-gen`](https://www.npmjs.com/package/ts-protoc-gen) & [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js) to build a fully typed gRPC application that runs on Node.js.
The [proto compiler](https://www.npmjs.com/package/grpc-tools) and [`ts-protoc-gen`](https://www.npmjs.com/package/ts-protoc-gen) compiler plugin are used to generate JavaScript & TypeScript files from the proto definitions. The [`protobuf-gradle-plugin`](https://github.com/google/protobuf-gradle-plugin) Gradle plugin is used to run the compiler from Gradle.
[`google-protobuf`](https://www.npmjs.com/package/google-protobuf) & [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js) are used at runtime.
## App layout
- [package.json](./package.json) - Dependencies and node build scripts
- [build.gradle](./build.gradle) - The Gradle build file
- [proto/](./proto/) - Protobuf definitions and generated types
- [server.ts](./server.ts) - The grpc server
- [client.ts](./client.ts) - The grpc client
## Generating the Types
Install dependencies:
```sh
npm install
# Apple M1 users should install for x64 due to grpc-tools not supporting arm64
npm i --target_arch=x64
```
Use Gradle & [`ts-protoc-gen`](https://www.npmjs.com/package/ts-protoc-gen) to generate the TypeScript files:
```sh
./gradlew generateProto
```
This is aliased as a npm script:
```sh
npm run build:proto
```
### Running the App
This simple app demonstrates the different gRPC calls you can perform.
First generated the types and build the application files:
```sh
npm run build
```
Start the server:
```sh
npm run start:server
```
Now run the client by specifying which example you want to run:
```bash
npm run start:client -- --unary
npm run start:client -- --server-streaming
npm run start:client -- --client-streaming
npm run start:client -- --bidi-streaming
```
================================================
FILE: examples/gradle-ts-protoc-gen/build.gradle
================================================
plugins {
id 'java'
id 'com.google.protobuf' version '0.8.16'
id 'com.github.jlouns.cpe' version '0.5.0'
}
project.ext.set('protobufVersion', '3.16.0')
project.ext.set('protocVersion', project.protobufVersion)
def isWindows = System.getProperty('os.name').toLowerCase().contains('windows')
repositories {
mavenCentral()
}
sourceSets {
main {
proto {
srcDir file('./proto')
}
}
}
protobuf {
protoc {
if (osdetector.os == 'osx') {
// Required for arm64 support on MacOS
artifact = "com.google.protobuf:protoc:${protocVersion}:osx-x86_64"
} else {
artifact = "com.google.protobuf:protoc:${protocVersion}"
}
}
plugins {
grpc {
path = file(
'./node_modules/.bin/grpc_tools_node_protoc_plugin' + (isWindows ? '.cmd' : '')
)
}
ts {
path = file(
'./node_modules/.bin/protoc-gen-ts' + (isWindows ? '.cmd' : '')
)
}
}
generateProtoTasks {
generateProto.finalizedBy copyGeneratedProto
all().each { task ->
task.plugins {
grpc {
outputSubDir = 'js'
option 'grpc_js'
}
ts {
option 'service=grpc-node,mode=grpc-js'
}
}
task.builtins {
remove java
js {
option 'import_style=commonjs'
}
}
task.dependsOn npmInstall
}
}
}
task copyGeneratedProto(type: Copy) {
from "$protobuf.generatedFilesBaseDir/main/ts", "$protobuf.generatedFilesBaseDir/main/js"
into 'proto'
}
task npmInstall(type: CrossPlatformExec) {
description 'Installs node dependencies'
inputs.file('package-lock.json').withPathSensitivity(PathSensitivity.RELATIVE)
outputs.dir('node_modules')
outputs.cacheIf { true }
commandLine 'npm', 'install'
}
================================================
FILE: examples/gradle-ts-protoc-gen/client.ts
================================================
import * as grpc from '@grpc/grpc-js';
import { ExampleClient } from './proto/example_grpc_pb';
import { ClientMessage, ServerMessage } from './proto/example_pb';
const host = '0.0.0.0:9090';
const client = new ExampleClient(host, grpc.credentials.createInsecure());
const deadline = new Date();
deadline.setSeconds(deadline.getSeconds() + 5);
client.waitForReady(deadline, (error?: Error) => {
if (error) {
console.log(`Client connect error: ${error.message}`);
} else {
onClientReady();
}
});
function onClientReady() {
switch (process.argv[process.argv.length - 1]) {
case '--unary':
doUnaryCall();
break;
case '--server-streaming':
doServerStreamingCall();
break;
case '--client-streaming':
doClientStreamingCall();
break;
case '--bidi-streaming':
doBidirectionalStreamingCall();
break;
default:
throw new Error('Example not specified');
}
}
function doUnaryCall() {
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
client.unaryCall(
clientMessage,
(error: grpc.ServiceError | null, serverMessage?: ServerMessage) => {
if (error) {
console.error(error.message);
} else if (serverMessage) {
console.log(
`(client) Got server message: ${serverMessage.getServerMessage()}`
);
}
}
);
}
function doServerStreamingCall() {
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
const stream = client.serverStreamingCall(clientMessage);
stream.on('data', (serverMessage: ServerMessage) => {
console.log(
`(client) Got server message: ${serverMessage.getServerMessage()}`
);
});
}
function doClientStreamingCall() {
const stream = client.clientStreamingCall(
(error: grpc.ServiceError | null) => {
if (error) {
console.error(error.message);
}
}
);
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
stream.write(clientMessage);
}
function doBidirectionalStreamingCall() {
const stream = client.bidirectionalStreamingCall();
// Server stream
stream.on('data', (serverMessage: ServerMessage) => {
console.log(
`(client) Got server message: ${serverMessage.getServerMessage()}`
);
});
// Client stream
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
stream.write(clientMessage);
}
================================================
FILE: examples/gradle-ts-protoc-gen/gradle/wrapper/gradle-wrapper.properties
================================================
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-7.0.1-bin.zip
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
================================================
FILE: examples/gradle-ts-protoc-gen/gradlew
================================================
#!/usr/bin/env sh
#
# Copyright 2015 the original author or authors.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# https://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
##############################################################################
##
## Gradle start up script for UN*X
##
##############################################################################
# Attempt to set APP_HOME
# Resolve links: $0 may be a link
PRG="$0"
# Need this for relative symlinks.
while [ -h "$PRG" ] ; do
ls=`ls -ld "$PRG"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
PRG="$link"
else
PRG=`dirname "$PRG"`"/$link"
fi
done
SAVED="`pwd`"
cd "`dirname \"$PRG\"`/" >/dev/null
APP_HOME="`pwd -P`"
cd "$SAVED" >/dev/null
APP_NAME="Gradle"
APP_BASE_NAME=`basename "$0"`
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
# Use the maximum available, or set MAX_FD != -1 to use that value.
MAX_FD="maximum"
warn () {
echo "$*"
}
die () {
echo
echo "$*"
echo
exit 1
}
# OS specific support (must be 'true' or 'false').
cygwin=false
msys=false
darwin=false
nonstop=false
case "`uname`" in
CYGWIN* )
cygwin=true
;;
Darwin* )
darwin=true
;;
MINGW* )
msys=true
;;
NONSTOP* )
nonstop=true
;;
esac
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
# Determine the Java command to use to start the JVM.
if [ -n "$JAVA_HOME" ] ; then
if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
# IBM's JDK on AIX uses strange locations for the executables
JAVACMD="$JAVA_HOME/jre/sh/java"
else
JAVACMD="$JAVA_HOME/bin/java"
fi
if [ ! -x "$JAVACMD" ] ; then
die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
else
JAVACMD="java"
which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
# Increase the maximum file descriptors if we can.
if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then
MAX_FD_LIMIT=`ulimit -H -n`
if [ $? -eq 0 ] ; then
if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
MAX_FD="$MAX_FD_LIMIT"
fi
ulimit -n $MAX_FD
if [ $? -ne 0 ] ; then
warn "Could not set maximum file descriptor limit: $MAX_FD"
fi
else
warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
fi
fi
# For Darwin, add options to specify how the application appears in the dock
if $darwin; then
GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
fi
# For Cygwin or MSYS, switch paths to Windows format before running java
if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then
APP_HOME=`cygpath --path --mixed "$APP_HOME"`
CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
JAVACMD=`cygpath --unix "$JAVACMD"`
# We build the pattern for arguments to be converted via cygpath
ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
SEP=""
for dir in $ROOTDIRSRAW ; do
ROOTDIRS="$ROOTDIRS$SEP$dir"
SEP="|"
done
OURCYGPATTERN="(^($ROOTDIRS))"
# Add a user-defined pattern to the cygpath arguments
if [ "$GRADLE_CYGPATTERN" != "" ] ; then
OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
fi
# Now convert the arguments - kludge to limit ourselves to /bin/sh
i=0
for arg in "$@" ; do
CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
else
eval `echo args$i`="\"$arg\""
fi
i=`expr $i + 1`
done
case $i in
0) set -- ;;
1) set -- "$args0" ;;
2) set -- "$args0" "$args1" ;;
3) set -- "$args0" "$args1" "$args2" ;;
4) set -- "$args0" "$args1" "$args2" "$args3" ;;
5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
esac
fi
# Escape application args
save () {
for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
echo " "
}
APP_ARGS=`save "$@"`
# Collect all arguments for the java command, following the shell quoting and substitution rules
eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
exec "$JAVACMD" "$@"
================================================
FILE: examples/gradle-ts-protoc-gen/gradlew.bat
================================================
@rem
@rem Copyright 2015 the original author or authors.
@rem
@rem Licensed under the Apache License, Version 2.0 (the "License");
@rem you may not use this file except in compliance with the License.
@rem You may obtain a copy of the License at
@rem
@rem https://www.apache.org/licenses/LICENSE-2.0
@rem
@rem Unless required by applicable law or agreed to in writing, software
@rem distributed under the License is distributed on an "AS IS" BASIS,
@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@rem See the License for the specific language governing permissions and
@rem limitations under the License.
@rem
@if "%DEBUG%" == "" @echo off
@rem ##########################################################################
@rem
@rem Gradle startup script for Windows
@rem
@rem ##########################################################################
@rem Set local scope for the variables with windows NT shell
if "%OS%"=="Windows_NT" setlocal
set DIRNAME=%~dp0
if "%DIRNAME%" == "" set DIRNAME=.
set APP_BASE_NAME=%~n0
set APP_HOME=%DIRNAME%
@rem Resolve any "." and ".." in APP_HOME to make it shorter.
for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m"
@rem Find java.exe
if defined JAVA_HOME goto findJavaFromJavaHome
set JAVA_EXE=java.exe
%JAVA_EXE% -version >NUL 2>&1
if "%ERRORLEVEL%" == "0" goto execute
echo.
echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:findJavaFromJavaHome
set JAVA_HOME=%JAVA_HOME:"=%
set JAVA_EXE=%JAVA_HOME%/bin/java.exe
if exist "%JAVA_EXE%" goto execute
echo.
echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:execute
@rem Setup the command line
set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
@rem Execute Gradle
"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %*
:end
@rem End local scope for the variables with windows NT shell
if "%ERRORLEVEL%"=="0" goto mainEnd
:fail
rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
rem the _cmd.exe /c_ return code!
if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
exit /b 1
:mainEnd
if "%OS%"=="Windows_NT" endlocal
:omega
================================================
FILE: examples/gradle-ts-protoc-gen/package.json
================================================
{
"name": "gradle-ts-protoc-gen",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"build": "npm run build:typescript",
"build:typescript": "tsc -p .",
"build:proto": "./gradlew generateProto",
"watch": "npm run build:typescript -- -w",
"prewatch": "npm run build:proto",
"prebuild": "npm run build:proto",
"lint": "npm run lint:prettier && npm run lint:eslint",
"lint:prettier": "prettier --check \"**/*.{ts,js,json,svg,md,yml}\"",
"lint:eslint": "eslint . --ext .js,.ts",
"lint:fix": "npm run lint:fix:prettier && npm run lint:eslint -- --fix",
"lint:fix:prettier": "prettier --write '**/*.{ts,tsx,js,json,svg,md,yml}'",
"start:server": "node server",
"start:client": "node client"
},
"keywords": [],
"author": "",
"license": "ISC",
"dependencies": {
"@grpc/grpc-js": "^1.6.8",
"google-protobuf": "^3.21.0"
},
"devDependencies": {
"@tsconfig/node12": "^1.0.11",
"@types/google-protobuf": "^3.15.6",
"@types/node": "^15.0.3",
"@typescript-eslint/eslint-plugin": "^5.31.0",
"@typescript-eslint/parser": "^5.31.0",
"eslint": "^8.20.0",
"eslint-config-prettier": "^8.5.0",
"eslint-plugin-node": "^11.1.0",
"eslint-plugin-prettier": "^4.2.1",
"grpc-tools": "^1.11.2",
"prettier": "^2.7.1",
"ts-protoc-gen": "^0.15.0",
"typescript": "^4.7.4"
},
"eslintConfig": {
"ignorePatterns": [
"**/*.js",
"proto/*.ts"
],
"env": {
"browser": false,
"es6": true,
"node": true
},
"parserOptions": {
"project": "./tsconfig.json",
"ecmaVersion": 2018,
"sourceType": "module"
},
"extends": [
"plugin:@typescript-eslint/recommended",
"plugin:prettier/recommended"
]
},
"prettier": {
"singleQuote": true,
"tabWidth": 2,
"printWidth": 80,
"useTabs": false
}
}
================================================
FILE: examples/gradle-ts-protoc-gen/proto/example.proto
================================================
syntax = "proto3";
package example_package;
message ServerMessage {
string server_message = 1;
}
message ClientMessage {
string client_message = 1;
}
service Example {
rpc unaryCall(ClientMessage) returns (ServerMessage) {}
rpc serverStreamingCall(ClientMessage) returns (stream ServerMessage) {}
rpc clientStreamingCall(stream ClientMessage) returns (ServerMessage) {}
rpc bidirectionalStreamingCall(stream ClientMessage) returns (stream ServerMessage) {}
}
================================================
FILE: examples/gradle-ts-protoc-gen/proto/example_grpc_pb.d.ts
================================================
// GENERATED CODE -- DO NOT EDIT!
// package: example_package
// file: example.proto
import * as example_pb from "./example_pb";
import * as grpc from "@grpc/grpc-js";
interface IExampleService extends grpc.ServiceDefinition<grpc.UntypedServiceImplementation> {
unaryCall: grpc.MethodDefinition<example_pb.ClientMessage, example_pb.ServerMessage>;
serverStreamingCall: grpc.MethodDefinition<example_pb.ClientMessage, example_pb.ServerMessage>;
clientStreamingCall: grpc.MethodDefinition<example_pb.ClientMessage, example_pb.ServerMessage>;
bidirectionalStreamingCall: grpc.MethodDefinition<example_pb.ClientMessage, example_pb.ServerMessage>;
}
export const ExampleService: IExampleService;
export interface IExampleServer extends grpc.UntypedServiceImplementation {
unaryCall: grpc.handleUnaryCall<example_pb.ClientMessage, example_pb.ServerMessage>;
serverStreamingCall: grpc.handleServerStreamingCall<example_pb.ClientMessage, example_pb.ServerMessage>;
clientStreamingCall: grpc.handleClientStreamingCall<example_pb.ClientMessage, example_pb.ServerMessage>;
bidirectionalStreamingCall: grpc.handleBidiStreamingCall<example_pb.ClientMessage, example_pb.ServerMessage>;
}
export class ExampleClient extends grpc.Client {
constructor(address: string, credentials: grpc.ChannelCredentials, options?: object);
unaryCall(argument: example_pb.ClientMessage, callback: grpc.requestCallback<example_pb.ServerMessage>): grpc.ClientUnaryCall;
unaryCall(argument: example_pb.ClientMessage, metadataOrOptions: grpc.Metadata | grpc.CallOptions | null, callback: grpc.requestCallback<example_pb.ServerMessage>): grpc.ClientUnaryCall;
unaryCall(argument: example_pb.ClientMessage, metadata: grpc.Metadata | null, options: grpc.CallOptions | null, callback: grpc.requestCallback<example_pb.ServerMessage>): grpc.ClientUnaryCall;
serverStreamingCall(argument: example_pb.ClientMessage, metadataOrOptions?: grpc.Metadata | grpc.CallOptions | null): grpc.ClientReadableStream<example_pb.ServerMessage>;
serverStreamingCall(argument: example_pb.ClientMessage, metadata?: grpc.Metadata | null, options?: grpc.CallOptions | null): grpc.ClientReadableStream<example_pb.ServerMessage>;
clientStreamingCall(callback: grpc.requestCallback<example_pb.ServerMessage>): grpc.ClientWritableStream<example_pb.ClientMessage>;
clientStreamingCall(metadataOrOptions: grpc.Metadata | grpc.CallOptions | null, callback: grpc.requestCallback<example_pb.ServerMessage>): grpc.ClientWritableStream<example_pb.ClientMessage>;
clientStreamingCall(metadata: grpc.Metadata | null, options: grpc.CallOptions | null, callback: grpc.requestCallback<example_pb.ServerMessage>): grpc.ClientWritableStream<example_pb.ClientMessage>;
bidirectionalStreamingCall(metadataOrOptions?: grpc.Metadata | grpc.CallOptions | null): grpc.ClientDuplexStream<example_pb.ClientMessage, example_pb.ServerMessage>;
bidirectionalStreamingCall(metadata?: grpc.Metadata | null, options?: grpc.CallOptions | null): grpc.ClientDuplexStream<example_pb.ClientMessage, example_pb.ServerMessage>;
}
================================================
FILE: examples/gradle-ts-protoc-gen/proto/example_pb.d.ts
================================================
// package: example_package
// file: example.proto
import * as jspb from "google-protobuf";
export class ServerMessage extends jspb.Message {
getServerMessage(): string;
setServerMessage(value: string): void;
serializeBinary(): Uint8Array;
toObject(includeInstance?: boolean): ServerMessage.AsObject;
static toObject(includeInstance: boolean, msg: ServerMessage): ServerMessage.AsObject;
static extensions: {[key: number]: jspb.ExtensionFieldInfo<jspb.Message>};
static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo<jspb.Message>};
static serializeBinaryToWriter(message: ServerMessage, writer: jspb.BinaryWriter): void;
static deserializeBinary(bytes: Uint8Array): ServerMessage;
static deserializeBinaryFromReader(message: ServerMessage, reader: jspb.BinaryReader): ServerMessage;
}
export namespace ServerMessage {
export type AsObject = {
serverMessage: string,
}
}
export class ClientMessage extends jspb.Message {
getClientMessage(): string;
setClientMessage(value: string): void;
serializeBinary(): Uint8Array;
toObject(includeInstance?: boolean): ClientMessage.AsObject;
static toObject(includeInstance: boolean, msg: ClientMessage): ClientMessage.AsObject;
static extensions: {[key: number]: jspb.ExtensionFieldInfo<jspb.Message>};
static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo<jspb.Message>};
static serializeBinaryToWriter(message: ClientMessage, writer: jspb.BinaryWriter): void;
static deserializeBinary(bytes: Uint8Array): ClientMessage;
static deserializeBinaryFromReader(message: ClientMessage, reader: jspb.BinaryReader): ClientMessage;
}
export namespace ClientMessage {
export type AsObject = {
clientMessage: string,
}
}
================================================
FILE: examples/gradle-ts-protoc-gen/server.ts
================================================
import * as grpc from '@grpc/grpc-js';
import { ExampleService, IExampleServer } from './proto/example_grpc_pb';
import { ClientMessage, ServerMessage } from './proto/example_pb';
const host = '0.0.0.0:9090';
const exampleServer: IExampleServer = {
unaryCall(
call: grpc.ServerUnaryCall<ClientMessage, ServerMessage>,
callback: grpc.sendUnaryData<ServerMessage>
) {
if (call.request) {
console.log(
`(server) Got client message: ${call.request.getClientMessage()}`
);
}
const serverMessage = new ServerMessage();
serverMessage.setServerMessage('Message from server');
callback(null, serverMessage);
},
serverStreamingCall(
call: grpc.ServerWritableStream<ClientMessage, ServerMessage>
) {
const serverMessage = new ServerMessage();
serverMessage.setServerMessage('Message from server');
call.write(serverMessage);
},
clientStreamingCall(
call: grpc.ServerReadableStream<ClientMessage, ServerMessage>
) {
call.on('data', (clientMessage: ClientMessage) => {
console.log(
`(server) Got client message: ${clientMessage.getClientMessage()}`
);
});
},
bidirectionalStreamingCall(
call: grpc.ServerDuplexStream<ClientMessage, ServerMessage>
) {
call.on('data', (clientMessage: ClientMessage) => {
console.log(
`(server) Got client message: ${clientMessage.getClientMessage()}`
);
});
const serverMessage = new ServerMessage();
serverMessage.setServerMessage('Message from server');
call.write(serverMessage);
},
};
function getServer(): grpc.Server {
const server = new grpc.Server();
server.addService(ExampleService, exampleServer);
return server;
}
if (require.main === module) {
const server = getServer();
server.bindAsync(
host,
grpc.ServerCredentials.createInsecure(),
(err: Error | null, port: number) => {
if (err) {
console.error(`Server error: ${err.message}`);
} else {
console.log(`Server bound on port: ${port}`);
server.start();
}
}
);
}
================================================
FILE: examples/gradle-ts-protoc-gen/settings.gradle
================================================
/*
* This file was generated by the Gradle 'init' task.
*
* The settings file is used to specify which projects to include in your build.
*
* Detailed information about configuring a multi-project build in Gradle can be found
* in the user manual at https://docs.gradle.org/6.6.1/userguide/multi_project_builds.html
*/
rootProject.name = 'gradle-ts-protoc-gen'
================================================
FILE: examples/gradle-ts-protoc-gen/tsconfig.json
================================================
{
"extends": "@tsconfig/node12/tsconfig.json",
"exclude": ["node_modules"]
}
================================================
FILE: examples/grpc-proto-loader/.gitignore
================================================
node_modules
generated
*.js
================================================
FILE: examples/grpc-proto-loader/.npmrc
================================================
registry=https://registry.npmjs.org/
================================================
FILE: examples/grpc-proto-loader/.nvmrc
================================================
14
================================================
FILE: examples/grpc-proto-loader/.prettierignore
================================================
package-lock.json
generated
================================================
FILE: examples/grpc-proto-loader/.vscode/extensions.json
================================================
{
"recommendations": [
"dbaeumer.vscode-eslint",
"EditorConfig.EditorConfig",
"esbenp.prettier-vscode",
"streetsidesoftware.code-spell-checker",
"zxh404.vscode-proto3"
]
}
================================================
FILE: examples/grpc-proto-loader/.vscode/settings.json
================================================
{
"typescript.tsc.autoDetect": "off",
"typescript.updateImportsOnFileMove.enabled": "always",
"files.insertFinalNewline": true,
"files.trimTrailingWhitespace": true,
"eslint.validate": ["javascript", "typescript"],
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true
},
"[markdown]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[json]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[yaml]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"cSpell.language": "en-GB",
"cSpell.words": ["grpc", "unary", "bidi"]
}
================================================
FILE: examples/grpc-proto-loader/README.md
================================================
# grpc-proto-loader example
This example shows how to use [`@grpc/proto-loader`](https://www.npmjs.com/package/@grpc/proto-loader) & [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js) to build a fully typed CLI application that runs on Node.js.
[`@grpc/proto-loader`](https://www.npmjs.com/package/@grpc/proto-loader) to used to [generate the types](https://github.com/grpc/grpc-node/pull/1474), as well as load the protobuf files at runtime using [`protobuf.js`](https://www.npmjs.com/package/protobufjs) instead of [`google-protobuf`](https://www.npmjs.com/package/google-protobuf).
_No proto compiler is used. It's all JavaScript._
## App layout
- [package.json](./package.json) - Dependencies and build scripts
- [proto/](./proto/) - Protobuf definitions and generated types
- [server.ts](./server.ts) - The grpc server
- [client.ts](./client.ts) - The grpc client
## Generating the Types
Install dependencies:
```sh
npm install
```
Use [`@grpc/proto-loader`](https://www.npmjs.com/package/@grpc/proto-loader) to generate the TypeScript files:
```sh
$(npm bin)/proto-loader-gen-types --longs=String --enums=String --defaults --oneofs --grpcLib=@grpc/grpc-js --outDir=proto/ proto/*.proto
```
This is aliased as a npm script:
```sh
npm run build:proto
```
### Running the App
This simple app demonstrates the different gRPC calls you can perform.
First generated the types and build the application files:
```sh
npm run build
```
Start the server:
```sh
npm run start:server
```
Now run the client by specifying which example you want to run:
```bash
npm run start:client -- --unary
npm run start:client -- --server-streaming
npm run start:client -- --client-streaming
npm run start:client -- --bidi-streaming
```
================================================
FILE: examples/grpc-proto-loader/client.ts
================================================
import * as grpc from '@grpc/grpc-js';
import * as protoLoader from '@grpc/proto-loader';
import { ProtoGrpcType } from './proto/example';
import { ServerMessage } from './proto/example_package/ServerMessage';
const host = '0.0.0.0:9090';
const packageDefinition = protoLoader.loadSync('./proto/example.proto', {
longs: String,
enums: String,
defaults: true,
oneofs: true,
});
const proto = grpc.loadPackageDefinition(
packageDefinition
) as unknown as ProtoGrpcType;
const client = new proto.example_package.Example(
host,
grpc.credentials.createInsecure()
);
const deadline = new Date();
deadline.setSeconds(deadline.getSeconds() + 5);
client.waitForReady(deadline, (error?: Error) => {
if (error) {
console.log(`Client connect error: ${error.message}`);
} else {
onClientReady();
}
});
function onClientReady() {
switch (process.argv[process.argv.length - 1]) {
case '--unary':
doUnaryCall();
break;
case '--server-streaming':
doServerStreamingCall();
break;
case '--client-streaming':
doClientStreamingCall();
break;
case '--bidi-streaming':
doBidirectionalStreamingCall();
break;
default:
throw new Error('Example not specified');
}
}
function doUnaryCall() {
client.unaryCall(
{
clientMessage: 'Message from client',
},
(error?: grpc.ServiceError | null, serverMessage?: ServerMessage) => {
if (error) {
console.error(error.message);
} else if (serverMessage) {
console.log(
`(client) Got server message: ${serverMessage.serverMessage}`
);
}
}
);
}
function doServerStreamingCall() {
const stream = client.serverStreamingCall({
clientMessage: 'Message from client',
});
stream.on('data', (serverMessage: ServerMessage) => {
console.log(`(client) Got server message: ${serverMessage.serverMessage}`);
});
}
function doClientStreamingCall() {
const stream = client.clientStreamingCall((error?: grpc.ServiceError | null) => {
if (error) {
console.error(error.message);
}
});
stream.write({
clientMessage: 'Message from client',
});
}
function doBidirectionalStreamingCall() {
const stream = client.bidirectionalStreamingCall();
// Server stream
stream.on('data', (serverMessage: ServerMessage) => {
console.log(`(client) Got server message: ${serverMessage.serverMessage}`);
});
// Client stream
stream.write({
clientMessage: 'Message from client',
});
}
================================================
FILE: examples/grpc-proto-loader/package.json
================================================
{
"name": "grpc-proto-loader-example",
"version": "1.0.0",
"description": "",
"keywords": [],
"author": "",
"license": "ISC",
"bugs": {
"url": "https://github.com/badsyntax/grpc-js-types/issues"
},
"repository": {
"type": "git",
"url": "https://github.com/badsyntax/grpc-js-types"
},
"scripts": {
"build": "npm run build:typescript",
"build:typescript": "tsc -p .",
"watch": "npm run build:typescript -- -w",
"build:proto": "proto-loader-gen-types --longs=String --enums=String --defaults --oneofs --grpcLib=@grpc/grpc-js --outDir=proto/ proto/*.proto",
"prewatch": "npm run build:proto",
"prebuild": "npm run build:proto",
"lint": "npm run lint:prettier && npm run lint:eslint",
"lint:prettier": "prettier --check \"**/*.{ts,js,json,svg,md,yml}\"",
"lint:eslint": "eslint . --ext .js,.ts",
"lint:fix": "npm run lint:fix:prettier && npm run lint:eslint -- --fix",
"lint:fix:prettier": "prettier --write '**/*.{ts,tsx,js,json,svg,md,yml}'",
"start:server": "node server",
"start:client": "node client"
},
"dependencies": {
"@grpc/grpc-js": "^1.6.8",
"@grpc/proto-loader": "^0.7.0"
},
"devDependencies": {
"@tsconfig/node12": "^1.0.11",
"@types/node": "^15.0.3",
"@typescript-eslint/eslint-plugin": "^5.31.0",
"@typescript-eslint/parser": "^5.31.0",
"eslint": "^8.20.0",
"eslint-config-prettier": "^8.5.0",
"eslint-plugin-node": "^11.1.0",
"eslint-plugin-prettier": "^4.2.1",
"prettier": "^2.7.1",
"typescript": "^4.7.4"
},
"eslintConfig": {
"ignorePatterns": [
"**/*.js",
"proto/**/*.ts"
],
"env": {
"browser": false,
"es6": true,
"node": true
},
"parserOptions": {
"project": "./tsconfig.json",
"ecmaVersion": 2018,
"sourceType": "module"
},
"extends": [
"plugin:@typescript-eslint/recommended",
"plugin:prettier/recommended"
]
},
"prettier": {
"singleQuote": true,
"tabWidth": 2,
"printWidth": 80,
"useTabs": false
}
}
================================================
FILE: examples/grpc-proto-loader/proto/example.proto
================================================
syntax = "proto3";
package example_package;
message ServerMessage {
string server_message = 1;
}
message ClientMessage {
string client_message = 1;
}
service Example {
rpc unaryCall(ClientMessage) returns (ServerMessage) {}
rpc serverStreamingCall(ClientMessage) returns (stream ServerMessage) {}
rpc clientStreamingCall(stream ClientMessage) returns (ServerMessage) {}
rpc bidirectionalStreamingCall(stream ClientMessage) returns (stream ServerMessage) {}
}
================================================
FILE: examples/grpc-proto-loader/proto/example.ts
================================================
import type * as grpc from '@grpc/grpc-js';
import type { MessageTypeDefinition } from '@grpc/proto-loader';
import type { ExampleClient as _example_package_ExampleClient, ExampleDefinition as _example_package_ExampleDefinition } from './example_package/Example';
type SubtypeConstructor<Constructor extends new (...args: any) => any, Subtype> = {
new(...args: ConstructorParameters<Constructor>): Subtype;
};
export interface ProtoGrpcType {
example_package: {
ClientMessage: MessageTypeDefinition
Example: SubtypeConstructor<typeof grpc.Client, _example_package_ExampleClient> & { service: _example_package_ExampleDefinition }
ServerMessage: MessageTypeDefinition
}
}
================================================
FILE: examples/grpc-proto-loader/proto/example_package/ClientMessage.ts
================================================
// Original file: proto/example.proto
export interface ClientMessage {
'clientMessage'?: (string);
}
export interface ClientMessage__Output {
'clientMessage': (string);
}
================================================
FILE: examples/grpc-proto-loader/proto/example_package/Example.ts
================================================
// Original file: proto/example.proto
import type * as grpc from '@grpc/grpc-js'
import type { MethodDefinition } from '@grpc/proto-loader'
import type { ClientMessage as _example_package_ClientMessage, ClientMessage__Output as _example_package_ClientMessage__Output } from '../example_package/ClientMessage';
import type { ServerMessage as _example_package_ServerMessage, ServerMessage__Output as _example_package_ServerMessage__Output } from '../example_package/ServerMessage';
export interface ExampleClient extends grpc.Client {
bidirectionalStreamingCall(metadata: grpc.Metadata, options?: grpc.CallOptions): grpc.ClientDuplexStream<_example_package_ClientMessage, _example_package_ServerMessage__Output>;
bidirectionalStreamingCall(options?: grpc.CallOptions): grpc.ClientDuplexStream<_example_package_ClientMessage, _example_package_ServerMessage__Output>;
bidirectionalStreamingCall(metadata: grpc.Metadata, options?: grpc.CallOptions): grpc.ClientDuplexStream<_example_package_ClientMessage, _example_package_ServerMessage__Output>;
bidirectionalStreamingCall(options?: grpc.CallOptions): grpc.ClientDuplexStream<_example_package_ClientMessage, _example_package_ServerMessage__Output>;
clientStreamingCall(metadata: grpc.Metadata, options: grpc.CallOptions, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientWritableStream<_example_package_ClientMessage>;
clientStreamingCall(metadata: grpc.Metadata, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientWritableStream<_example_package_ClientMessage>;
clientStreamingCall(options: grpc.CallOptions, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientWritableStream<_example_package_ClientMessage>;
clientStreamingCall(callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientWritableStream<_example_package_ClientMessage>;
clientStreamingCall(metadata: grpc.Metadata, options: grpc.CallOptions, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientWritableStream<_example_package_ClientMessage>;
clientStreamingCall(metadata: grpc.Metadata, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientWritableStream<_example_package_ClientMessage>;
clientStreamingCall(options: grpc.CallOptions, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientWritableStream<_example_package_ClientMessage>;
clientStreamingCall(callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientWritableStream<_example_package_ClientMessage>;
serverStreamingCall(argument: _example_package_ClientMessage, metadata: grpc.Metadata, options?: grpc.CallOptions): grpc.ClientReadableStream<_example_package_ServerMessage__Output>;
serverStreamingCall(argument: _example_package_ClientMessage, options?: grpc.CallOptions): grpc.ClientReadableStream<_example_package_ServerMessage__Output>;
serverStreamingCall(argument: _example_package_ClientMessage, metadata: grpc.Metadata, options?: grpc.CallOptions): grpc.ClientReadableStream<_example_package_ServerMessage__Output>;
serverStreamingCall(argument: _example_package_ClientMessage, options?: grpc.CallOptions): grpc.ClientReadableStream<_example_package_ServerMessage__Output>;
unaryCall(argument: _example_package_ClientMessage, metadata: grpc.Metadata, options: grpc.CallOptions, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientUnaryCall;
unaryCall(argument: _example_package_ClientMessage, metadata: grpc.Metadata, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientUnaryCall;
unaryCall(argument: _example_package_ClientMessage, options: grpc.CallOptions, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientUnaryCall;
unaryCall(argument: _example_package_ClientMessage, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientUnaryCall;
unaryCall(argument: _example_package_ClientMessage, metadata: grpc.Metadata, options: grpc.CallOptions, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientUnaryCall;
unaryCall(argument: _example_package_ClientMessage, metadata: grpc.Metadata, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientUnaryCall;
unaryCall(argument: _example_package_ClientMessage, options: grpc.CallOptions, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientUnaryCall;
unaryCall(argument: _example_package_ClientMessage, callback: grpc.requestCallback<_example_package_ServerMessage__Output>): grpc.ClientUnaryCall;
}
export interface ExampleHandlers extends grpc.UntypedServiceImplementation {
bidirectionalStreamingCall: grpc.handleBidiStreamingCall<_example_package_ClientMessage__Output, _example_package_ServerMessage>;
clientStreamingCall: grpc.handleClientStreamingCall<_example_package_ClientMessage__Output, _example_package_ServerMessage>;
serverStreamingCall: grpc.handleServerStreamingCall<_example_package_ClientMessage__Output, _example_package_ServerMessage>;
unaryCall: grpc.handleUnaryCall<_example_package_ClientMessage__Output, _example_package_ServerMessage>;
}
export interface ExampleDefinition extends grpc.ServiceDefinition {
bidirectionalStreamingCall: MethodDefinition<_example_package_ClientMessage, _example_package_ServerMessage, _example_package_ClientMessage__Output, _example_package_ServerMessage__Output>
clientStreamingCall: MethodDefinition<_example_package_ClientMessage, _example_package_ServerMessage, _example_package_ClientMessage__Output, _example_package_ServerMessage__Output>
serverStreamingCall: MethodDefinition<_example_package_ClientMessage, _example_package_ServerMessage, _example_package_ClientMessage__Output, _example_package_ServerMessage__Output>
unaryCall: MethodDefinition<_example_package_ClientMessage, _example_package_ServerMessage, _example_package_ClientMessage__Output, _example_package_ServerMessage__Output>
}
================================================
FILE: examples/grpc-proto-loader/proto/example_package/ServerMessage.ts
================================================
// Original file: proto/example.proto
export interface ServerMessage {
'serverMessage'?: (string);
}
export interface ServerMessage__Output {
'serverMessage': (string);
}
================================================
FILE: examples/grpc-proto-loader/server.ts
================================================
import * as grpc from '@grpc/grpc-js';
import * as protoLoader from '@grpc/proto-loader';
import { ProtoGrpcType } from './proto/example';
import { ClientMessage } from './proto/example_package/ClientMessage';
import { ExampleHandlers } from './proto/example_package/Example';
import { ServerMessage } from './proto/example_package/ServerMessage';
const host = '0.0.0.0:9090';
const exampleServer: ExampleHandlers = {
unaryCall(
call: grpc.ServerUnaryCall<ClientMessage, ServerMessage>,
callback: grpc.sendUnaryData<ServerMessage>
) {
if (call.request) {
console.log(`(server) Got client message: ${call.request.clientMessage}`);
}
callback(null, {
serverMessage: 'Message from server',
});
},
serverStreamingCall(
call: grpc.ServerWritableStream<ClientMessage, ServerMessage>
) {
call.write({
serverMessage: 'Message from server',
});
},
clientStreamingCall(
call: grpc.ServerReadableStream<ClientMessage, ServerMessage>
) {
call.on('data', (clientMessage: ClientMessage) => {
console.log(
`(server) Got client message: ${clientMessage.clientMessage}`
);
});
},
bidirectionalStreamingCall(
call: grpc.ServerDuplexStream<ClientMessage, ServerMessage>
) {
call.write({
serverMessage: 'Message from server',
});
call.on('data', (clientMessage: ClientMessage) => {
console.log(
`(server) Got client message: ${clientMessage.clientMessage}`
);
});
},
};
function getServer(): grpc.Server {
const packageDefinition = protoLoader.loadSync('./proto/example.proto', {
longs: String,
enums: String,
defaults: true,
oneofs: true,
});
const proto = grpc.loadPackageDefinition(
packageDefinition
) as unknown as ProtoGrpcType;
const server = new grpc.Server();
server.addService(proto.example_package.Example.service, exampleServer);
return server;
}
if (require.main === module) {
const server = getServer();
server.bindAsync(
host,
grpc.ServerCredentials.createInsecure(),
(err: Error | null, port: number) => {
if (err) {
console.error(`Server error: ${err.message}`);
} else {
console.log(`Server bound on port: ${port}`);
server.start();
}
}
);
}
================================================
FILE: examples/grpc-proto-loader/tsconfig.json
================================================
{
"extends": "@tsconfig/node12/tsconfig.json",
"exclude": ["node_modules"]
}
================================================
FILE: examples/grpc-web/.gitignore
================================================
node_modules
*.js
proto/*.ts
dist/
================================================
FILE: examples/grpc-web/.npmrc
================================================
registry=https://registry.npmjs.org/
================================================
FILE: examples/grpc-web/.prettierignore
================================================
package-lock.json
dist/
================================================
FILE: examples/grpc-web/.vscode/extensions.json
================================================
{
"recommendations": [
"dbaeumer.vscode-eslint",
"EditorConfig.EditorConfig",
"esbenp.prettier-vscode",
"streetsidesoftware.code-spell-checker",
"zxh404.vscode-proto3"
]
}
================================================
FILE: examples/grpc-web/.vscode/settings.json
================================================
{
"typescript.tsc.autoDetect": "off",
"typescript.updateImportsOnFileMove.enabled": "always",
"files.insertFinalNewline": true,
"files.trimTrailingWhitespace": true,
"eslint.validate": ["javascript", "typescript"],
"editor.formatOnSave": false,
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true,
"source.organizeImports": false
},
"[markdown]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[json]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[yaml]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"cSpell.language": "en-GB",
"cSpell.words": ["grpc"]
}
================================================
FILE: examples/grpc-web/README.md
================================================
# grpc-web
This examples shows how to use the [proto compiler](https://www.npmjs.com/package/grpc-tools), [`ts-protoc-gen`](https://www.npmjs.com/package/ts-protoc-gen), [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js), [`protoc-gen-grpc-web`](https://www.npmjs.com/package/protoc-gen-grpc-web) & [`grpc-web`](https://www.npmjs.com/package/grpc-web) to build a fully typed gRPC CLI chat application that runs on Node.js and your browser.
The [`ts-protoc-gen`](https://www.npmjs.com/package/ts-protoc-gen) compiler plugin is used to generate TypeScript files and the [`protoc-gen-grpc-web`](https://www.npmjs.com/package/protoc-gen-grpc-web) compiler plugin is used to generate the grpc-web files from the proto definitions. The generated code uses [`google-protobuf`](https://www.npmjs.com/package/google-protobuf) & [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js) at runtime.
## App layout
- [package.json](./package.json) - Dependencies and node build scripts
- [compile-proto.sh](./compile-proto.sh) - The proto compiler script
- [proto/](./proto/) - Protobuf definitions and generated types
- [server.ts](./server.ts) - The grpc server
- [client.ts](./client.ts) - The grpc client
## Generating the Types
```sh
npm install
# Apple M1 users should install for x64 due to grpc-tools not supporting arm64
npm install --target_arch=x64
./compile-proto.sh
```
### Running the app
(Note, docker is required to run the envoy proxy.)
Run the demo:
```bash
npm install
npm run build
npm run start:proxy
npm run start:server
python3 -m http.server 8081
```
Open http://localhost:8081/ in multiple browser windows and chat to yourself.
Development workflow:
```bash
npm run watch:typescript
npm run watch:webpack
npm run start:proxy
npm run start:server
python3 -m http.server 8081
```
## Credits
The chat application idea is inspired from https://techblog.fexcofts.com/2018/07/20/grpc-nodejs-chat-example/
================================================
FILE: examples/grpc-web/client.ts
================================================
/* eslint-disable @typescript-eslint/no-non-null-assertion */
import { RpcError as GrpcWebError } from 'grpc-web';
import { ChatClient } from './proto/chat_grpc_web_pb';
import { ClientMessage, ServerMessage } from './proto/chat_pb';
let user: string;
window.addEventListener('DOMContentLoaded', () => {
document.getElementById('submit-name')?.addEventListener(
'submit',
async (e) => {
e.preventDefault();
user = (document.getElementById('name') as HTMLFormElement)?.value;
if (user) {
document.getElementById('submit-message')!.style.display = 'block';
document.getElementById('submit-name')!.style.display = 'none';
initChat(user);
}
},
false
);
});
async function initChat(user: string) {
const client = new ChatClient('http://' + window.location.hostname + ':8080');
const clientMessage = new ClientMessage();
clientMessage.setUser(user);
const stream = client.join(clientMessage);
stream.on('data', (message: ServerMessage) => {
const messageElement = document.createElement('div');
messageElement.innerText = `${message.getUser()}: ${message.getText()}`;
document.getElementById('messages')!.appendChild(messageElement);
});
function sendMessage(message: string) {
const clientMessage = new ClientMessage();
clientMessage.setUser(user);
clientMessage.setText(message);
client.send(
clientMessage,
undefined,
(err: GrpcWebError, response: ServerMessage) => {
if (err) {
console.error(err);
} else {
console.log('response', response.toObject());
(document.getElementById('message') as HTMLFormElement)!.value = '';
}
}
);
}
document.getElementById('submit-message')?.addEventListener(
'submit',
(e) => {
e.preventDefault();
const message = (document.getElementById('message') as HTMLFormElement)
?.value;
sendMessage(message);
},
false
);
}
================================================
FILE: examples/grpc-web/compile-proto.sh
================================================
#!/usr/bin/env bash
OUT_DIR="."
TS_OUT_DIR="."
IN_DIR="./proto"
PROTOC="$(npm bin)/grpc_tools_node_protoc"
PROTOC_GEN_TS_PATH="$(npm bin)/protoc-gen-ts"
PROTOC_GEN_GRPC_PATH="$(npm bin)/grpc_tools_node_protoc_plugin"
PROTOC_GEN_GRPC_WEB_PATH="$(npm bin)/protoc-gen-grpc-web"
# generate grpc-web files & types
$PROTOC \
-I="./" \
--plugin=protoc-gen-grpc-web=${PROTOC_GEN_GRPC_WEB_PATH} \
--js_out=import_style=commonjs:$OUT_DIR \
--grpc-web_out=import_style=commonjs+dts,mode=grpcwebtext:$OUT_DIR \
"$IN_DIR"/*.proto
# generate grpc-js files & types
$PROTOC \
-I="./" \
--plugin=protoc-gen-ts=$PROTOC_GEN_TS_PATH \
--plugin=protoc-gen-grpc=${PROTOC_GEN_GRPC_PATH} \
--js_out=import_style=commonjs:$OUT_DIR \
--ts_out=service=grpc-node,mode=grpc-js:$TS_OUT_DIR \
--grpc_out=grpc_js:$OUT_DIR \
"$IN_DIR"/*.proto
================================================
FILE: examples/grpc-web/envoy.yaml
================================================
static_resources:
listeners:
- name: listener_0
address:
socket_address: { address: 0.0.0.0, port_value: 8080 }
filter_chains:
- filters:
- name: envoy.http_connection_manager
config:
codec_type: auto
stat_prefix: ingress_http
route_config:
name: local_route
virtual_hosts:
- name: local_service
domains: ["*"]
routes:
- match: { prefix: "/" }
route:
cluster: greeter_service
max_grpc_timeout: 0s
cors:
allow_origin_string_match:
- prefix: "*"
allow_methods: GET, PUT, DELETE, POST, OPTIONS
allow_headers: keep-alive,user-agent,cache-control,content-type,content-transfer-encoding,custom-header-1,x-accept-content-transfer-encoding,x-accept-response-streaming,x-user-agent,x-grpc-web,grpc-timeout
max_age: "1728000"
expose_headers: custom-header-1,grpc-status,grpc-message
http_filters:
- name: envoy.grpc_web
- name: envoy.cors
- name: envoy.router
clusters:
- name: greeter_service
connect_timeout: 0.25s
type: logical_dns
http2_protocol_options: {}
lb_policy: round_robin
hosts: [{ socket_address: { address: host.docker.internal, port_value: 9090 }}]
================================================
FILE: examples/grpc-web/index.html
================================================
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>gRPC-Web Example</title>
<script src="./dist/main.js"></script>
<style type="text/css">
#submit-message {
display: none;
}
#messages {
margin-bottom: 0.5rem;
}
.container {
display: flex;
flex-direction: column;
margin: 2rem;
}
</style>
</head>
<body>
<section class="container">
<div id="messages"></div>
<form id="submit-name" action="#">
<p>Enter your name to join the chat</p>
<input autofocus placeholder="Enter your name..." type="text" id="name" />
<button type="submit">Submit</button>
</form>
<form id="submit-message" action="#">
Chat
<input autofocus placeholder="Type a message..." id="message" type="text" />
<button type="submit">Submit</button>
</form>
</section>
</body>
</html>
================================================
FILE: examples/grpc-web/package.json
================================================
{
"name": "grpc-web-example",
"version": "1.0.0",
"description": "",
"private": true,
"scripts": {
"build": "npm run build:typescript && npm run build:webpack",
"build:typescript": "tsc -p .",
"build:proto": "./compile-proto.sh",
"build:webpack": "webpack ./client.js -c webpack.config.js",
"watch:typescript": "npm run build:typescript -- -w",
"watch:webpack": "npm run build:webpack -- -w",
"prebuild": "npm run build:proto",
"lint": "npm run lint:prettier && npm run lint:eslint",
"lint:prettier": "prettier --check \"**/*.{ts,js,json,svg,md,yml}\"",
"lint:eslint": "eslint . --ext .js,.ts",
"lint:fix": "npm run lint:fix:prettier && npm run lint:eslint -- --fix",
"lint:fix:prettier": "prettier --write '**/*.{ts,tsx,js,json,svg,md,yml}'",
"start:server": "node server",
"start:proxy": "docker run -d -p 8080:8080 -v \"$(pwd)\"/envoy.yaml:/etc/envoy/envoy.yaml:ro envoyproxy/envoy:v1.15.0"
},
"keywords": [],
"author": "",
"license": "ISC",
"devDependencies": {
"@grpc/grpc-js": "^1.6.8",
"@grpc/proto-loader": "^0.7.0",
"@tsconfig/node12": "^1.0.11",
"@types/google-protobuf": "^3.15.6",
"@types/node": "^14.14.14",
"@typescript-eslint/eslint-plugin": "^5.31.0",
"@typescript-eslint/parser": "^5.31.0",
"eslint": "^8.20.0",
"eslint-config-prettier": "^8.5.0",
"eslint-plugin-import": "^2.26.0",
"eslint-plugin-node": "^11.1.0",
"eslint-plugin-prettier": "^4.2.1",
"google-protobuf": "^3.21.0",
"grpc-tools": "^1.11.2",
"grpc-web": "^1.3.1",
"prettier": "^2.7.1",
"prettier-plugin-organize-imports": "^3.0.0",
"protoc-gen-grpc-web": "^1.4.0",
"ts-protoc-gen": "^0.15.0",
"typescript": "^4.7.4",
"webpack": "^5.74.0",
"webpack-cli": "^4.10.0"
},
"eslintConfig": {
"ignorePatterns": [
"**/*.js",
"proto/*.ts",
"generated"
],
"env": {
"browser": false,
"es6": true,
"node": true
},
"parserOptions": {
"project": "./tsconfig.json",
"ecmaVersion": 2018,
"sourceType": "module"
},
"extends": [
"plugin:@typescript-eslint/recommended",
"prettier/@typescript-eslint",
"plugin:prettier/recommended",
"plugin:import/errors",
"plugin:import/warnings",
"plugin:import/typescript"
]
},
"prettier": {
"singleQuote": true,
"tabWidth": 2,
"printWidth": 80,
"useTabs": false
}
}
================================================
FILE: examples/grpc-web/proto/chat.proto
================================================
syntax = "proto3";
package chat_package;
message ServerMessage {
string user = 1;
string text = 2;
}
message ClientMessage {
string user = 1;
string text = 2;
}
service Chat {
rpc join(ClientMessage) returns (stream ServerMessage) {}
rpc send(ClientMessage) returns (ServerMessage) {}
}
================================================
FILE: examples/grpc-web/server.ts
================================================
import * as grpc from '@grpc/grpc-js';
import { ChatService, IChatServer } from './proto/chat_grpc_pb';
import { ClientMessage, ServerMessage } from './proto/chat_pb';
const users: grpc.ServerWritableStream<ClientMessage, ServerMessage>[] = [];
const messages: ClientMessage[] = [];
function notifyChat(message: ServerMessage) {
messages.push(message);
users.forEach((user) => {
user.write(message);
});
}
const chatServer: IChatServer = {
join(call: grpc.ServerWritableStream<ClientMessage, ServerMessage>): void {
users.push(call);
const serverMessage = new ServerMessage();
serverMessage.setUser('Server');
serverMessage.setText(`${call.request?.getUser()} joined`);
notifyChat(serverMessage);
},
send(
call: grpc.ServerUnaryCall<ClientMessage, ServerMessage>,
callback: grpc.sendUnaryData<ServerMessage>
): void {
if (call.request) {
const serverMessage = new ServerMessage();
serverMessage.setUser(call.request.getUser());
serverMessage.setText(call.request.getText());
notifyChat(serverMessage);
callback(null, serverMessage);
}
},
};
export function getServer(): grpc.Server {
const server = new grpc.Server();
server.addService(ChatService, chatServer);
return server;
}
if (require.main === module) {
const server = getServer();
server.bindAsync(
'0.0.0.0:9090',
grpc.ServerCredentials.createInsecure(),
(err: Error | null, port: number) => {
if (err) {
console.error(`Server error: ${err.message}`);
} else {
console.log(`Server bound on port: ${port}`);
server.start();
}
}
);
}
================================================
FILE: examples/grpc-web/tsconfig.json
================================================
{
"extends": "@tsconfig/node12/tsconfig.json",
"compilerOptions": {
"lib": ["DOM"]
},
"exclude": ["node_modules"]
}
================================================
FILE: examples/grpc-web/webpack.config.ts
================================================
import * as path from 'path';
export default {
mode: 'production',
entry: {
index: './client.js',
},
output: {
filename: '[name].js',
chunkFilename: '[name].js',
path: path.resolve(__dirname, 'dist'),
},
};
================================================
FILE: examples/grpc_tools_node_protoc_ts/.gitignore
================================================
node_modules
**/*.js
!proto/*.js
================================================
FILE: examples/grpc_tools_node_protoc_ts/.npmrc
================================================
registry=https://registry.npmjs.org/
================================================
FILE: examples/grpc_tools_node_protoc_ts/.prettierignore
================================================
package-lock.json
proto/*.ts
================================================
FILE: examples/grpc_tools_node_protoc_ts/.vscode/extensions.json
================================================
{
"recommendations": [
"dbaeumer.vscode-eslint",
"EditorConfig.EditorConfig",
"esbenp.prettier-vscode",
"streetsidesoftware.code-spell-checker",
"zxh404.vscode-proto3"
]
}
================================================
FILE: examples/grpc_tools_node_protoc_ts/.vscode/settings.json
================================================
{
"typescript.tsc.autoDetect": "off",
"typescript.updateImportsOnFileMove.enabled": "always",
"files.insertFinalNewline": true,
"files.trimTrailingWhitespace": true,
"eslint.validate": ["javascript", "typescript"],
"editor.formatOnSave": false,
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true,
"source.organizeImports": false
},
"[markdown]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[json]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[yaml]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"cSpell.language": "en-GB",
"cSpell.words": [
"Unary",
"grpc"
]
}
================================================
FILE: examples/grpc_tools_node_protoc_ts/README.md
================================================
# grpc_tools_node_protoc_ts example
This example shows how to use the [proto compiler](https://www.npmjs.com/package/grpc-tools), [`grpc_tools_node_protoc_ts`](https://www.npmjs.com/package/grpc_tools_node_protoc_ts) & [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js) to build a fully typed gRPC application that runs on Node.js.
The [proto compiler](https://www.npmjs.com/package/grpc-tools) and [`grpc_tools_node_protoc_ts`](https://www.npmjs.com/package/grpc_tools_node_protoc_ts) compiler plugin are used to generate JavaScript & TypeScript files from the proto definitions and [`google-protobuf`](https://www.npmjs.com/package/google-protobuf) & [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js) is used at runtime.
## App layout
- [package.json](./package.json) - Dependencies and node build scripts
- [compile-proto.sh](./compile-proto.sh) - The proto compiler script
- [server.ts](./server.ts) - The grpc server
- [client.ts](./client.ts) - The grpc client
## Generating the Types
Install dependencies:
```sh
npm install
# Apple M1 users should install for x64 due to grpc-tools not supporting arm64
npm i --target_arch=x64
```
Use [`grpc_tools_node_protoc_ts`](https://www.npmjs.com/package/grpc_tools_node_protoc_ts) to generate the TypeScript files:
```sh
./compile-proto.sh
```
This is aliased as a npm script:
```sh
npm run build:proto
```
### Running the App
This simple app demonstrates the different gRPC calls you can perform.
First generated the types and build the application files:
```sh
npm run build
```
Start the server:
```sh
npm run start:server
```
Now run the client by specifying which example you want to run:
```bash
npm run start:client -- --unary
npm run start:client -- --server-streaming
npm run start:client -- --client-streaming
npm run start:client -- --bidi-streaming
```
================================================
FILE: examples/grpc_tools_node_protoc_ts/client.ts
================================================
import * as grpc from '@grpc/grpc-js';
import { ExampleClient } from './proto/example_grpc_pb';
import { ClientMessage, ServerMessage } from './proto/example_pb';
const host = '0.0.0.0:9090';
const client = new ExampleClient(host, grpc.credentials.createInsecure());
const deadline = new Date();
deadline.setSeconds(deadline.getSeconds() + 5);
client.waitForReady(deadline, (error?: Error) => {
if (error) {
console.log(`Client connect error: ${error.message}`);
} else {
onClientReady();
}
});
function onClientReady() {
switch (process.argv[process.argv.length - 1]) {
case '--unary':
doUnaryCall();
break;
case '--server-streaming':
doServerStreamingCall();
break;
case '--client-streaming':
doClientStreamingCall();
break;
case '--bidi-streaming':
doBidirectionalStreamingCall();
break;
default:
throw new Error('Example not specified');
}
}
function doUnaryCall() {
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
client.unaryCall(
clientMessage,
(error: grpc.ServiceError | null, serverMessage?: ServerMessage) => {
if (error) {
console.error(error.message);
} else if (serverMessage) {
console.log(
`(client) Got server message: ${serverMessage.getServerMessage()}`
);
}
}
);
}
function doServerStreamingCall() {
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
const stream = client.serverStreamingCall(clientMessage);
stream.on('data', (serverMessage: ServerMessage) => {
console.log(
`(client) Got server message: ${serverMessage.getServerMessage()}`
);
});
}
function doClientStreamingCall() {
const stream = client.clientStreamingCall(
(error: grpc.ServiceError | null) => {
if (error) {
console.error(error.message);
}
}
);
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
stream.write(clientMessage);
}
function doBidirectionalStreamingCall() {
const stream = client.bidirectionalStreamingCall();
// Server stream
stream.on('data', (serverMessage: ServerMessage) => {
console.log(
`(client) Got server message: ${serverMessage.getServerMessage()}`
);
});
// Client stream
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
stream.write(clientMessage);
}
================================================
FILE: examples/grpc_tools_node_protoc_ts/compile-proto.sh
================================================
#!/usr/bin/env bash
OUT_DIR="."
TS_OUT_DIR="."
IN_DIR="./proto"
PROTOC="$(npm bin)/grpc_tools_node_protoc"
PROTOC_GEN_TS_PATH="$(npm bin)/protoc-gen-ts"
PROTOC_GEN_GRPC_PATH="$(npm bin)/grpc_tools_node_protoc_plugin"
$PROTOC \
-I="./" \
--plugin=protoc-gen-ts=$PROTOC_GEN_TS_PATH \
--plugin=protoc-gen-grpc=${PROTOC_GEN_GRPC_PATH} \
--js_out=import_style=commonjs:$OUT_DIR \
--grpc_out=grpc_js:$OUT_DIR \
--ts_out=grpc_js:$TS_OUT_DIR \
"$IN_DIR"/*.proto
================================================
FILE: examples/grpc_tools_node_protoc_ts/package.json
================================================
{
"name": "grpc-js-example",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"build": "npm run build:typescript",
"build:typescript": "tsc -p .",
"build:proto": "./compile-proto.sh",
"watch": "npm run build:typescript -- -w",
"prewatch": "npm run build:proto",
"prebuild": "npm run build:proto",
"lint": "npm run lint:prettier && npm run lint:eslint",
"lint:prettier": "prettier --check \"**/*.{ts,js,json,svg,md,yml}\"",
"lint:eslint": "eslint . --ext .js,.ts",
"lint:fix": "npm run lint:fix:prettier && npm run lint:eslint -- --fix",
"lint:fix:prettier": "prettier --write '**/*.{ts,tsx,js,json,svg,md,yml}'",
"start:server": "node server",
"start:client": "node client"
},
"keywords": [],
"author": "",
"license": "ISC",
"dependencies": {
"@grpc/grpc-js": "^1.6.8",
"google-protobuf": "^3.21.0"
},
"devDependencies": {
"@tsconfig/node12": "^1.0.11",
"@types/google-protobuf": "^3.15.6",
"@types/node": "^15.0.3",
"@typescript-eslint/eslint-plugin": "^5.31.0",
"@typescript-eslint/parser": "^5.31.0",
"eslint": "^8.20.0",
"eslint-config-prettier": "^8.5.0",
"eslint-plugin-node": "^11.1.0",
"eslint-plugin-prettier": "^4.2.1",
"grpc_tools_node_protoc_ts": "^5.3.2",
"grpc-tools": "^1.11.2",
"prettier": "^2.7.1",
"typescript": "^4.7.4"
},
"eslintConfig": {
"ignorePatterns": [
"**/*.js",
"proto/*.ts"
],
"env": {
"browser": false,
"es6": true,
"node": true
},
"parserOptions": {
"project": "./tsconfig.json",
"ecmaVersion": 2018,
"sourceType": "module"
},
"extends": [
"plugin:@typescript-eslint/recommended",
"plugin:prettier/recommended"
]
},
"prettier": {
"singleQuote": true,
"tabWidth": 2,
"printWidth": 80,
"useTabs": false
}
}
================================================
FILE: examples/grpc_tools_node_protoc_ts/proto/example.proto
================================================
syntax = "proto3";
package example_package;
message ServerMessage {
string server_message = 1;
}
message ClientMessage {
string client_message = 1;
}
service Example {
rpc unaryCall(ClientMessage) returns (ServerMessage) {}
rpc serverStreamingCall(ClientMessage) returns (stream ServerMessage) {}
rpc clientStreamingCall(stream ClientMessage) returns (ServerMessage) {}
rpc bidirectionalStreamingCall(stream ClientMessage) returns (stream ServerMessage) {}
}
================================================
FILE: examples/grpc_tools_node_protoc_ts/proto/example_grpc_pb.d.ts
================================================
// package: example_package
// file: proto/example.proto
/* tslint:disable */
/* eslint-disable */
import * as grpc from "@grpc/grpc-js";
import * as proto_example_pb from "../proto/example_pb";
interface IExampleService extends grpc.ServiceDefinition<grpc.UntypedServiceImplementation> {
unaryCall: IExampleService_IunaryCall;
serverStreamingCall: IExampleService_IserverStreamingCall;
clientStreamingCall: IExampleService_IclientStreamingCall;
bidirectionalStreamingCall: IExampleService_IbidirectionalStreamingCall;
}
interface IExampleService_IunaryCall extends grpc.MethodDefinition<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage> {
path: "/example_package.Example/unaryCall";
requestStream: false;
responseStream: false;
requestSerialize: grpc.serialize<proto_example_pb.ClientMessage>;
requestDeserialize: grpc.deserialize<proto_example_pb.ClientMessage>;
responseSerialize: grpc.serialize<proto_example_pb.ServerMessage>;
responseDeserialize: grpc.deserialize<proto_example_pb.ServerMessage>;
}
interface IExampleService_IserverStreamingCall extends grpc.MethodDefinition<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage> {
path: "/example_package.Example/serverStreamingCall";
requestStream: false;
responseStream: true;
requestSerialize: grpc.serialize<proto_example_pb.ClientMessage>;
requestDeserialize: grpc.deserialize<proto_example_pb.ClientMessage>;
responseSerialize: grpc.serialize<proto_example_pb.ServerMessage>;
responseDeserialize: grpc.deserialize<proto_example_pb.ServerMessage>;
}
interface IExampleService_IclientStreamingCall extends grpc.MethodDefinition<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage> {
path: "/example_package.Example/clientStreamingCall";
requestStream: true;
responseStream: false;
requestSerialize: grpc.serialize<proto_example_pb.ClientMessage>;
requestDeserialize: grpc.deserialize<proto_example_pb.ClientMessage>;
responseSerialize: grpc.serialize<proto_example_pb.ServerMessage>;
responseDeserialize: grpc.deserialize<proto_example_pb.ServerMessage>;
}
interface IExampleService_IbidirectionalStreamingCall extends grpc.MethodDefinition<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage> {
path: "/example_package.Example/bidirectionalStreamingCall";
requestStream: true;
responseStream: true;
requestSerialize: grpc.serialize<proto_example_pb.ClientMessage>;
requestDeserialize: grpc.deserialize<proto_example_pb.ClientMessage>;
responseSerialize: grpc.serialize<proto_example_pb.ServerMessage>;
responseDeserialize: grpc.deserialize<proto_example_pb.ServerMessage>;
}
export const ExampleService: IExampleService;
export interface IExampleServer extends grpc.UntypedServiceImplementation {
unaryCall: grpc.handleUnaryCall<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
serverStreamingCall: grpc.handleServerStreamingCall<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
clientStreamingCall: grpc.handleClientStreamingCall<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
bidirectionalStreamingCall: grpc.handleBidiStreamingCall<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
}
export interface IExampleClient {
unaryCall(request: proto_example_pb.ClientMessage, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientUnaryCall;
unaryCall(request: proto_example_pb.ClientMessage, metadata: grpc.Metadata, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientUnaryCall;
unaryCall(request: proto_example_pb.ClientMessage, metadata: grpc.Metadata, options: Partial<grpc.CallOptions>, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientUnaryCall;
serverStreamingCall(request: proto_example_pb.ClientMessage, options?: Partial<grpc.CallOptions>): grpc.ClientReadableStream<proto_example_pb.ServerMessage>;
serverStreamingCall(request: proto_example_pb.ClientMessage, metadata?: grpc.Metadata, options?: Partial<grpc.CallOptions>): grpc.ClientReadableStream<proto_example_pb.ServerMessage>;
clientStreamingCall(callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
clientStreamingCall(metadata: grpc.Metadata, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
clientStreamingCall(options: Partial<grpc.CallOptions>, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
clientStreamingCall(metadata: grpc.Metadata, options: Partial<grpc.CallOptions>, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
bidirectionalStreamingCall(): grpc.ClientDuplexStream<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
bidirectionalStreamingCall(options: Partial<grpc.CallOptions>): grpc.ClientDuplexStream<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
bidirectionalStreamingCall(metadata: grpc.Metadata, options?: Partial<grpc.CallOptions>): grpc.ClientDuplexStream<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
}
export class ExampleClient extends grpc.Client implements IExampleClient {
constructor(address: string, credentials: grpc.ChannelCredentials, options?: Partial<grpc.ClientOptions>);
public unaryCall(request: proto_example_pb.ClientMessage, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientUnaryCall;
public unaryCall(request: proto_example_pb.ClientMessage, metadata: grpc.Metadata, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientUnaryCall;
public unaryCall(request: proto_example_pb.ClientMessage, metadata: grpc.Metadata, options: Partial<grpc.CallOptions>, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientUnaryCall;
public serverStreamingCall(request: proto_example_pb.ClientMessage, options?: Partial<grpc.CallOptions>): grpc.ClientReadableStream<proto_example_pb.ServerMessage>;
public serverStreamingCall(request: proto_example_pb.ClientMessage, metadata?: grpc.Metadata, options?: Partial<grpc.CallOptions>): grpc.ClientReadableStream<proto_example_pb.ServerMessage>;
public clientStreamingCall(callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
public clientStreamingCall(metadata: grpc.Metadata, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
public clientStreamingCall(options: Partial<grpc.CallOptions>, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
public clientStreamingCall(metadata: grpc.Metadata, options: Partial<grpc.CallOptions>, callback: (error: grpc.ServiceError | null, response: proto_example_pb.ServerMessage) => void): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
public bidirectionalStreamingCall(options?: Partial<grpc.CallOptions>): grpc.ClientDuplexStream<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
public bidirectionalStreamingCall(metadata?: grpc.Metadata, options?: Partial<grpc.CallOptions>): grpc.ClientDuplexStream<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
}
================================================
FILE: examples/grpc_tools_node_protoc_ts/proto/example_pb.d.ts
================================================
// package: example_package
// file: proto/example.proto
/* tslint:disable */
/* eslint-disable */
import * as jspb from "google-protobuf";
export class ServerMessage extends jspb.Message {
getServerMessage(): string;
setServerMessage(value: string): ServerMessage;
serializeBinary(): Uint8Array;
toObject(includeInstance?: boolean): ServerMessage.AsObject;
static toObject(includeInstance: boolean, msg: ServerMessage): ServerMessage.AsObject;
static extensions: {[key: number]: jspb.ExtensionFieldInfo<jspb.Message>};
static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo<jspb.Message>};
static serializeBinaryToWriter(message: ServerMessage, writer: jspb.BinaryWriter): void;
static deserializeBinary(bytes: Uint8Array): ServerMessage;
static deserializeBinaryFromReader(message: ServerMessage, reader: jspb.BinaryReader): ServerMessage;
}
export namespace ServerMessage {
export type AsObject = {
serverMessage: string,
}
}
export class ClientMessage extends jspb.Message {
getClientMessage(): string;
setClientMessage(value: string): ClientMessage;
serializeBinary(): Uint8Array;
toObject(includeInstance?: boolean): ClientMessage.AsObject;
static toObject(includeInstance: boolean, msg: ClientMessage): ClientMessage.AsObject;
static extensions: {[key: number]: jspb.ExtensionFieldInfo<jspb.Message>};
static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo<jspb.Message>};
static serializeBinaryToWriter(message: ClientMessage, writer: jspb.BinaryWriter): void;
static deserializeBinary(bytes: Uint8Array): ClientMessage;
static deserializeBinaryFromReader(message: ClientMessage, reader: jspb.BinaryReader): ClientMessage;
}
export namespace ClientMessage {
export type AsObject = {
clientMessage: string,
}
}
================================================
FILE: examples/grpc_tools_node_protoc_ts/server.ts
================================================
import * as grpc from '@grpc/grpc-js';
import { ExampleService, IExampleServer } from './proto/example_grpc_pb';
import { ClientMessage, ServerMessage } from './proto/example_pb';
const host = '0.0.0.0:9090';
const exampleServer: IExampleServer = {
unaryCall(
call: grpc.ServerUnaryCall<ClientMessage, ServerMessage>,
callback: grpc.sendUnaryData<ServerMessage>
) {
if (call.request) {
console.log(
`(server) Got client message: ${call.request.getClientMessage()}`
);
}
const serverMessage = new ServerMessage();
serverMessage.setServerMessage('Message from server');
callback(null, serverMessage);
},
serverStreamingCall(
call: grpc.ServerWritableStream<ClientMessage, ServerMessage>
) {
const serverMessage = new ServerMessage();
serverMessage.setServerMessage('Message from server');
call.write(serverMessage);
},
clientStreamingCall(
call: grpc.ServerReadableStream<ClientMessage, ServerMessage>
) {
call.on('data', (clientMessage: ClientMessage) => {
console.log(
`(server) Got client message: ${clientMessage.getClientMessage()}`
);
});
},
bidirectionalStreamingCall(
call: grpc.ServerDuplexStream<ClientMessage, ServerMessage>
) {
call.on('data', (clientMessage: ClientMessage) => {
console.log(
`(server) Got client message: ${clientMessage.getClientMessage()}`
);
});
const serverMessage = new ServerMessage();
serverMessage.setServerMessage('Message from server');
call.write(serverMessage);
},
};
function getServer(): grpc.Server {
const server = new grpc.Server();
server.addService(ExampleService, exampleServer);
return server;
}
if (require.main === module) {
const server = getServer();
server.bindAsync(
host,
grpc.ServerCredentials.createInsecure(),
(err: Error | null, port: number) => {
if (err) {
console.error(`Server error: ${err.message}`);
} else {
console.log(`Server bound on port: ${port}`);
server.start();
}
}
);
}
================================================
FILE: examples/grpc_tools_node_protoc_ts/tsconfig.json
================================================
{
"extends": "@tsconfig/node12/tsconfig.json",
"exclude": ["node_modules"]
}
================================================
FILE: examples/ts-protoc-gen/.gitignore
================================================
node_modules
*.js
!proto/*.js
================================================
FILE: examples/ts-protoc-gen/.npmrc
================================================
registry=https://registry.npmjs.org/
================================================
FILE: examples/ts-protoc-gen/.prettierignore
================================================
package-lock.json
proto/*.ts
================================================
FILE: examples/ts-protoc-gen/.vscode/extensions.json
================================================
{
"recommendations": [
"dbaeumer.vscode-eslint",
"EditorConfig.EditorConfig",
"esbenp.prettier-vscode",
"streetsidesoftware.code-spell-checker",
"zxh404.vscode-proto3"
]
}
================================================
FILE: examples/ts-protoc-gen/.vscode/settings.json
================================================
{
"typescript.tsc.autoDetect": "off",
"typescript.updateImportsOnFileMove.enabled": "always",
"files.insertFinalNewline": true,
"files.trimTrailingWhitespace": true,
"eslint.validate": ["javascript", "typescript"],
"editor.formatOnSave": false,
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true,
"source.organizeImports": false
},
"[markdown]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[json]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[yaml]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"cSpell.language": "en-GB",
"cSpell.words": ["grpc"]
}
================================================
FILE: examples/ts-protoc-gen/README.md
================================================
# ts-protoc-gen
This examples shows how to use the [proto compiler](https://www.npmjs.com/package/grpc-tools), [`ts-protoc-gen`](https://www.npmjs.com/package/ts-protoc-gen) & [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js) to build a fully typed gRPC CLI application that runs on Node.js.
The [proto compiler](https://www.npmjs.com/package/grpc-tools) and [`ts-protoc-gen`](https://www.npmjs.com/package/ts-protoc-gen) compiler plugin are used to generate JavaScript & TypeScript files from the proto definitions.
[`google-protobuf`](https://www.npmjs.com/package/google-protobuf) & [`@grpc/grpc-js`](https://www.npmjs.com/package/@grpc/grpc-js) are used at runtime.
## App layout
- [package.json](./package.json) - Dependencies and node build scripts
- [compile-proto.sh](./compile-proto.sh) - The proto compiler script
- [proto/](./proto/) - Protobuf definitions and generated types
- [server.ts](./server.ts) - The grpc server
- [client.ts](./client.ts) - The grpc client
## Generating the Types
Install dependencies:
```sh
npm install
# Apple M1 users should install for x64 due to grpc-tools not supporting arm64
npm install --target_arch=x64
```
Use [proto compiler](https://www.npmjs.com/package/grpc-tools) and [`ts-protoc-gen`](https://www.npmjs.com/package/ts-protoc-gen) to generate the TypeScript files:
```sh
./compile-proto.sh
```
This is aliased as a npm script:
```sh
npm run build:proto
```
### Running the App
This simple app demonstrates the different gRPC calls you can perform.
First generate the types and build the application files:
```sh
npm run build
```
Start the server:
```sh
npm run start:server
```
Now run the client by specifying which example you want to run:
```bash
npm run start:client -- --unary
npm run start:client -- --server-streaming
npm run start:client -- --client-streaming
npm run start:client -- --bidi-streaming
```
================================================
FILE: examples/ts-protoc-gen/client.ts
================================================
import * as grpc from '@grpc/grpc-js';
import { ExampleClient } from './proto/example_grpc_pb';
import { ClientMessage, ServerMessage } from './proto/example_pb';
const host = '0.0.0.0:9090';
const client = new ExampleClient(host, grpc.credentials.createInsecure());
const deadline = new Date();
deadline.setSeconds(deadline.getSeconds() + 5);
client.waitForReady(deadline, (error?: Error) => {
if (error) {
console.log(`Client connect error: ${error.message}`);
} else {
onClientReady();
}
});
function onClientReady() {
switch (process.argv[process.argv.length - 1]) {
case '--unary':
doUnaryCall();
break;
case '--server-streaming':
doServerStreamingCall();
break;
case '--client-streaming':
doClientStreamingCall();
break;
case '--bidi-streaming':
doBidirectionalStreamingCall();
break;
default:
throw new Error('Example not specified');
}
}
function doUnaryCall() {
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
client.unaryCall(
clientMessage,
(error: grpc.ServiceError | null, serverMessage?: ServerMessage) => {
if (error) {
console.error(error.message);
} else if (serverMessage) {
console.log(
`(client) Got server message: ${serverMessage.getServerMessage()}`
);
}
}
);
}
function doServerStreamingCall() {
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
const stream = client.serverStreamingCall(clientMessage);
stream.on('data', (serverMessage: ServerMessage) => {
console.log(
`(client) Got server message: ${serverMessage.getServerMessage()}`
);
});
}
function doClientStreamingCall() {
const stream = client.clientStreamingCall(
(error: grpc.ServiceError | null) => {
if (error) {
console.error(error.message);
}
}
);
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
stream.write(clientMessage);
}
function doBidirectionalStreamingCall() {
const stream = client.bidirectionalStreamingCall();
// Server stream
stream.on('data', (serverMessage: ServerMessage) => {
console.log(
`(client) Got server message: ${serverMessage.getServerMessage()}`
);
});
// Client stream
const clientMessage = new ClientMessage();
clientMessage.setClientMessage('Message from client');
stream.write(clientMessage);
}
================================================
FILE: examples/ts-protoc-gen/compile-proto.sh
================================================
#!/usr/bin/env bash
OUT_DIR="."
TS_OUT_DIR="."
IN_DIR="./proto"
PROTOC="$(npm bin)/grpc_tools_node_protoc"
PROTOC_GEN_TS_PATH="$(npm bin)/protoc-gen-ts"
PROTOC_GEN_GRPC_PATH="$(npm bin)/grpc_tools_node_protoc_plugin"
$PROTOC \
-I="./" \
--plugin=protoc-gen-ts=$PROTOC_GEN_TS_PATH \
--plugin=protoc-gen-grpc=$PROTOC_GEN_GRPC_PATH \
--js_out=import_style=commonjs:$OUT_DIR \
--grpc_out=grpc_js:$OUT_DIR \
--ts_out=service=grpc-node,mode=grpc-js:$TS_OUT_DIR \
"$IN_DIR"/*.proto
================================================
FILE: examples/ts-protoc-gen/package.json
================================================
{
"name": "grpc-js-example",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"build": "npm run build:typescript",
"build:typescript": "tsc -p .",
"build:proto": "./compile-proto.sh",
"watch": "npm run build:typescript -- -w",
"prewatch": "npm run build:proto",
"prebuild": "npm run build:proto",
"lint": "npm run lint:prettier && npm run lint:eslint",
"lint:prettier": "prettier --check \"**/*.{ts,js,json,svg,md,yml}\"",
"lint:eslint": "eslint . --ext .js,.ts",
"lint:fix": "npm run lint:fix:prettier && npm run lint:eslint -- --fix",
"lint:fix:prettier": "prettier --write '**/*.{ts,tsx,js,json,svg,md,yml}'",
"start:server": "node server",
"start:client": "node client"
},
"keywords": [],
"author": "",
"license": "ISC",
"dependencies": {
"@grpc/grpc-js": "^1.6.8",
"google-protobuf": "^3.21.0"
},
"devDependencies": {
"@tsconfig/node12": "^1.0.11",
"@types/google-protobuf": "^3.15.6",
"@types/node": "^14.14.14",
"@typescript-eslint/eslint-plugin": "^5.31.0",
"@typescript-eslint/parser": "^5.31.0",
"eslint": "^8.20.0",
"eslint-config-prettier": "^8.5.0",
"eslint-plugin-node": "^11.1.0",
"eslint-plugin-prettier": "^4.2.1",
"grpc-tools": "^1.11.2",
"prettier": "^2.7.1",
"ts-protoc-gen": "^0.15.0",
"typescript": "^4.7.4"
},
"eslintConfig": {
"ignorePatterns": [
"**/*.js",
"proto/*.ts"
],
"env": {
"browser": false,
"es6": true,
"node": true
},
"parserOptions": {
"project": "./tsconfig.json",
"ecmaVersion": 2018,
"sourceType": "module"
},
"extends": [
"plugin:@typescript-eslint/recommended",
"prettier/@typescript-eslint",
"plugin:prettier/recommended"
]
},
"prettier": {
"singleQuote": true,
"tabWidth": 2,
"printWidth": 80,
"useTabs": false
}
}
================================================
FILE: examples/ts-protoc-gen/proto/example.proto
================================================
syntax = "proto3";
package example_package;
message ServerMessage {
string server_message = 1;
}
message ClientMessage {
string client_message = 1;
}
service Example {
rpc unaryCall(ClientMessage) returns (ServerMessage) {}
rpc serverStreamingCall(ClientMessage) returns (stream ServerMessage) {}
rpc clientStreamingCall(stream ClientMessage) returns (ServerMessage) {}
rpc bidirectionalStreamingCall(stream ClientMessage) returns (stream ServerMessage) {}
}
================================================
FILE: examples/ts-protoc-gen/proto/example_grpc_pb.d.ts
================================================
// GENERATED CODE -- DO NOT EDIT!
// package: example_package
// file: proto/example.proto
import * as proto_example_pb from "../proto/example_pb";
import * as grpc from "@grpc/grpc-js";
interface IExampleService extends grpc.ServiceDefinition<grpc.UntypedServiceImplementation> {
unaryCall: grpc.MethodDefinition<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
serverStreamingCall: grpc.MethodDefinition<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
clientStreamingCall: grpc.MethodDefinition<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
bidirectionalStreamingCall: grpc.MethodDefinition<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
}
export const ExampleService: IExampleService;
export interface IExampleServer extends grpc.UntypedServiceImplementation {
unaryCall: grpc.handleUnaryCall<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
serverStreamingCall: grpc.handleServerStreamingCall<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
clientStreamingCall: grpc.handleClientStreamingCall<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
bidirectionalStreamingCall: grpc.handleBidiStreamingCall<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
}
export class ExampleClient extends grpc.Client {
constructor(address: string, credentials: grpc.ChannelCredentials, options?: object);
unaryCall(argument: proto_example_pb.ClientMessage, callback: grpc.requestCallback<proto_example_pb.ServerMessage>): grpc.ClientUnaryCall;
unaryCall(argument: proto_example_pb.ClientMessage, metadataOrOptions: grpc.Metadata | grpc.CallOptions | null, callback: grpc.requestCallback<proto_example_pb.ServerMessage>): grpc.ClientUnaryCall;
unaryCall(argument: proto_example_pb.ClientMessage, metadata: grpc.Metadata | null, options: grpc.CallOptions | null, callback: grpc.requestCallback<proto_example_pb.ServerMessage>): grpc.ClientUnaryCall;
serverStreamingCall(argument: proto_example_pb.ClientMessage, metadataOrOptions?: grpc.Metadata | grpc.CallOptions | null): grpc.ClientReadableStream<proto_example_pb.ServerMessage>;
serverStreamingCall(argument: proto_example_pb.ClientMessage, metadata?: grpc.Metadata | null, options?: grpc.CallOptions | null): grpc.ClientReadableStream<proto_example_pb.ServerMessage>;
clientStreamingCall(callback: grpc.requestCallback<proto_example_pb.ServerMessage>): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
clientStreamingCall(metadataOrOptions: grpc.Metadata | grpc.CallOptions | null, callback: grpc.requestCallback<proto_example_pb.ServerMessage>): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
clientStreamingCall(metadata: grpc.Metadata | null, options: grpc.CallOptions | null, callback: grpc.requestCallback<proto_example_pb.ServerMessage>): grpc.ClientWritableStream<proto_example_pb.ClientMessage>;
bidirectionalStreamingCall(metadataOrOptions?: grpc.Metadata | grpc.CallOptions | null): grpc.ClientDuplexStream<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
bidirectionalStreamingCall(metadata?: grpc.Metadata | null, options?: grpc.CallOptions | null): grpc.ClientDuplexStream<proto_example_pb.ClientMessage, proto_example_pb.ServerMessage>;
}
================================================
FILE: examples/ts-protoc-gen/proto/example_pb.d.ts
================================================
// package: example_package
// file: proto/example.proto
import * as jspb from "google-protobuf";
export class ServerMessage extends jspb.Message {
getServerMessage(): string;
setServerMessage(value: string): void;
serializeBinary(): Uint8Array;
toObject(includeInstance?: boolean): ServerMessage.AsObject;
static toObject(includeInstance: boolean, msg: ServerMessage): ServerMessage.AsObject;
static extensions: {[key: number]: jspb.ExtensionFieldInfo<jspb.Message>};
static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo<jspb.Message>};
static serializeBinaryToWriter(message: ServerMessage, writer: jspb.BinaryWriter): void;
static deserializeBinary(bytes: Uint8Array): ServerMessage;
static deserializeBinaryFromReader(message: ServerMessage, reader: jspb.BinaryReader): ServerMessage;
}
export namespace ServerMessage {
export type AsObject = {
serverMessage: string,
}
}
export class ClientMessage extends jspb.Message {
getClientMessage(): string;
setClientMessage(value: string): void;
serializeBinary(): Uint8Array;
toObject(includeInstance?: boolean): ClientMessage.AsObject;
static toObject(includeInstance: boolean, msg: ClientMessage): ClientMessage.AsObject;
static extensions: {[key: number]: jspb.ExtensionFieldInfo<jspb.Message>};
static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo<jspb.Message>};
static serializeBinaryToWriter(message: ClientMessage, writer: jspb.BinaryWriter): void;
static deserializeBinary(bytes: Uint8Array): ClientMessage;
static deserializeBinaryFromReader(message: ClientMessage, reader: jspb.BinaryReader): ClientMessage;
}
export namespace ClientMessage {
export type AsObject = {
clientMessage: string,
}
}
================================================
FILE: examples/ts-protoc-gen/server.ts
================================================
import * as grpc from '@grpc/grpc-js';
import { ExampleService, IExampleServer } from './proto/example_grpc_pb';
import { ClientMessage, ServerMessage } from './proto/example_pb';
const host = '0.0.0.0:9090';
const exampleServer: IExampleServer = {
unaryCall(
call: grpc.ServerUnaryCall<ClientMessage, ServerMessage>,
callback: grpc.sendUnaryData<ServerMessage>
) {
if (call.request) {
console.log(
`(server) Got client message: ${call.request.getClientMessage()}`
);
}
const serverMessage = new ServerMessage();
serverMessage.setServerMessage('Message from server');
callback(null, serverMessage);
},
serverStreamingCall(
call: grpc.ServerWritableStream<ClientMessage, ServerMessage>
) {
const serverMessage = new ServerMessage();
serverMessage.setServerMessage('Message from server');
call.write(serverMessage);
},
clientStreamingCall(
call: grpc.ServerReadableStream<ClientMessage, ServerMessage>
) {
call.on('data', (clientMessage: ClientMessage) => {
console.log(
`(server) Got client message: ${clientMessage.getClientMessage()}`
);
});
},
bidirectionalStreamingCall(
call: grpc.ServerDuplexStream<ClientMessage, ServerMessage>
) {
call.on('data', (clientMessage: ClientMessage) => {
console.log(
`(server) Got client message: ${clientMessage.getClientMessage()}`
);
});
const serverMessage = new ServerMessage();
serverMessage.setServerMessage('Message from server');
call.write(serverMessage);
},
};
function getServer(): grpc.Server {
const server = new grpc.Server();
server.addService(ExampleService, exampleServer);
return server;
}
if (require.main === module) {
const server = getServer();
server.bindAsync(
host,
grpc.ServerCredentials.createInsecure(),
(err: Error | null, port: number) => {
if (err) {
console.error(`Server error: ${err.message}`);
} else {
console.log(`Server bound on port: ${port}`);
server.start();
}
}
);
}
================================================
FILE: examples/ts-protoc-gen/tsconfig.json
================================================
{
"extends": "@tsconfig/node12/tsconfig.json",
"exclude": ["node_modules"]
}
gitextract_7hw2d8wn/
├── .github/
│ ├── CODEOWNERS
│ ├── dependabot.yml
│ └── workflows/
│ └── test.yml
├── README.md
└── examples/
├── gradle-ts-protoc-gen/
│ ├── .gitattributes
│ ├── .gitignore
│ ├── .npmrc
│ ├── .prettierignore
│ ├── .vscode/
│ │ ├── extensions.json
│ │ └── settings.json
│ ├── README.md
│ ├── build.gradle
│ ├── client.ts
│ ├── gradle/
│ │ └── wrapper/
│ │ ├── gradle-wrapper.jar
│ │ └── gradle-wrapper.properties
│ ├── gradlew
│ ├── gradlew.bat
│ ├── package.json
│ ├── proto/
│ │ ├── example.proto
│ │ ├── example_grpc_pb.d.ts
│ │ └── example_pb.d.ts
│ ├── server.ts
│ ├── settings.gradle
│ └── tsconfig.json
├── grpc-proto-loader/
│ ├── .gitignore
│ ├── .npmrc
│ ├── .nvmrc
│ ├── .prettierignore
│ ├── .vscode/
│ │ ├── extensions.json
│ │ └── settings.json
│ ├── README.md
│ ├── client.ts
│ ├── package.json
│ ├── proto/
│ │ ├── example.proto
│ │ ├── example.ts
│ │ └── example_package/
│ │ ├── ClientMessage.ts
│ │ ├── Example.ts
│ │ └── ServerMessage.ts
│ ├── server.ts
│ └── tsconfig.json
├── grpc-web/
│ ├── .gitignore
│ ├── .npmrc
│ ├── .prettierignore
│ ├── .vscode/
│ │ ├── extensions.json
│ │ └── settings.json
│ ├── README.md
│ ├── client.ts
│ ├── compile-proto.sh
│ ├── envoy.yaml
│ ├── index.html
│ ├── package.json
│ ├── proto/
│ │ └── chat.proto
│ ├── server.ts
│ ├── tsconfig.json
│ └── webpack.config.ts
├── grpc_tools_node_protoc_ts/
│ ├── .gitignore
│ ├── .npmrc
│ ├── .prettierignore
│ ├── .vscode/
│ │ ├── extensions.json
│ │ └── settings.json
│ ├── README.md
│ ├── client.ts
│ ├── compile-proto.sh
│ ├── package.json
│ ├── proto/
│ │ ├── example.proto
│ │ ├── example_grpc_pb.d.ts
│ │ └── example_pb.d.ts
│ ├── server.ts
│ └── tsconfig.json
└── ts-protoc-gen/
├── .gitignore
├── .npmrc
├── .prettierignore
├── .vscode/
│ ├── extensions.json
│ └── settings.json
├── README.md
├── client.ts
├── compile-proto.sh
├── package.json
├── proto/
│ ├── example.proto
│ ├── example_grpc_pb.d.ts
│ └── example_pb.d.ts
├── server.ts
└── tsconfig.json
SYMBOL INDEX (80 symbols across 20 files)
FILE: examples/gradle-ts-protoc-gen/client.ts
function onClientReady (line 19) | function onClientReady() {
function doUnaryCall (line 38) | function doUnaryCall() {
function doServerStreamingCall (line 55) | function doServerStreamingCall() {
function doClientStreamingCall (line 66) | function doClientStreamingCall() {
function doBidirectionalStreamingCall (line 79) | function doBidirectionalStreamingCall() {
FILE: examples/gradle-ts-protoc-gen/proto/example_grpc_pb.d.ts
type IExampleService (line 9) | interface IExampleService extends grpc.ServiceDefinition<grpc.UntypedSer...
type IExampleServer (line 18) | interface IExampleServer extends grpc.UntypedServiceImplementation {
class ExampleClient (line 25) | class ExampleClient extends grpc.Client {
FILE: examples/gradle-ts-protoc-gen/proto/example_pb.d.ts
class ServerMessage (line 6) | class ServerMessage extends jspb.Message {
type AsObject (line 21) | type AsObject = {
class ClientMessage (line 26) | class ClientMessage extends jspb.Message {
type AsObject (line 41) | type AsObject = {
FILE: examples/gradle-ts-protoc-gen/server.ts
method unaryCall (line 8) | unaryCall(
method serverStreamingCall (line 22) | serverStreamingCall(
method clientStreamingCall (line 30) | clientStreamingCall(
method bidirectionalStreamingCall (line 40) | bidirectionalStreamingCall(
function getServer (line 55) | function getServer(): grpc.Server {
FILE: examples/grpc-proto-loader/client.ts
function onClientReady (line 32) | function onClientReady() {
function doUnaryCall (line 51) | function doUnaryCall() {
function doServerStreamingCall (line 68) | function doServerStreamingCall() {
function doClientStreamingCall (line 77) | function doClientStreamingCall() {
function doBidirectionalStreamingCall (line 88) | function doBidirectionalStreamingCall() {
FILE: examples/grpc-proto-loader/proto/example.ts
type SubtypeConstructor (line 6) | type SubtypeConstructor<Constructor extends new (...args: any) => any, S...
type ProtoGrpcType (line 10) | interface ProtoGrpcType {
FILE: examples/grpc-proto-loader/proto/example_package/ClientMessage.ts
type ClientMessage (line 4) | interface ClientMessage {
type ClientMessage__Output (line 8) | interface ClientMessage__Output {
FILE: examples/grpc-proto-loader/proto/example_package/Example.ts
type ExampleClient (line 8) | interface ExampleClient extends grpc.Client {
type ExampleHandlers (line 39) | interface ExampleHandlers extends grpc.UntypedServiceImplementation {
type ExampleDefinition (line 50) | interface ExampleDefinition extends grpc.ServiceDefinition {
FILE: examples/grpc-proto-loader/proto/example_package/ServerMessage.ts
type ServerMessage (line 4) | interface ServerMessage {
type ServerMessage__Output (line 8) | interface ServerMessage__Output {
FILE: examples/grpc-proto-loader/server.ts
method unaryCall (line 11) | unaryCall(
method serverStreamingCall (line 23) | serverStreamingCall(
method clientStreamingCall (line 31) | clientStreamingCall(
method bidirectionalStreamingCall (line 41) | bidirectionalStreamingCall(
function getServer (line 55) | function getServer(): grpc.Server {
FILE: examples/grpc-web/client.ts
function initChat (line 25) | async function initChat(user: string) {
FILE: examples/grpc-web/server.ts
function notifyChat (line 8) | function notifyChat(message: ServerMessage) {
method join (line 16) | join(call: grpc.ServerWritableStream<ClientMessage, ServerMessage>): void {
method send (line 23) | send(
function getServer (line 37) | function getServer(): grpc.Server {
FILE: examples/grpc_tools_node_protoc_ts/client.ts
function onClientReady (line 19) | function onClientReady() {
function doUnaryCall (line 38) | function doUnaryCall() {
function doServerStreamingCall (line 55) | function doServerStreamingCall() {
function doClientStreamingCall (line 66) | function doClientStreamingCall() {
function doBidirectionalStreamingCall (line 79) | function doBidirectionalStreamingCall() {
FILE: examples/grpc_tools_node_protoc_ts/proto/example_grpc_pb.d.ts
type IExampleService (line 10) | interface IExampleService extends grpc.ServiceDefinition<grpc.UntypedSer...
type IExampleService_IunaryCall (line 17) | interface IExampleService_IunaryCall extends grpc.MethodDefinition<proto...
type IExampleService_IserverStreamingCall (line 26) | interface IExampleService_IserverStreamingCall extends grpc.MethodDefini...
type IExampleService_IclientStreamingCall (line 35) | interface IExampleService_IclientStreamingCall extends grpc.MethodDefini...
type IExampleService_IbidirectionalStreamingCall (line 44) | interface IExampleService_IbidirectionalStreamingCall extends grpc.Metho...
type IExampleServer (line 56) | interface IExampleServer extends grpc.UntypedServiceImplementation {
type IExampleClient (line 63) | interface IExampleClient {
class ExampleClient (line 78) | class ExampleClient extends grpc.Client implements IExampleClient {
FILE: examples/grpc_tools_node_protoc_ts/proto/example_pb.d.ts
class ServerMessage (line 9) | class ServerMessage extends jspb.Message {
type AsObject (line 24) | type AsObject = {
class ClientMessage (line 29) | class ClientMessage extends jspb.Message {
type AsObject (line 44) | type AsObject = {
FILE: examples/grpc_tools_node_protoc_ts/server.ts
method unaryCall (line 8) | unaryCall(
method serverStreamingCall (line 22) | serverStreamingCall(
method clientStreamingCall (line 30) | clientStreamingCall(
method bidirectionalStreamingCall (line 40) | bidirectionalStreamingCall(
function getServer (line 55) | function getServer(): grpc.Server {
FILE: examples/ts-protoc-gen/client.ts
function onClientReady (line 19) | function onClientReady() {
function doUnaryCall (line 38) | function doUnaryCall() {
function doServerStreamingCall (line 55) | function doServerStreamingCall() {
function doClientStreamingCall (line 66) | function doClientStreamingCall() {
function doBidirectionalStreamingCall (line 79) | function doBidirectionalStreamingCall() {
FILE: examples/ts-protoc-gen/proto/example_grpc_pb.d.ts
type IExampleService (line 9) | interface IExampleService extends grpc.ServiceDefinition<grpc.UntypedSer...
type IExampleServer (line 18) | interface IExampleServer extends grpc.UntypedServiceImplementation {
class ExampleClient (line 25) | class ExampleClient extends grpc.Client {
FILE: examples/ts-protoc-gen/proto/example_pb.d.ts
class ServerMessage (line 6) | class ServerMessage extends jspb.Message {
type AsObject (line 21) | type AsObject = {
class ClientMessage (line 26) | class ClientMessage extends jspb.Message {
type AsObject (line 41) | type AsObject = {
FILE: examples/ts-protoc-gen/server.ts
method unaryCall (line 8) | unaryCall(
method serverStreamingCall (line 22) | serverStreamingCall(
method clientStreamingCall (line 30) | clientStreamingCall(
method bidirectionalStreamingCall (line 40) | bidirectionalStreamingCall(
function getServer (line 55) | function getServer(): grpc.Server {
Condensed preview — 83 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (106K chars).
[
{
"path": ".github/CODEOWNERS",
"chars": 13,
"preview": "* @badsyntax\n"
},
{
"path": ".github/dependabot.yml",
"chars": 136,
"preview": "version: 2\nupdates:\n- package-ecosystem: github-actions\n directory: \"/\"\n schedule:\n interval: daily\n open-pull-req"
},
{
"path": ".github/workflows/test.yml",
"chars": 1081,
"preview": "name: Test\n\non:\n push:\n branches: [master]\n pull_request:\n branches: [master]\n\njobs:\n test:\n runs-on: ubuntu"
},
{
"path": "README.md",
"chars": 1807,
"preview": "# gRPC TypeScript\n\n[](https"
},
{
"path": "examples/gradle-ts-protoc-gen/.gitattributes",
"chars": 154,
"preview": "#\n# https://help.github.com/articles/dealing-with-line-endings/\n#\n# These are explicitly windows files and should use cr"
},
{
"path": "examples/gradle-ts-protoc-gen/.gitignore",
"chars": 184,
"preview": "node_modules\n**/*.js\n!proto/*.js\n\n# Ignore Gradle project-specific cache directory\n.gradle\n\n# Ignore Gradle build output"
},
{
"path": "examples/gradle-ts-protoc-gen/.npmrc",
"chars": 36,
"preview": "registry=https://registry.npmjs.org/"
},
{
"path": "examples/gradle-ts-protoc-gen/.prettierignore",
"chars": 29,
"preview": "package-lock.json\nproto/*.ts\n"
},
{
"path": "examples/gradle-ts-protoc-gen/.vscode/extensions.json",
"chars": 196,
"preview": "{\n \"recommendations\": [\n \"dbaeumer.vscode-eslint\",\n \"EditorConfig.EditorConfig\",\n \"esbenp.prettier-vscode\",\n "
},
{
"path": "examples/gradle-ts-protoc-gen/.vscode/settings.json",
"chars": 722,
"preview": "{\n \"typescript.tsc.autoDetect\": \"off\",\n \"typescript.updateImportsOnFileMove.enabled\": \"always\",\n \"files.insertFinalNe"
},
{
"path": "examples/gradle-ts-protoc-gen/README.md",
"chars": 2016,
"preview": "# gradle-ts-protoc-gen example\n\nThis examples shows how to uses [Gradle](https://gradle.org/), the [proto compiler](http"
},
{
"path": "examples/gradle-ts-protoc-gen/build.gradle",
"chars": 1779,
"preview": "\nplugins {\n id 'java'\n id 'com.google.protobuf' version '0.8.16'\n id 'com.github.jlouns.cpe' version '0.5.0'\n}\n\nproje"
},
{
"path": "examples/gradle-ts-protoc-gen/client.ts",
"chars": 2529,
"preview": "import * as grpc from '@grpc/grpc-js';\nimport { ExampleClient } from './proto/example_grpc_pb';\nimport { ClientMessage, "
},
{
"path": "examples/gradle-ts-protoc-gen/gradle/wrapper/gradle-wrapper.properties",
"chars": 202,
"preview": "distributionBase=GRADLE_USER_HOME\ndistributionPath=wrapper/dists\ndistributionUrl=https\\://services.gradle.org/distributi"
},
{
"path": "examples/gradle-ts-protoc-gen/gradlew",
"chars": 5766,
"preview": "#!/usr/bin/env sh\n\n#\n# Copyright 2015 the original author or authors.\n#\n# Licensed under the Apache License, Version 2.0"
},
{
"path": "examples/gradle-ts-protoc-gen/gradlew.bat",
"chars": 2763,
"preview": "@rem\r\n@rem Copyright 2015 the original author or authors.\r\n@rem\r\n@rem Licensed under the Apache License, Version 2.0 (th"
},
{
"path": "examples/gradle-ts-protoc-gen/package.json",
"chars": 1913,
"preview": "{\n \"name\": \"gradle-ts-protoc-gen\",\n \"version\": \"1.0.0\",\n \"description\": \"\",\n \"main\": \"index.js\",\n \"scripts\": {\n "
},
{
"path": "examples/gradle-ts-protoc-gen/proto/example.proto",
"chars": 475,
"preview": "syntax = \"proto3\";\n\npackage example_package;\n\nmessage ServerMessage {\n string server_message = 1;\n}\n\nmessage ClientMess"
},
{
"path": "examples/gradle-ts-protoc-gen/proto/example_grpc_pb.d.ts",
"chars": 3072,
"preview": "// GENERATED CODE -- DO NOT EDIT!\n\n// package: example_package\n// file: example.proto\n\nimport * as example_pb from \"./ex"
},
{
"path": "examples/gradle-ts-protoc-gen/proto/example_pb.d.ts",
"chars": 1748,
"preview": "// package: example_package\n// file: example.proto\n\nimport * as jspb from \"google-protobuf\";\n\nexport class ServerMessage"
},
{
"path": "examples/gradle-ts-protoc-gen/server.ts",
"chars": 2088,
"preview": "import * as grpc from '@grpc/grpc-js';\nimport { ExampleService, IExampleServer } from './proto/example_grpc_pb';\nimport "
},
{
"path": "examples/gradle-ts-protoc-gen/settings.gradle",
"chars": 369,
"preview": "/*\n * This file was generated by the Gradle 'init' task.\n *\n * The settings file is used to specify which projects to in"
},
{
"path": "examples/gradle-ts-protoc-gen/tsconfig.json",
"chars": 81,
"preview": "{\n \"extends\": \"@tsconfig/node12/tsconfig.json\",\n \"exclude\": [\"node_modules\"]\n}\n"
},
{
"path": "examples/grpc-proto-loader/.gitignore",
"chars": 28,
"preview": "node_modules\ngenerated\n*.js\n"
},
{
"path": "examples/grpc-proto-loader/.npmrc",
"chars": 36,
"preview": "registry=https://registry.npmjs.org/"
},
{
"path": "examples/grpc-proto-loader/.nvmrc",
"chars": 3,
"preview": "14\n"
},
{
"path": "examples/grpc-proto-loader/.prettierignore",
"chars": 28,
"preview": "package-lock.json\ngenerated\n"
},
{
"path": "examples/grpc-proto-loader/.vscode/extensions.json",
"chars": 196,
"preview": "{\n \"recommendations\": [\n \"dbaeumer.vscode-eslint\",\n \"EditorConfig.EditorConfig\",\n \"esbenp.prettier-vscode\",\n "
},
{
"path": "examples/grpc-proto-loader/.vscode/settings.json",
"chars": 600,
"preview": "{\n \"typescript.tsc.autoDetect\": \"off\",\n \"typescript.updateImportsOnFileMove.enabled\": \"always\",\n \"files.insertFinalNe"
},
{
"path": "examples/grpc-proto-loader/README.md",
"chars": 1749,
"preview": "# grpc-proto-loader example\n\nThis example shows how to use [`@grpc/proto-loader`](https://www.npmjs.com/package/@grpc/pr"
},
{
"path": "examples/grpc-proto-loader/client.ts",
"chars": 2516,
"preview": "import * as grpc from '@grpc/grpc-js';\nimport * as protoLoader from '@grpc/proto-loader';\nimport { ProtoGrpcType } from "
},
{
"path": "examples/grpc-proto-loader/package.json",
"chars": 2080,
"preview": "{\n \"name\": \"grpc-proto-loader-example\",\n \"version\": \"1.0.0\",\n \"description\": \"\",\n \"keywords\": [],\n \"author\": \"\",\n "
},
{
"path": "examples/grpc-proto-loader/proto/example.proto",
"chars": 475,
"preview": "syntax = \"proto3\";\n\npackage example_package;\n\nmessage ServerMessage {\n string server_message = 1;\n}\n\nmessage ClientMess"
},
{
"path": "examples/grpc-proto-loader/proto/example.ts",
"chars": 692,
"preview": "import type * as grpc from '@grpc/grpc-js';\nimport type { MessageTypeDefinition } from '@grpc/proto-loader';\n\nimport typ"
},
{
"path": "examples/grpc-proto-loader/proto/example_package/ClientMessage.ts",
"chars": 178,
"preview": "// Original file: proto/example.proto\n\n\nexport interface ClientMessage {\n 'clientMessage'?: (string);\n}\n\nexport interfa"
},
{
"path": "examples/grpc-proto-loader/proto/example_package/Example.ts",
"chars": 6138,
"preview": "// Original file: proto/example.proto\n\nimport type * as grpc from '@grpc/grpc-js'\nimport type { MethodDefinition } from "
},
{
"path": "examples/grpc-proto-loader/proto/example_package/ServerMessage.ts",
"chars": 178,
"preview": "// Original file: proto/example.proto\n\n\nexport interface ServerMessage {\n 'serverMessage'?: (string);\n}\n\nexport interfa"
},
{
"path": "examples/grpc-proto-loader/server.ts",
"chars": 2301,
"preview": "import * as grpc from '@grpc/grpc-js';\nimport * as protoLoader from '@grpc/proto-loader';\nimport { ProtoGrpcType } from "
},
{
"path": "examples/grpc-proto-loader/tsconfig.json",
"chars": 81,
"preview": "{\n \"extends\": \"@tsconfig/node12/tsconfig.json\",\n \"exclude\": [\"node_modules\"]\n}\n"
},
{
"path": "examples/grpc-web/.gitignore",
"chars": 35,
"preview": "node_modules\n*.js\nproto/*.ts\ndist/\n"
},
{
"path": "examples/grpc-web/.npmrc",
"chars": 36,
"preview": "registry=https://registry.npmjs.org/"
},
{
"path": "examples/grpc-web/.prettierignore",
"chars": 24,
"preview": "package-lock.json\ndist/\n"
},
{
"path": "examples/grpc-web/.vscode/extensions.json",
"chars": 196,
"preview": "{\n \"recommendations\": [\n \"dbaeumer.vscode-eslint\",\n \"EditorConfig.EditorConfig\",\n \"esbenp.prettier-vscode\",\n "
},
{
"path": "examples/grpc-web/.vscode/settings.json",
"chars": 652,
"preview": "{\n \"typescript.tsc.autoDetect\": \"off\",\n \"typescript.updateImportsOnFileMove.enabled\": \"always\",\n \"files.insertFinalNe"
},
{
"path": "examples/grpc-web/README.md",
"chars": 1946,
"preview": "# grpc-web\n\nThis examples shows how to use the [proto compiler](https://www.npmjs.com/package/grpc-tools), [`ts-protoc-g"
},
{
"path": "examples/grpc-web/client.ts",
"chars": 1994,
"preview": "/* eslint-disable @typescript-eslint/no-non-null-assertion */\n\nimport { RpcError as GrpcWebError } from 'grpc-web';\nimpo"
},
{
"path": "examples/grpc-web/compile-proto.sh",
"chars": 861,
"preview": "#!/usr/bin/env bash\n\nOUT_DIR=\".\"\nTS_OUT_DIR=\".\"\nIN_DIR=\"./proto\"\nPROTOC=\"$(npm bin)/grpc_tools_node_protoc\"\nPROTOC_GEN_T"
},
{
"path": "examples/grpc-web/envoy.yaml",
"chars": 1425,
"preview": "static_resources:\n listeners:\n - name: listener_0\n address:\n socket_address: { address: 0.0.0.0, port_value: 8"
},
{
"path": "examples/grpc-web/index.html",
"chars": 957,
"preview": "<!DOCTYPE html>\n<html lang=\"en\">\n <head>\n <meta charset=\"UTF-8\" />\n <title>gRPC-Web Example</title>\n <script s"
},
{
"path": "examples/grpc-web/package.json",
"chars": 2478,
"preview": "{\n \"name\": \"grpc-web-example\",\n \"version\": \"1.0.0\",\n \"description\": \"\",\n \"private\": true,\n \"scripts\": {\n \"build\""
},
{
"path": "examples/grpc-web/proto/chat.proto",
"chars": 303,
"preview": "syntax = \"proto3\";\n\npackage chat_package;\n\nmessage ServerMessage {\n string user = 1;\n string text = 2;\n}\n\nmessage Clie"
},
{
"path": "examples/grpc-web/server.ts",
"chars": 1651,
"preview": "import * as grpc from '@grpc/grpc-js';\nimport { ChatService, IChatServer } from './proto/chat_grpc_pb';\nimport { ClientM"
},
{
"path": "examples/grpc-web/tsconfig.json",
"chars": 128,
"preview": "{\n \"extends\": \"@tsconfig/node12/tsconfig.json\",\n \"compilerOptions\": {\n \"lib\": [\"DOM\"]\n },\n \"exclude\": [\"node_modu"
},
{
"path": "examples/grpc-web/webpack.config.ts",
"chars": 234,
"preview": "import * as path from 'path';\n\nexport default {\n mode: 'production',\n entry: {\n index: './client.js',\n },\n output"
},
{
"path": "examples/grpc_tools_node_protoc_ts/.gitignore",
"chars": 33,
"preview": "node_modules\n**/*.js\n!proto/*.js\n"
},
{
"path": "examples/grpc_tools_node_protoc_ts/.npmrc",
"chars": 36,
"preview": "registry=https://registry.npmjs.org/"
},
{
"path": "examples/grpc_tools_node_protoc_ts/.prettierignore",
"chars": 29,
"preview": "package-lock.json\nproto/*.ts\n"
},
{
"path": "examples/grpc_tools_node_protoc_ts/.vscode/extensions.json",
"chars": 196,
"preview": "{\n \"recommendations\": [\n \"dbaeumer.vscode-eslint\",\n \"EditorConfig.EditorConfig\",\n \"esbenp.prettier-vscode\",\n "
},
{
"path": "examples/grpc_tools_node_protoc_ts/.vscode/settings.json",
"chars": 673,
"preview": "{\n \"typescript.tsc.autoDetect\": \"off\",\n \"typescript.updateImportsOnFileMove.enabled\": \"always\",\n \"files.insertFinalNe"
},
{
"path": "examples/grpc_tools_node_protoc_ts/README.md",
"chars": 1858,
"preview": "# grpc_tools_node_protoc_ts example\n\nThis example shows how to use the [proto compiler](https://www.npmjs.com/package/gr"
},
{
"path": "examples/grpc_tools_node_protoc_ts/client.ts",
"chars": 2529,
"preview": "import * as grpc from '@grpc/grpc-js';\nimport { ExampleClient } from './proto/example_grpc_pb';\nimport { ClientMessage, "
},
{
"path": "examples/grpc_tools_node_protoc_ts/compile-proto.sh",
"chars": 484,
"preview": "#!/usr/bin/env bash\n\nOUT_DIR=\".\"\nTS_OUT_DIR=\".\"\nIN_DIR=\"./proto\"\nPROTOC=\"$(npm bin)/grpc_tools_node_protoc\"\nPROTOC_GEN_T"
},
{
"path": "examples/grpc_tools_node_protoc_ts/package.json",
"chars": 1914,
"preview": "{\n \"name\": \"grpc-js-example\",\n \"version\": \"1.0.0\",\n \"description\": \"\",\n \"main\": \"index.js\",\n \"scripts\": {\n \"buil"
},
{
"path": "examples/grpc_tools_node_protoc_ts/proto/example.proto",
"chars": 475,
"preview": "syntax = \"proto3\";\n\npackage example_package;\n\nmessage ServerMessage {\n string server_message = 1;\n}\n\nmessage ClientMess"
},
{
"path": "examples/grpc_tools_node_protoc_ts/proto/example_grpc_pb.d.ts",
"chars": 8004,
"preview": "// package: example_package\n// file: proto/example.proto\n\n/* tslint:disable */\n/* eslint-disable */\n\nimport * as grpc fr"
},
{
"path": "examples/grpc_tools_node_protoc_ts/proto/example_pb.d.ts",
"chars": 1872,
"preview": "// package: example_package\n// file: proto/example.proto\n\n/* tslint:disable */\n/* eslint-disable */\n\nimport * as jspb fr"
},
{
"path": "examples/grpc_tools_node_protoc_ts/server.ts",
"chars": 2088,
"preview": "import * as grpc from '@grpc/grpc-js';\nimport { ExampleService, IExampleServer } from './proto/example_grpc_pb';\nimport "
},
{
"path": "examples/grpc_tools_node_protoc_ts/tsconfig.json",
"chars": 81,
"preview": "{\n \"extends\": \"@tsconfig/node12/tsconfig.json\",\n \"exclude\": [\"node_modules\"]\n}\n"
},
{
"path": "examples/ts-protoc-gen/.gitignore",
"chars": 30,
"preview": "node_modules\n*.js\n!proto/*.js\n"
},
{
"path": "examples/ts-protoc-gen/.npmrc",
"chars": 36,
"preview": "registry=https://registry.npmjs.org/"
},
{
"path": "examples/ts-protoc-gen/.prettierignore",
"chars": 29,
"preview": "package-lock.json\nproto/*.ts\n"
},
{
"path": "examples/ts-protoc-gen/.vscode/extensions.json",
"chars": 196,
"preview": "{\n \"recommendations\": [\n \"dbaeumer.vscode-eslint\",\n \"EditorConfig.EditorConfig\",\n \"esbenp.prettier-vscode\",\n "
},
{
"path": "examples/ts-protoc-gen/.vscode/settings.json",
"chars": 652,
"preview": "{\n \"typescript.tsc.autoDetect\": \"off\",\n \"typescript.updateImportsOnFileMove.enabled\": \"always\",\n \"files.insertFinalNe"
},
{
"path": "examples/ts-protoc-gen/README.md",
"chars": 1902,
"preview": "# ts-protoc-gen\n\nThis examples shows how to use the [proto compiler](https://www.npmjs.com/package/grpc-tools), [`ts-pro"
},
{
"path": "examples/ts-protoc-gen/client.ts",
"chars": 2529,
"preview": "import * as grpc from '@grpc/grpc-js';\nimport { ExampleClient } from './proto/example_grpc_pb';\nimport { ClientMessage, "
},
{
"path": "examples/ts-protoc-gen/compile-proto.sh",
"chars": 505,
"preview": "#!/usr/bin/env bash\n\nOUT_DIR=\".\"\nTS_OUT_DIR=\".\"\nIN_DIR=\"./proto\"\nPROTOC=\"$(npm bin)/grpc_tools_node_protoc\"\nPROTOC_GEN_T"
},
{
"path": "examples/ts-protoc-gen/package.json",
"chars": 1942,
"preview": "{\n \"name\": \"grpc-js-example\",\n \"version\": \"1.0.0\",\n \"description\": \"\",\n \"main\": \"index.js\",\n \"scripts\": {\n \"buil"
},
{
"path": "examples/ts-protoc-gen/proto/example.proto",
"chars": 475,
"preview": "syntax = \"proto3\";\n\npackage example_package;\n\nmessage ServerMessage {\n string server_message = 1;\n}\n\nmessage ClientMess"
},
{
"path": "examples/ts-protoc-gen/proto/example_grpc_pb.d.ts",
"chars": 3307,
"preview": "// GENERATED CODE -- DO NOT EDIT!\n\n// package: example_package\n// file: proto/example.proto\n\nimport * as proto_example_p"
},
{
"path": "examples/ts-protoc-gen/proto/example_pb.d.ts",
"chars": 1754,
"preview": "// package: example_package\n// file: proto/example.proto\n\nimport * as jspb from \"google-protobuf\";\n\nexport class ServerM"
},
{
"path": "examples/ts-protoc-gen/server.ts",
"chars": 2088,
"preview": "import * as grpc from '@grpc/grpc-js';\nimport { ExampleService, IExampleServer } from './proto/example_grpc_pb';\nimport "
},
{
"path": "examples/ts-protoc-gen/tsconfig.json",
"chars": 81,
"preview": "{\n \"extends\": \"@tsconfig/node12/tsconfig.json\",\n \"exclude\": [\"node_modules\"]\n}\n"
}
]
// ... and 1 more files (download for full content)
About this extraction
This page contains the full source code of the badsyntax/grpc-js-typescript GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 83 files (92.9 KB), approximately 26.2k tokens, and a symbol index with 80 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.